This is the mail archive of the
libc-help@sourceware.org
mailing list for the glibc project.
Questions about strptime()/strftime()
- From: Richard Harvey Chapman <hchapman at 3gfp dot com>
- To: libc-help at sourceware dot org
- Date: Sat, 21 Jun 2008 13:57:39 -0400
- Subject: Questions about strptime()/strftime()
Hello all and thanks in advance.
I'm trying to transmit date and time in a user readable format from one
machine to another. My goal is a format like this:
"17:25:58 2008-06-20 -0500"
I am thinking of using the strftime() and strptime() functions except
that I don't get consistent results. I've attached a sample program and
included here the output on a recent 10.5.3 OS X machine and an Ubuntu
Linux machine using libc-2.3.6. The Linux version segfaults when
strftime() uses the tm struct that was filled using strptime().
Can someone suggest a reliable method for this?
Am I supposed to be initializing the tm struct?
OS X output:
harveybook:coding_tests hchapman$ make time_formats && ./time_formats
g++ -ggdb time_formats.cc -o time_formats
-----strftime(localtime(time())) output-----
Time now is "17:25:58 2008-06-20 -0500 UTC" (Local)
Time now is "17:25:58 2008-06-20 -0500 UTC" (GM)
-----printf() of strptime(strftime(...))-----
Reverse time is "17:25:58 2008-06-20 -0500 (null) DST" (Local)
Reverse time is "17:25:58 2008-06-20 -0500 (null) DST" (GM)
-----printf() of original tm structs used with strftime()-----
Reverse time is "17:25:58 2008-06-20 00000 UTC " (Local)
Reverse time is "17:25:58 2008-06-20 00000 UTC " (Local)
-----printf() of strftime(strptime(strftime(...)))-----
Time now is "17:25:58 2008-06-20 -0400 EDT" (Local)
Time now is "17:25:58 2008-06-20 " (GM)
-----Crude attempt to go back-and-forth using time() and ctime()-----
Time in seconds is "1213982758"
Time reversed is "Fri Jun 20 13:25:58 2008
"
Ubuntu output:
dev1:~# g++ -ggdb time_formats.cc -o time_formats && ./time_formats
-----strftime(localtime(time())) output-----
Time now is "17:25:03 2008-06-20 +0000 GMT" (Local)
Time now is "17:25:03 2008-06-20 +0000 GMT" (GM)
-----printf() of strptime(strftime(...))-----
Reverse time is
"17:25:03 2008-06-20 00000 UÂÃ]ÃÂÂÂÂÂÂÂÂÂÂÂUÂÃ]ÃÂÂÂÂÂÂÂÂÂÂÂUÂÃÂU
ÂÃtÂEÂ DST" (Local)
Reverse time is "17:25:03 2008-06-20 00000 DST" (GM)
-----printf() of original tm structs used with strftime()-----
Reverse time is "17:25:03 2008-06-20 00000 GMT " (Local)
Reverse time is "17:25:03 2008-06-20 00000 GMT " (Local)
-----printf() of strftime(strptime(strftime(...)))-----
Time now is "17:25:03 2008-06-20 UÂÃ]ÃÂÂÂÂÂÂÂÂÂÂÂUÂÃ]ÃÂÂÂÂÂÂÂÂÂÂÂUÂÃÂU
ÂÃtÂEÂ" (Local)
Segmentation fault
#include <stdio.h>
#include <time.h>
// size_t
// strftime(char *restrict s, size_t maxsize, const char *restrict format,
// const struct tm *restrict timeptr);
int main()
{
char str[100];
char *result = NULL;
time_t t = time(NULL);
struct tm *tt = localtime(&t);
struct tm *tt2 = gmtime(&t);
struct tm tt_r;
struct tm tt2_r;
char format[] = "%T %F %z %Z"; // time, date, zone // "15:02:18 2008-06-20 -0500 UTC"
int len = 0;
// First, test conversion to a string
printf("-----strftime(localtime(time())) output-----\n");
len = strftime(str, 100, format, tt);
printf(" Time now is \"%s\" (Local)\n", str);
len = strftime(str, 100, format, tt2);
printf(" Time now is \"%s\" (GM)\n", str);
printf("\n");
// Second, test converting back and verifying the results
printf("-----printf() of strptime(strftime(...))-----\n");
result = strptime(str, format, &tt_r);
printf("Reverse time is \"%02u:%02u:%02u %4u-%02u-%02u %05ld %s %s\" (Local)\n",
tt_r.tm_hour,
tt_r.tm_min,
tt_r.tm_sec,
tt_r.tm_year + 1900,
tt_r.tm_mon + 1,
tt_r.tm_mday,
tt_r.tm_gmtoff / 36,
tt_r.tm_zone == NULL ? "(null)" : tt_r.tm_zone,
tt_r.tm_isdst ? "DST" : "");
result = strptime(str, format, &tt2_r);
printf("Reverse time is \"%02u:%02u:%02u %4u-%02u-%02u %05ld %s %s\" (GM)\n",
tt2_r.tm_hour,
tt2_r.tm_min,
tt2_r.tm_sec,
tt2_r.tm_year + 1900,
tt2_r.tm_mon + 1,
tt2_r.tm_mday,
tt2_r.tm_gmtoff / 36,
tt2_r.tm_zone == NULL ? "(null)" : tt2_r.tm_zone,
tt2_r.tm_isdst ? "DST" : "");
printf("\n");
// Try printing the original tm structs
printf("-----printf() of original tm structs used with strftime()-----\n");
printf("Reverse time is \"%02u:%02u:%02u %4u-%02u-%02u %05ld %s %s\" (Local)\n",
tt->tm_hour,
tt->tm_min,
tt->tm_sec,
tt->tm_year + 1900,
tt->tm_mon + 1,
tt->tm_mday,
tt->tm_gmtoff / 36,
tt->tm_zone == NULL ? "(null)" : tt->tm_zone,
tt->tm_isdst ? "DST" : "");
printf("Reverse time is \"%02u:%02u:%02u %4u-%02u-%02u %05ld %s %s\" (Local)\n",
tt2->tm_hour,
tt2->tm_min,
tt2->tm_sec,
tt2->tm_year + 1900,
tt2->tm_mon + 1,
tt2->tm_mday,
tt2->tm_gmtoff / 36,
tt2->tm_zone == NULL ? "(null)" : tt2->tm_zone,
tt2->tm_isdst ? "DST" : "");
printf("\n");
// Can we take the reversed tm struct and then convert it back into a string?
printf("-----printf() of strftime(strptime(strftime(...)))-----\n");
len = strftime(str, 100, format, &tt_r);
printf(" Time now is \"%s\" (Local)\n", str);
len = strftime(str, 100, format, &tt2_r);
printf(" Time now is \"%s\" (GM)\n", str);
printf("\n");
// What about time in seconds?
printf("-----Crude attempt to go back-and-forth using time() and ctime()-----\n");
time_t t_s = time(NULL);
printf("Time in seconds is \"%lu\"\n", t_s);
printf("Time reversed is \"%s\"\n", ctime(&t_s));
return(0);
}