Section 6.10. Time and Date Routines

team bbl


6.10. Time and Date Routines

The basic time service provided by the UNIX kernel counts the number of seconds that have passed since the Epoch: 00:00:00 January 1, 1970, Coordinated Universal Time (UTC). In Section 1.10, we said that these seconds are represented in a time_t data type, and we call them calendar times. These calendar times represent both the time and the date. The UNIX System has always differed from other operating systems in (a) keeping time in UTC instead of the local time, (b) automatically handling conversions, such as daylight saving time, and (c) keeping the time and date as a single quantity.

The time function returns the current time and date.

 #include <time.h> time_t time(time_t *calptr); 

Returns: value of time if OK, 1 on error


The time value is always returned as the value of the function. If the argument is non- null, the time value is also stored at the location pointed to by calptr.

We haven't said how the kernel's notion of the current time is initialized. Historically, on implementations derived from System V, the stime(2) function was called, whereas BSD-derived systems used settimeofday(2).

The Single UNIX Specification doesn't specify how a system sets its current time.

The gettimeofday function provides greater resolution (up to a microsecond) than the time function. This is important for some applications.

[View full width]

 #include <sys/time.h> int gettimeofday(struct timeval *restrict tp, void  *restrict tzp); 

Returns: 0 always


This function is defined as an XSI extension in the Single UNIX Specification. The only legal value for tzp is NULL; other values result in unspecified behavior. Some platforms support the specification of a time zone through the use of tzp, but this is implementation-specific and not defined by the Single UNIX Specification.

The gettimeofday function stores the current time as measured from the Epoch in the memory pointed to by tp. This time is represented as a timeval structure, which stores seconds and microseconds:

    struct timeval {            time_t tv_sec;    /* seconds */            long   tv_usec;   /* microseconds */    }; 

Once we have the integer value that counts the number of seconds since the Epoch, we normally call one of the other time functions to convert it to a human-readable time and date. Figure 6.8 shows the relationships between the various time functions.

Figure 6.8. Relationship of the various time functions


(The four functions in this figure that are shown with dashed lineslocaltime, mktime, ctime, and strftimeare all affected by the TZ environment variable, which we describe later in this section.)

The two functions localtime and gmtime convert a calendar time into what's called a broken-down time, a tm structure.

    struct tm {        /* a broken-down time */      int  tm_sec;     /* seconds after the minute: [0 - 60] */      int  tm_min;     /* minutes after the hour: [0 - 59] */      int  tm_hour;    /* hours after midnight: [0 - 23] */      int  tm_mday;    /* day of the month: [1 - 31] */      int  tm_mon;     /* months since January: [0 - 11] */      int  tm_year;    /* years since 1900 */      int  tm_wday;    /* days since Sunday: [0 - 6] */      int  tm_yday;    /* days since January 1: [0 - 365] */      int  tm_isdst;   /* daylight saving time flag: <0, 0, >0 */    }; 

The reason that the seconds can be greater than 59 is to allow for a leap second. Note that all the fields except the day of the month are 0-based. The daylight saving time flag is positive if daylight saving time is in effect, 0 if it's not in effect, and negative if the information isn't available.

In previous versions of the Single UNIX Specification, double leap seconds were allowed. Thus, the valid range of values for the tm_sec member was 061. The formal definition of UTC doesn't allow for double leap seconds, so the valid range for seconds is now defined to be 060.

 #include <time.h> struct tm *gmtime(const time_t *calptr); struct tm *localtime(const time_t *calptr); 

Both return: pointer to broken-down time


The difference between localtime and gmtime is that the first converts the calendar time to the local time, taking into account the local time zone and daylight saving time flag, whereas the latter converts the calendar time into a broken-down time expressed as UTC.

The function mktime takes a broken-down time, expressed as a local time, and converts it into a time_t value.

 #include <time.h> time_t mktime(struct tm *tmptr); 

Returns: calendar time if OK, 1 on error


The asctime and ctime functions produce the familiar 26-byte string that is similar to the default output of the date(1) command:

     Tue Feb 10 18:27:38 2004\n\0 

 #include <time.h> char *asctime(const struct tm *tmptr); char *ctime(const time_t *calptr); 

Both return: pointer to null-terminated string


The argument to asctime is a pointer to a broken-down string, whereas the argument to ctime is a pointer to a calendar time.

The final time function, strftime, is the most complicated. It is a printf-like function for time values.

 #include <time.h> size_t strftime(char *restrict buf, size_t maxsize,                 const char *restrict format,                 const struct tm *restrict tmptr); 

Returns: number of characters stored in array if room, 0 otherwise


The final argument is the time value to format, specified by a pointer to a broken-down time value. The formatted result is stored in the array buf whose size is maxsize characters. If the size of the result, including the terminating null, fits in the buffer, the function returns the number of characters stored in buf, excluding the terminating null. Otherwise, the function returns 0.

The format argument controls the formatting of the time value. Like the printf functions, conversion specifiers are given as a percent followed by a special character. All other characters in the format string are copied to the output. Two percents in a row generate a single percent in the output. Unlike the printf functions, each conversion specified generates a different fixed-size output stringthere are no field widths in the format string. Figure 6.9 describes the 37 ISO C conversion specifiers. The third column of this figure is from the output of strftime under Linux, corresponding to the time and date Tue Feb 10 18:27:38 EST 2004.

Figure 6.9. Conversion specifiers for strftime

Format

Description

Example

%a

abbreviated weekday name

Tue

%A

full weekday name

Tuesday

%b

abbreviated month name

Feb

%B

full month name

February

%c

date and time

Tue Feb 10 18:27:38 2004

%C

year/100: [0099]

20

%d

day of the month: [0131]

10

%D

date [MM/DD/YY]

02/10/04

%e

day of month (single digit preceded by space) [131]

10

%F

ISO 8601 date format [YYYYMMDD]

2004-02-10

%g

last two digits of ISO 8601 week-based year [0099]

04

%G

ISO 8601 week-based year

2004

%h

same as %b

Feb

%H

hour of the day (24-hour format): [0023]

18

%I

hour of the day (12-hour format): [0112]

06

%j

day of the year: [001366]

041

%m

month: [0112]

02

%M

minute: [0059]

27

%n

newline character

 

%p

AM/PM

PM

%r

locale's time (12-hour format)

06:27:38 PM

%R

same as "%H:%M"

18:27

%S

second: [0060]

38

%t

horizontal tab character

 

%T

same as "%H:%M:%S"

18:27:38

%u

ISO 8601 weekday [Monday=1, 17]

2

%U

Sunday week number: [0053]

06

%V

ISO 8601 week number: [0153]

07

%w

weekday: [0=Sunday, 06]

2

%W

Monday week number: [0053]

06

%x

date

02/10/04

%X

time

18:27:38

%y

last two digits of year: [0099]

04

%Y

year

2004

%z

offset from UTC in ISO 8601 format

-0500

%Z

time zone name

EST

%%

translates to a percent sign

%


The only specifiers that are not self-evident are %U, %V, and %W. The %U specifier represents the week number of the year, where the week containing the first Sunday is week 1. The %W specifier represents the week number of the year, where the week containing the first Monday is week 1. The %V specifier is different. If the week containing the first day in January has four or more days in the new year, then this is treated as week 1. Otherwise, it is treated as the last week of the previous year. In both cases, Monday is treated as the first day of the week.

As with printf, strftime supports modifiers for some of the conversion specifiers. The E and O modifiers can be used to generate an alternate format if supported by the locale.

Some systems support additional, nonstandard extensions to the format string for strftime.

We mentioned that the four functions in Figure 6.8 with dashed lines were affected by the TZ environment variable: localtime, mktime, ctime, and strftime. If defined, the value of this environment variable is used by these functions instead of the default time zone. If the variable is defined to be a null string, such as TZ=, then UTC is normally used. The value of this environment variable is often something like TZ=EST5EDT, but POSIX.1 allows a much more detailed specification. Refer to the Environment Variables chapter of the Single UNIX Specification [Open Group 2004] for all the details on the TZ variable.

All the time and date functions described in this section, except gettimeofday, are defined by the ISO C standard. POSIX.1, however, added the TZ environment variable. On FreeBSD 5.2.1, Linux 2.4.22, and Mac OS X 10.3, more information on the TZ variable can be found in the tzset(3) manual page. On Solaris 9, this information is in the environ(5) manual page.

    team bbl



    Advanced Programming in the UNIX Environment
    Advanced Programming in the UNIX Environment, Second Edition (Addison-Wesley Professional Computing Series)
    ISBN: 0321525949
    EAN: 2147483647
    Year: 2005
    Pages: 370

    flylib.com © 2008-2017.
    If you may any questions please contact us: flylib@qtcs.net