2 * Unit test suite for time functions.
4 * Copyright 2004 Uwe Bonnes
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 #include "wine/test.h"
26 #include <stdlib.h> /*setenv*/
27 #include <stdio.h> /*printf*/
31 #define _MAX__TIME64_T (((__time64_t)0x00000007 << 32) | 0x93406FFF)
33 #define SECSPERDAY 86400
34 #define SECSPERHOUR 3600
36 #define MINSPERHOUR 60
37 #define HOURSPERDAY 24
40 const char *short_wday
[7];
42 const char *short_mon
[12];
46 const char *short_date
;
54 static __time32_t (__cdecl
*p_mkgmtime32
)(struct tm
*);
55 static struct tm
* (__cdecl
*p_gmtime32
)(__time32_t
*);
56 static struct tm
* (__cdecl
*p_gmtime
)(time_t*);
57 static errno_t (__cdecl
*p_gmtime32_s
)(struct tm
*, __time32_t
*);
58 static struct tm
* (__cdecl
*p_gmtime64
)(__time64_t
*);
59 static errno_t (__cdecl
*p_gmtime64_s
)(struct tm
*, __time64_t
*);
60 static errno_t (__cdecl
*p_strtime_s
)(char*,size_t);
61 static errno_t (__cdecl
*p_strdate_s
)(char*,size_t);
62 static errno_t (__cdecl
*p_localtime32_s
)(struct tm
*, __time32_t
*);
63 static errno_t (__cdecl
*p_localtime64_s
)(struct tm
*, __time64_t
*);
64 static int* (__cdecl
*p__daylight
)(void);
65 static int* (__cdecl
*p___p__daylight
)(void);
66 static long* (__cdecl
*p___p__dstbias
)(void);
67 static long* (__cdecl
*p__dstbias
)(void);
68 static long* (__cdecl
*p___p__timezone
)(void);
69 static size_t (__cdecl
*p_strftime
)(char *, size_t, const char *, const struct tm
*);
70 static size_t (__cdecl
*p__Strftime
)(char*, size_t, const char*, const struct tm
*, void*);
71 static size_t (__cdecl
*p_wcsftime
)(wchar_t *, size_t, const wchar_t *, const struct tm
*);
72 static char* (__cdecl
*p_asctime
)(const struct tm
*);
74 static void init(void)
76 HMODULE hmod
= LoadLibraryA("msvcrt.dll");
78 p_gmtime32
= (void*)GetProcAddress(hmod
, "_gmtime32");
79 p_gmtime
= (void*)GetProcAddress(hmod
, "gmtime");
80 p_gmtime32_s
= (void*)GetProcAddress(hmod
, "_gmtime32_s");
81 p_gmtime64
= (void*)GetProcAddress(hmod
, "_gmtime64");
82 p_gmtime64_s
= (void*)GetProcAddress(hmod
, "_gmtime64_s");
83 p_mkgmtime32
= (void*)GetProcAddress(hmod
, "_mkgmtime32");
84 p_strtime_s
= (void*)GetProcAddress(hmod
, "_strtime_s");
85 p_strdate_s
= (void*)GetProcAddress(hmod
, "_strdate_s");
86 p_localtime32_s
= (void*)GetProcAddress(hmod
, "_localtime32_s");
87 p_localtime64_s
= (void*)GetProcAddress(hmod
, "_localtime64_s");
88 p__daylight
= (void*)GetProcAddress(hmod
, "__daylight");
89 p___p__daylight
= (void*)GetProcAddress(hmod
, "__p__daylight");
90 p___p__dstbias
= (void*)GetProcAddress(hmod
, "__p__dstbias");
91 p__dstbias
= (void*)GetProcAddress(hmod
, "__dstbias");
92 p___p__timezone
= (void*)GetProcAddress(hmod
, "__p__timezone");
93 p_strftime
= (void*)GetProcAddress(hmod
, "strftime");
94 p__Strftime
= (void*)GetProcAddress(hmod
, "_Strftime");
95 p_wcsftime
= (void*)GetProcAddress(hmod
, "wcsftime");
96 p_asctime
= (void*)GetProcAddress(hmod
, "asctime");
99 static int get_test_year(time_t *start
)
101 time_t now
= time(NULL
);
102 struct tm
*tm
= localtime(&now
);
104 /* compute start of year in seconds */
105 *start
= SECSPERDAY
* ((tm
->tm_year
- 70) * 365 +
106 (tm
->tm_year
- 69) / 4 -
107 (tm
->tm_year
- 1) / 100 +
108 (tm
->tm_year
+ 299) / 400);
112 static void test_ctime(void)
116 ret
= ctime(&badtime
);
117 ok(ret
== NULL
, "expected ctime to return NULL, got %s\n", ret
);
119 static void test_gmtime(void)
121 __time32_t valid
, gmt
;
122 struct tm
* gmt_tm
, gmt_tm_s
;
126 win_skip("Skipping _gmtime32 tests\n");
130 gmt_tm
= p_gmtime32(NULL
);
131 ok(gmt_tm
== NULL
, "gmt_tm != NULL\n");
134 gmt_tm
= p_gmtime32(&gmt
);
135 ok(gmt_tm
==NULL
|| broken(gmt_tm
->tm_year
==70 && gmt_tm
->tm_sec
<0), "gmt_tm != NULL\n");
138 gmt_tm
= p_gmtime32(&gmt
);
140 ok(0, "_gmtime32() failed\n");
144 ok(((gmt_tm
->tm_year
== 70) && (gmt_tm
->tm_mon
== 0) && (gmt_tm
->tm_yday
== 0) &&
145 (gmt_tm
->tm_mday
== 1) && (gmt_tm
->tm_wday
== 4) && (gmt_tm
->tm_hour
== 0) &&
146 (gmt_tm
->tm_min
== 0) && (gmt_tm
->tm_sec
== 0) && (gmt_tm
->tm_isdst
== 0)),
147 "Wrong date:Year %4d mon %2d yday %3d mday %2d wday %1d hour%2d min %2d sec %2d dst %2d\n",
148 gmt_tm
->tm_year
, gmt_tm
->tm_mon
, gmt_tm
->tm_yday
, gmt_tm
->tm_mday
, gmt_tm
->tm_wday
,
149 gmt_tm
->tm_hour
, gmt_tm
->tm_min
, gmt_tm
->tm_sec
, gmt_tm
->tm_isdst
);
152 win_skip("Skipping _mkgmtime32 tests\n");
156 gmt_tm
->tm_wday
= gmt_tm
->tm_yday
= 0;
157 gmt
= p_mkgmtime32(gmt_tm
);
158 ok(gmt
== valid
, "gmt = %lu\n", gmt
);
159 ok(gmt_tm
->tm_wday
== 4, "gmt_tm->tm_wday = %d\n", gmt_tm
->tm_wday
);
160 ok(gmt_tm
->tm_yday
== 0, "gmt_tm->tm_yday = %d\n", gmt_tm
->tm_yday
);
162 gmt_tm
->tm_wday
= gmt_tm
->tm_yday
= 0;
163 gmt_tm
->tm_isdst
= -1;
164 gmt
= p_mkgmtime32(gmt_tm
);
165 ok(gmt
== valid
, "gmt = %lu\n", gmt
);
166 ok(gmt_tm
->tm_wday
== 4, "gmt_tm->tm_wday = %d\n", gmt_tm
->tm_wday
);
167 ok(gmt_tm
->tm_yday
== 0, "gmt_tm->tm_yday = %d\n", gmt_tm
->tm_yday
);
169 gmt_tm
->tm_wday
= gmt_tm
->tm_yday
= 0;
170 gmt_tm
->tm_isdst
= 1;
171 gmt
= p_mkgmtime32(gmt_tm
);
172 ok(gmt
== valid
, "gmt = %lu\n", gmt
);
173 ok(gmt_tm
->tm_wday
== 4, "gmt_tm->tm_wday = %d\n", gmt_tm
->tm_wday
);
174 ok(gmt_tm
->tm_yday
== 0, "gmt_tm->tm_yday = %d\n", gmt_tm
->tm_yday
);
176 gmt
= valid
= 173921;
177 gmt_tm
= p_gmtime32(&gmt
);
179 ok(0, "_gmtime32() failed\n");
183 gmt_tm
->tm_isdst
= -1;
184 gmt
= p_mkgmtime32(gmt_tm
);
185 ok(gmt
== valid
, "gmt = %lu\n", gmt
);
186 ok(gmt_tm
->tm_wday
== 6, "gmt_tm->tm_wday = %d\n", gmt_tm
->tm_wday
);
187 ok(gmt_tm
->tm_yday
== 2, "gmt_tm->tm_yday = %d\n", gmt_tm
->tm_yday
);
189 gmt_tm
->tm_isdst
= 1;
190 gmt
= p_mkgmtime32(gmt_tm
);
191 ok(gmt
== valid
, "gmt = %lu\n", gmt
);
194 win_skip("Skipping _gmtime32_s tests\n");
200 err
= p_gmtime32_s(NULL
, &gmt
);
201 ok(err
== EINVAL
, "err = %d\n", err
);
202 ok(errno
== EINVAL
, "errno = %d\n", errno
);
206 err
= p_gmtime32_s(&gmt_tm_s
, &gmt
);
207 ok(gmt_tm_s
.tm_year
== -1 || broken(gmt_tm_s
.tm_year
== 70 && gmt_tm_s
.tm_sec
< 0),
208 "tm_year = %d, tm_sec = %d\n", gmt_tm_s
.tm_year
, gmt_tm_s
.tm_sec
);
209 if(gmt_tm_s
.tm_year
== -1) {
210 ok(err
==EINVAL
, "err = %d\n", err
);
211 ok(errno
==EINVAL
, "errno = %d\n", errno
);
215 static void test_gmtime64(void)
222 memset(&tm
, 0xcc, sizeof(tm
));
223 ptm
= p_gmtime64(&t
);
226 skip("Old gmtime64 limits, skipping tests.\n");
229 ok(!!ptm
, "got NULL.\n");
230 ret
= p_gmtime64_s(&tm
, &t
);
231 ok(!ret
, "got %d.\n", ret
);
232 ok(tm
.tm_year
== 69 && tm
.tm_hour
== 23 && tm
.tm_min
== 59 && tm
.tm_sec
== 59, "got %d, %d, %d, %d.\n",
233 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
236 memset(&tm
, 0xcc, sizeof(tm
));
237 ptm
= p_gmtime64(&t
);
238 ok(!!ptm
, "got NULL.\n");
239 ret
= p_gmtime64_s(&tm
, &t
);
240 ok(!ret
, "got %d.\n", ret
);
241 ok(tm
.tm_year
== 69 && tm
.tm_hour
== 12 && tm
.tm_min
== 0 && tm
.tm_sec
== 0, "got %d, %d, %d, %d.\n",
242 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
243 ptm
= p_gmtime32((__time32_t
*)&t
);
244 ok(!!ptm
, "got NULL.\n");
245 memset(&tm
, 0xcc, sizeof(tm
));
246 ret
= p_gmtime32_s(&tm
, (__time32_t
*)&t
);
247 ok(!ret
, "got %d.\n", ret
);
248 todo_wine_if(tm
.tm_year
== 69 && tm
.tm_hour
== 12)
249 ok(tm
.tm_year
== 70 && tm
.tm_hour
== -12 && tm
.tm_min
== 0 && tm
.tm_sec
== 0, "got %d, %d, %d, %d.\n",
250 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
253 ptm
= p_gmtime64(&t
);
254 ok(!ptm
, "got non-NULL.\n");
255 memset(&tm
, 0xcc, sizeof(tm
));
256 ret
= p_gmtime64_s(&tm
, &t
);
257 ok(ret
== EINVAL
, "got %d.\n", ret
);
258 ok(tm
.tm_year
== -1 && tm
.tm_hour
== -1 && tm
.tm_min
== -1 && tm
.tm_sec
== -1, "got %d, %d, %d, %d.\n",
259 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
260 ptm
= p_gmtime32((__time32_t
*)&t
);
261 ok(!ptm
, "got NULL.\n");
262 memset(&tm
, 0xcc, sizeof(tm
));
263 ret
= p_gmtime32_s(&tm
, (__time32_t
*)&t
);
264 ok(ret
== EINVAL
, "got %d.\n", ret
);
265 ok(tm
.tm_year
== -1 && tm
.tm_hour
== -1 && tm
.tm_min
== -1 && tm
.tm_sec
== -1, "got %d, %d, %d, %d.\n",
266 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
268 t
= _MAX__TIME64_T
+ 46800;
269 memset(&tm
, 0xcc, sizeof(tm
));
270 ptm
= p_gmtime64(&t
);
271 ok(!!ptm
, "got NULL.\n");
272 ret
= p_gmtime64_s(&tm
, &t
);
273 ok(!ret
, "got %d.\n", ret
);
274 ok(tm
.tm_year
== 1101 && tm
.tm_hour
== 20 && tm
.tm_min
== 59 && tm
.tm_sec
== 59, "got %d, %d, %d, %d.\n",
275 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
277 t
= _MAX__TIME64_T
+ 46801;
278 ptm
= p_gmtime64(&t
);
279 ok(!ptm
, "got non-NULL.\n");
280 memset(&tm
, 0xcc, sizeof(tm
));
281 ret
= p_gmtime64_s(&tm
, &t
);
282 ok(ret
== EINVAL
, "got %d.\n", ret
);
283 ok(tm
.tm_year
== -1 && tm
.tm_hour
== -1 && tm
.tm_min
== -1 && tm
.tm_sec
== -1, "got %d, %d, %d, %d.\n",
284 tm
.tm_year
, tm
.tm_hour
, tm
.tm_min
, tm
.tm_sec
);
287 static void test_mktime(void)
289 TIME_ZONE_INFORMATION tzinfo
;
290 DWORD res
= GetTimeZoneInformation(&tzinfo
);
291 struct tm my_tm
, sav_tm
;
292 time_t nulltime
, local_time
;
298 year
= get_test_year( &ref
);
301 ok (res
!= TIME_ZONE_ID_INVALID
, "GetTimeZoneInformation failed\n");
302 WideCharToMultiByte( CP_ACP
, 0, tzinfo
.StandardName
, -1, buffer
, sizeof(buffer
), NULL
, NULL
);
303 trace( "bias %ld std %ld dst %ld zone %s\n",
304 tzinfo
.Bias
, tzinfo
.StandardBias
, tzinfo
.DaylightBias
, buffer
);
305 /* Bias may be positive or negative, to use offset of one day */
306 my_tm
= *localtime(&ref
); /* retrieve current dst flag */
307 secs
= SECSPERDAY
- tzinfo
.Bias
* SECSPERMIN
;
308 secs
-= (my_tm
.tm_isdst
? tzinfo
.DaylightBias
: tzinfo
.StandardBias
) * SECSPERMIN
;
309 my_tm
.tm_mday
= 1 + secs
/SECSPERDAY
;
310 secs
= secs
% SECSPERDAY
;
311 my_tm
.tm_hour
= secs
/ SECSPERHOUR
;
312 secs
= secs
% SECSPERHOUR
;
313 my_tm
.tm_min
= secs
/ SECSPERMIN
;
314 secs
= secs
% SECSPERMIN
;
317 my_tm
.tm_year
= year
;
322 local_time
= mktime(&my_tm
);
323 ok(local_time
== ref
, "mktime returned %lu, expected %lu\n",
324 (DWORD
)local_time
, (DWORD
)ref
);
325 /* now test some unnormalized struct tm's */
329 local_time
= mktime(&my_tm
);
330 ok(local_time
== ref
, "Unnormalized mktime returned %lu, expected %lu\n",
331 (DWORD
)local_time
, (DWORD
)ref
);
332 ok( my_tm
.tm_year
== sav_tm
.tm_year
&& my_tm
.tm_mon
== sav_tm
.tm_mon
&&
333 my_tm
.tm_mday
== sav_tm
.tm_mday
&& my_tm
.tm_hour
== sav_tm
.tm_hour
&&
334 my_tm
.tm_sec
== sav_tm
.tm_sec
,
335 "mktime returned %2d-%02d-%02d %02d:%02d expected %2d-%02d-%02d %02d:%02d\n",
336 my_tm
.tm_year
,my_tm
.tm_mon
,my_tm
.tm_mday
,
337 my_tm
.tm_hour
,my_tm
.tm_sec
,
338 sav_tm
.tm_year
,sav_tm
.tm_mon
,sav_tm
.tm_mday
,
339 sav_tm
.tm_hour
,sav_tm
.tm_sec
);
343 local_time
= mktime(&my_tm
);
344 ok(local_time
== ref
, "Unnormalized mktime returned %lu, expected %lu\n",
345 (DWORD
)local_time
, (DWORD
)ref
);
346 ok( my_tm
.tm_year
== sav_tm
.tm_year
&& my_tm
.tm_mon
== sav_tm
.tm_mon
&&
347 my_tm
.tm_mday
== sav_tm
.tm_mday
&& my_tm
.tm_hour
== sav_tm
.tm_hour
&&
348 my_tm
.tm_sec
== sav_tm
.tm_sec
,
349 "mktime returned %2d-%02d-%02d %02d:%02d expected %2d-%02d-%02d %02d:%02d\n",
350 my_tm
.tm_year
,my_tm
.tm_mon
,my_tm
.tm_mday
,
351 my_tm
.tm_hour
,my_tm
.tm_sec
,
352 sav_tm
.tm_year
,sav_tm
.tm_mon
,sav_tm
.tm_mday
,
353 sav_tm
.tm_hour
,sav_tm
.tm_sec
);
357 local_time
= mktime(&my_tm
);
358 ok(local_time
== ref
, "Unnormalized mktime returned %lu, expected %lu\n",
359 (DWORD
)local_time
, (DWORD
)ref
);
360 ok( my_tm
.tm_year
== sav_tm
.tm_year
&& my_tm
.tm_mon
== sav_tm
.tm_mon
&&
361 my_tm
.tm_mday
== sav_tm
.tm_mday
&& my_tm
.tm_hour
== sav_tm
.tm_hour
&&
362 my_tm
.tm_sec
== sav_tm
.tm_sec
,
363 "mktime returned %2d-%02d-%02d %02d:%02d expected %2d-%02d-%02d %02d:%02d\n",
364 my_tm
.tm_year
,my_tm
.tm_mon
,my_tm
.tm_mday
,
365 my_tm
.tm_hour
,my_tm
.tm_sec
,
366 sav_tm
.tm_year
,sav_tm
.tm_mon
,sav_tm
.tm_mday
,
367 sav_tm
.tm_hour
,sav_tm
.tm_sec
);
371 local_time
= mktime(&my_tm
);
372 ok(local_time
== ref
, "Unnormalized mktime returned %lu, expected %lu\n",
373 (DWORD
)local_time
, (DWORD
)ref
);
374 ok( my_tm
.tm_year
== sav_tm
.tm_year
&& my_tm
.tm_mon
== sav_tm
.tm_mon
&&
375 my_tm
.tm_mday
== sav_tm
.tm_mday
&& my_tm
.tm_hour
== sav_tm
.tm_hour
&&
376 my_tm
.tm_sec
== sav_tm
.tm_sec
,
377 "mktime returned %2d-%02d-%02d %02d:%02d expected %2d-%02d-%02d %02d:%02d\n",
378 my_tm
.tm_year
,my_tm
.tm_mon
,my_tm
.tm_mday
,
379 my_tm
.tm_hour
,my_tm
.tm_sec
,
380 sav_tm
.tm_year
,sav_tm
.tm_mon
,sav_tm
.tm_mday
,
381 sav_tm
.tm_hour
,sav_tm
.tm_sec
);
382 /* now a bad time example */
385 local_time
= mktime(&my_tm
);
386 ok((local_time
== -1), "(bad time) mktime returned %d, expected -1\n", (int)local_time
);
389 /* TEST that we are independent from the TZ variable */
390 /*Argh, msvcrt doesn't have setenv() */
391 _snprintf(TZ_env
,255,"TZ=%s",(getenv("TZ")?getenv("TZ"):""));
393 nulltime
= mktime(&my_tm
);
394 ok(nulltime
== ref
,"mktime returned 0x%08lx\n",(DWORD
)nulltime
);
398 static void test_localtime(void)
400 TIME_ZONE_INFORMATION tzinfo
;
401 DWORD res
= GetTimeZoneInformation(&tzinfo
);
406 int year
= get_test_year( &ref
);
407 int is_leap
= !(year
% 4) && ((year
% 100) || !((year
+ 300) % 400));
409 gmt
= ref
+ SECSPERDAY
+ tzinfo
.Bias
* SECSPERMIN
;
410 ok (res
!= TIME_ZONE_ID_INVALID
, "GetTimeZoneInformation failed\n");
411 lt
= localtime(&gmt
);
412 gmt
+= (lt
->tm_isdst
? tzinfo
.DaylightBias
: tzinfo
.StandardBias
) * SECSPERMIN
;
413 lt
= localtime(&gmt
);
414 ok(((lt
->tm_year
== year
) && (lt
->tm_mon
== 0) && (lt
->tm_yday
== 1) &&
415 (lt
->tm_mday
== 2) && (lt
->tm_hour
== 0) &&
416 (lt
->tm_min
== 0) && (lt
->tm_sec
== 0)),
417 "Wrong date:Year %d mon %d yday %d mday %d wday %d hour %d min %d sec %d dst %d\n",
418 lt
->tm_year
, lt
->tm_mon
, lt
->tm_yday
, lt
->tm_mday
, lt
->tm_wday
, lt
->tm_hour
,
419 lt
->tm_min
, lt
->tm_sec
, lt
->tm_isdst
);
421 _snprintf(TZ_env
,255,"TZ=%s",(getenv("TZ")?getenv("TZ"):""));
423 lt
= localtime(&gmt
);
424 ok(((lt
->tm_year
== year
) && (lt
->tm_mon
== 0) && (lt
->tm_yday
== 1) &&
425 (lt
->tm_mday
== 2) && (lt
->tm_hour
== 0) &&
426 (lt
->tm_min
== 0) && (lt
->tm_sec
== 0)),
427 "Wrong date:Year %d mon %d yday %d mday %d wday %d hour %d min %d sec %d dst %d\n",
428 lt
->tm_year
, lt
->tm_mon
, lt
->tm_yday
, lt
->tm_mday
, lt
->tm_wday
, lt
->tm_hour
,
429 lt
->tm_min
, lt
->tm_sec
, lt
->tm_isdst
);
433 gmt
= ref
+ 202 * SECSPERDAY
+ tzinfo
.Bias
* SECSPERMIN
;
434 lt
= localtime(&gmt
);
435 gmt
+= (lt
->tm_isdst
? tzinfo
.DaylightBias
: tzinfo
.StandardBias
) * SECSPERMIN
;
436 lt
= localtime(&gmt
);
437 ok(((lt
->tm_year
== year
) && (lt
->tm_mon
== 6) && (lt
->tm_yday
== 202) &&
438 (lt
->tm_mday
== 22 - is_leap
) && (lt
->tm_hour
== 0) &&
439 (lt
->tm_min
== 0) && (lt
->tm_sec
== 0)),
440 "Wrong date:Year %d mon %d yday %d mday %d wday %d hour %d min %d sec %d dst %d\n",
441 lt
->tm_year
, lt
->tm_mon
, lt
->tm_yday
, lt
->tm_mday
, lt
->tm_wday
, lt
->tm_hour
,
442 lt
->tm_min
, lt
->tm_sec
, lt
->tm_isdst
);
445 static void test_strdate(void)
447 char date
[16], * result
;
448 int month
, day
, year
, count
, len
;
451 result
= _strdate(date
);
452 ok(result
== date
, "Wrong return value\n");
454 ok(len
== 8, "Wrong length: returned %d, should be 8\n", len
);
455 count
= sscanf(date
, "%02d/%02d/%02d", &month
, &day
, &year
);
456 ok(count
== 3, "Wrong format: count = %d, should be 3\n", count
);
459 win_skip("Skipping _strdate_s tests\n");
464 err
= p_strdate_s(NULL
, 1);
465 ok(err
== EINVAL
, "err = %d\n", err
);
466 ok(errno
== EINVAL
, "errno = %d\n", errno
);
470 err
= p_strdate_s(date
, 8);
471 ok(err
== ERANGE
, "err = %d\n", err
);
472 ok(errno
== ERANGE
, "errno = %d\n", errno
);
473 ok(date
[0] == '\0', "date[0] != '\\0'\n");
474 ok(date
[1] == 'x', "date[1] != 'x'\n");
476 err
= p_strdate_s(date
, 9);
477 ok(err
== 0, "err = %x\n", err
);
480 static void test_strtime(void)
482 char time
[16], * result
;
483 int hour
, minute
, second
, count
, len
;
486 result
= _strtime(time
);
487 ok(result
== time
, "Wrong return value\n");
489 ok(len
== 8, "Wrong length: returned %d, should be 8\n", len
);
490 count
= sscanf(time
, "%02d:%02d:%02d", &hour
, &minute
, &second
);
491 ok(count
== 3, "Wrong format: count = %d, should be 3\n", count
);
494 win_skip("Skipping _strtime_s tests\n");
499 err
= p_strtime_s(NULL
, 0);
500 ok(err
== EINVAL
, "err = %d\n", err
);
501 ok(errno
== EINVAL
, "errno = %d\n", errno
);
503 err
= p_strtime_s(NULL
, 1);
504 ok(err
== EINVAL
, "err = %d\n", err
);
505 ok(errno
== EINVAL
, "errno = %d\n", errno
);
508 err
= p_strtime_s(time
, 8);
509 ok(err
== ERANGE
, "err = %d\n", err
);
510 ok(errno
== ERANGE
, "errno = %d\n", errno
);
511 ok(time
[0] == '\0', "time[0] != '\\0'\n");
513 err
= p_strtime_s(time
, 9);
514 ok(err
== 0, "err = %x\n", err
);
517 static void test_wstrdate(void)
519 wchar_t date
[16], * result
;
520 int month
, day
, year
, count
, len
;
522 result
= _wstrdate(date
);
523 ok(result
== date
, "Wrong return value\n");
525 ok(len
== 8, "Wrong length: returned %d, should be 8\n", len
);
526 count
= swscanf(date
, L
"%02d/%02d/%02d", &month
, &day
, &year
);
527 ok(count
== 3, "Wrong format: count = %d, should be 3\n", count
);
530 static void test_wstrtime(void)
532 wchar_t time
[16], * result
;
533 int hour
, minute
, second
, count
, len
;
535 result
= _wstrtime(time
);
536 ok(result
== time
, "Wrong return value\n");
538 ok(len
== 8, "Wrong length: returned %d, should be 8\n", len
);
539 count
= swscanf(time
, L
"%02d:%02d:%02d", &hour
, &minute
, &second
);
540 ok(count
== 3, "Wrong format: count = %d, should be 3\n", count
);
543 static void test_localtime32_s(void)
549 if (!p_localtime32_s
)
551 win_skip("Skipping _localtime32_s tests\n");
556 err
= p_localtime32_s(NULL
, NULL
);
557 ok(err
== EINVAL
, "Expected _localtime32_s to return EINVAL, got %d\n", err
);
558 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
562 err
= p_localtime32_s(NULL
, &time
);
563 ok(err
== EINVAL
, "Expected _localtime32_s to return EINVAL, got %d\n", err
);
564 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
566 memset(&tm
, 0, sizeof(tm
));
568 err
= p_localtime32_s(&tm
, NULL
);
569 ok(err
== EINVAL
, "Expected _localtime32_s to return EINVAL, got %d\n", err
);
570 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
571 ok(tm
.tm_sec
== -1 && tm
.tm_min
== -1 && tm
.tm_hour
== -1 &&
572 tm
.tm_mday
== -1 && tm
.tm_mon
== -1 && tm
.tm_year
== -1 &&
573 tm
.tm_wday
== -1 && tm
.tm_yday
== -1 && tm
.tm_isdst
== -1,
574 "Expected tm structure members to be initialized to -1, got "
575 "(%d, %d, %d, %d, %d, %d, %d, %d, %d)\n", tm
.tm_sec
, tm
.tm_min
,
576 tm
.tm_hour
, tm
.tm_mday
, tm
.tm_mon
, tm
.tm_year
, tm
.tm_wday
, tm
.tm_yday
,
579 memset(&tm
, 0, sizeof(tm
));
582 err
= p_localtime32_s(&tm
, &time
);
583 ok(err
== EINVAL
, "Expected _localtime32_s to return EINVAL, got %d\n", err
);
584 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
585 ok(tm
.tm_sec
== -1 && tm
.tm_min
== -1 && tm
.tm_hour
== -1 &&
586 tm
.tm_mday
== -1 && tm
.tm_mon
== -1 && tm
.tm_year
== -1 &&
587 tm
.tm_wday
== -1 && tm
.tm_yday
== -1 && tm
.tm_isdst
== -1,
588 "Expected tm structure members to be initialized to -1, got "
589 "(%d, %d, %d, %d, %d, %d, %d, %d, %d)\n", tm
.tm_sec
, tm
.tm_min
,
590 tm
.tm_hour
, tm
.tm_mday
, tm
.tm_mon
, tm
.tm_year
, tm
.tm_wday
, tm
.tm_yday
,
594 static void test_localtime64_s(void)
600 if (!p_localtime64_s
)
602 win_skip("Skipping _localtime64_s tests\n");
607 err
= p_localtime64_s(NULL
, NULL
);
608 ok(err
== EINVAL
, "Expected _localtime64_s to return EINVAL, got %d\n", err
);
609 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
613 err
= p_localtime64_s(NULL
, &time
);
614 ok(err
== EINVAL
, "Expected _localtime64_s to return EINVAL, got %d\n", err
);
615 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
617 memset(&tm
, 0, sizeof(tm
));
619 err
= p_localtime64_s(&tm
, NULL
);
620 ok(err
== EINVAL
, "Expected _localtime64_s to return EINVAL, got %d\n", err
);
621 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
622 ok(tm
.tm_sec
== -1 && tm
.tm_min
== -1 && tm
.tm_hour
== -1 &&
623 tm
.tm_mday
== -1 && tm
.tm_mon
== -1 && tm
.tm_year
== -1 &&
624 tm
.tm_wday
== -1 && tm
.tm_yday
== -1 && tm
.tm_isdst
== -1,
625 "Expected tm structure members to be initialized to -1, got "
626 "(%d, %d, %d, %d, %d, %d, %d, %d, %d)\n", tm
.tm_sec
, tm
.tm_min
,
627 tm
.tm_hour
, tm
.tm_mday
, tm
.tm_mon
, tm
.tm_year
, tm
.tm_wday
, tm
.tm_yday
,
630 memset(&tm
, 0, sizeof(tm
));
633 err
= p_localtime64_s(&tm
, &time
);
634 ok(err
== EINVAL
, "Expected _localtime64_s to return EINVAL, got %d\n", err
);
635 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
636 ok(tm
.tm_sec
== -1 && tm
.tm_min
== -1 && tm
.tm_hour
== -1 &&
637 tm
.tm_mday
== -1 && tm
.tm_mon
== -1 && tm
.tm_year
== -1 &&
638 tm
.tm_wday
== -1 && tm
.tm_yday
== -1 && tm
.tm_isdst
== -1,
639 "Expected tm structure members to be initialized to -1, got "
640 "(%d, %d, %d, %d, %d, %d, %d, %d, %d)\n", tm
.tm_sec
, tm
.tm_min
,
641 tm
.tm_hour
, tm
.tm_mday
, tm
.tm_mon
, tm
.tm_year
, tm
.tm_wday
, tm
.tm_yday
,
644 memset(&tm
, 0, sizeof(tm
));
645 time
= _MAX__TIME64_T
+ 1;
647 err
= p_localtime64_s(&tm
, &time
);
648 ok(err
== EINVAL
, "Expected _localtime64_s to return EINVAL, got %d\n", err
);
649 ok(errno
== EINVAL
, "Expected errno to be EINVAL, got %d\n", errno
);
650 ok(tm
.tm_sec
== -1 && tm
.tm_min
== -1 && tm
.tm_hour
== -1 &&
651 tm
.tm_mday
== -1 && tm
.tm_mon
== -1 && tm
.tm_year
== -1 &&
652 tm
.tm_wday
== -1 && tm
.tm_yday
== -1 && tm
.tm_isdst
== -1,
653 "Expected tm structure members to be initialized to -1, got "
654 "(%d, %d, %d, %d, %d, %d, %d, %d, %d)\n", tm
.tm_sec
, tm
.tm_min
,
655 tm
.tm_hour
, tm
.tm_mday
, tm
.tm_mon
, tm
.tm_year
, tm
.tm_wday
, tm
.tm_yday
,
659 static void test_daylight(void)
665 win_skip("__daylight() not available\n");
669 /* Examine the returned pointer from __p__environ(), if available. */
670 if (sizeof(void*) != sizeof(int))
671 ok( !p___p__daylight
, "___p__daylight() should be 32-bit only\n");
674 ret1
= p__daylight();
675 ret2
= p___p__daylight();
676 ok(ret1
&& ret1
== ret2
, "got %p\n", ret1
);
680 static void test_strftime(void)
703 {"e%#%e", "e%e", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
704 {"%c", "01/01/70 00:00:00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
705 {"%c", "02/30/70 00:00:00", { 0, 0, 0, 30, 1, 70, 4, 0, 0 }},
706 {"%#c", "Thursday, January 01, 1970 00:00:00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
707 {"%#c", "Thursday, February 30, 1970 00:00:00", { 0, 0, 0, 30, 1, 70, 4, 0, 0 }},
708 {"%x", "01/01/70", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
709 {"%x", "02/30/70", { 0, 0, 0, 30, 1, 70, 4, 0, 0 }},
710 {"%#x", "Thursday, January 01, 1970", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
711 {"%#x", "Thursday, February 30, 1970", { 0, 0, 0, 30, 1, 70, 4, 0, 0 }},
712 {"%X", "00:00:00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
713 {"%X", "14:00:00", { 0, 0, 14, 1, 0, 70, 4, 0, 0 }},
714 {"%a", "Thu", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
715 {"%A", "Thursday", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
716 {"%b", "Jan", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
717 {"%B", "January", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
718 {"%d", "01", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
719 {"%#d", "1", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
720 {"%H", "00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
721 {"%I", "12", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
722 {"%j", "001", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
723 {"%m", "01", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
724 {"%#M", "0", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
725 {"%p", "AM", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
726 {"%U", "00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
727 {"%W", "00", { 0, 0, 0, 1, 0, 70, 4, 0, 0 }},
728 {"%U", "01", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
729 {"%W", "00", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
730 {"%U", "53", { 0, 0, 0, 1, 0, 70, 0, 365, 0 }},
731 {"%W", "52", { 0, 0, 0, 1, 0, 70, 0, 365, 0 }},
737 const char *short_date
;
743 { "%c", "x z", "x", "y", "z", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
744 { "%#c", "y z", "x", "y", "z", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
745 { "%X", "m1", 0, 0, "MMM", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
746 { "%X", "1", 0, 0, "h", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
747 { "%X", "01", 0, 0, "hh", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
748 { "%X", "h01", 0, 0, "hhh", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
749 { "%X", "hh01", 0, 0, "hhhh", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
750 { "%X", "1", 0, 0, "H", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
751 { "%X", "01", 0, 0, "HH", { 0, 0, 1, 1, 0, 70, 0, 0, 0 }},
752 { "%X", "H13", 0, 0, "HHH", { 0, 0, 13, 1, 0, 70, 0, 0, 0 }},
753 { "%X", "0", 0, 0, "m", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
754 { "%X", "00", 0, 0, "mm", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
755 { "%X", "0", 0, 0, "s", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
756 { "%X", "00", 0, 0, "ss", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
757 { "%X", "s00", 0, 0, "sss", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
758 { "%X", "t", 0, 0, "t", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
759 { "%X", "tam", 0, 0, "tt", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
760 { "%X", "tam", 0, 0, "ttttttttt", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
761 { "%X", "tam", 0, 0, "a", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
762 { "%X", "tam", 0, 0, "aaaaa", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
763 { "%X", "tam", 0, 0, "A", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
764 { "%X", "tam", 0, 0, "AAAAA", { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
765 { "%x", "1", "d", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
766 { "%x", "01", "dd", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
767 { "%x", "d1", "ddd", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
768 { "%x", "day1", "dddd", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
769 { "%x", "dday1", "ddddd", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
770 { "%x", "1", "M", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
771 { "%x", "01", "MM", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
772 { "%x", "m1", "MMM", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
773 { "%x", "mon1", "MMMM", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
774 { "%x", "Mmon1", "MMMMM", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
775 { "%x", "y", "y", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
776 { "%x", "70", "yy", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
777 { "%x", "y70", "yyy", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
778 { "%x", "1970", "yyyy", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
779 { "%x", "y1970", "yyyyy", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
780 { "%x", "ggggggggggg", "ggggggggggg", 0, 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
781 { "%#x", "1", 0, "d", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
782 { "%#x", "01", 0, "dd", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
783 { "%#x", "d1", 0, "ddd", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
784 { "%#x", "day1", 0, "dddd", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
785 { "%#x", "dday1", 0, "ddddd", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
786 { "%#x", "1", 0, "M", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
787 { "%#x", "01", 0, "MM", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
788 { "%#x", "m1", 0, "MMM", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
789 { "%#x", "mon1", 0, "MMMM", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
790 { "%#x", "Mmon1", 0, "MMMMM", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
791 { "%#x", "y", 0, "y", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
792 { "%#x", "70", 0, "yy", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
793 { "%#x", "y70", 0, "yyy", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
794 { "%#x", "1970", 0, "yyyy", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
795 { "%#x", "y1970", 0, "yyyyy", 0, { 0, 0, 0, 1, 0, 70, 0, 0, 0 }},
798 __lc_time_data time_data
= {
799 { "d1", "d2", "d3", "d4", "d5", "d6", "d7" },
800 { "day1", "day2", "day3", "day4", "day5", "day6", "day7" },
801 { "m1", "m2", "m3", "m4", "m5", "m6", "m7", "m8", "m9", "m10", "m11", "m12" },
802 { "mon1", "mon2", "mon3", "mon4", "mon5", "mon6", "mon7", "mon8", "mon9", "mon10", "mon11", "mon12" },
807 char buf
[256], bufA
[256];
812 if (!p_strftime
|| !p_wcsftime
|| !p_gmtime
)
814 win_skip("strftime, wcsftime or gmtime is not available\n");
818 setlocale(LC_TIME
, "C");
821 gmt_tm
= p_gmtime(&gmt
);
822 ok(gmt_tm
!= NULL
, "gmtime failed\n");
824 for (i
=0; i
<ARRAY_SIZE(tests_einval
); i
++)
827 retA
= p_strftime(bufA
, 256, tests_einval
[i
].format
, gmt_tm
);
828 ok(retA
== 0, "%d) ret = %ld\n", i
, retA
);
829 ok(errno
==EINVAL
|| broken(errno
==0xdeadbeef), "%d) errno = %d\n", i
, errno
);
833 retA
= p_strftime(NULL
, 0, "copy", gmt_tm
);
834 ok(retA
== 0, "expected 0, got %ld\n", retA
);
835 ok(errno
==EINVAL
|| broken(errno
==0xdeadbeef), "errno = %d\n", errno
);
837 retA
= p_strftime(bufA
, 256, "copy", NULL
);
838 ok(retA
== 4, "expected 4, got %ld\n", retA
);
839 ok(!strcmp(bufA
, "copy"), "got %s\n", bufA
);
841 retA
= p_strftime(bufA
, 256, "copy it", gmt_tm
);
842 ok(retA
== 7, "expected 7, got %ld\n", retA
);
843 ok(!strcmp(bufA
, "copy it"), "got %s\n", bufA
);
846 retA
= p_strftime(bufA
, 2, "copy", gmt_tm
);
847 ok(retA
== 0, "expected 0, got %ld\n", retA
);
848 ok(!strcmp(bufA
, "") || broken(!strcmp(bufA
, "copy it")), "got %s\n", bufA
);
849 ok(errno
==ERANGE
|| errno
==0xdeadbeef, "errno = %d\n", errno
);
852 retA
= p_strftime(bufA
, 256, "a%e", gmt_tm
);
853 ok(retA
==0 || broken(retA
==1), "expected 0, got %ld\n", retA
);
854 ok(!strcmp(bufA
, "") || broken(!strcmp(bufA
, "a")), "got %s\n", bufA
);
855 ok(errno
==EINVAL
|| broken(errno
==0xdeadbeef), "errno = %d\n", errno
);
857 if(0) { /* crashes on Win2k */
859 retA
= p_strftime(bufA
, 256, "%c", NULL
);
860 ok(retA
== 0, "expected 0, got %ld\n", retA
);
861 ok(!strcmp(bufA
, ""), "got %s\n", bufA
);
862 ok(errno
== EINVAL
, "errno = %d\n", errno
);
865 for (i
=0; i
<ARRAY_SIZE(tests
); i
++)
867 retA
= p_strftime(bufA
, 256, tests
[i
].format
, &tests
[i
].tm
);
868 todo_wine_if(tests
[i
].todo
) {
869 ok(retA
== strlen(tests
[i
].ret
), "%d) ret = %ld\n", i
, retA
);
870 ok(!strcmp(bufA
, tests
[i
].ret
), "%d) buf = \"%s\", expected \"%s\"\n",
871 i
, bufA
, tests
[i
].ret
);
875 retA
= p_strftime(bufA
, 256, "%c", gmt_tm
);
876 retW
= p_wcsftime(bufW
, 256, L
"%c", gmt_tm
);
877 ok(retW
== 17, "expected 17, got %ld\n", retW
);
878 ok(retA
== retW
, "expected %ld, got %ld\n", retA
, retW
);
880 retA
= WideCharToMultiByte(CP_ACP
, 0, bufW
, retW
, buf
, 256, NULL
, NULL
);
882 ok(strcmp(bufA
, buf
) == 0, "expected %s, got %s\n", bufA
, buf
);
884 if(!setlocale(LC_ALL
, "Japanese_Japan.932")) {
885 win_skip("Japanese_Japan.932 locale not available\n");
889 /* test with multibyte character */
890 retA
= p_strftime(bufA
, 256, "\x82%c", gmt_tm
);
891 ok(retA
== 3, "expected 3, got %ld\n", retA
);
892 ok(!strcmp(bufA
, "\x82%c"), "got %s\n", bufA
);
894 setlocale(LC_ALL
, "C");
896 win_skip("_Strftime is not available\n");
900 /* TODO: find meaning of unk */
902 for (i
=0; i
<ARRAY_SIZE(tests_td
); i
++)
904 time_data
.short_date
= tests_td
[i
].short_date
;
905 time_data
.date
= tests_td
[i
].date
;
906 time_data
.time
= tests_td
[i
].time
;
907 retA
= p__Strftime(buf
, sizeof(buf
), tests_td
[i
].format
, &tests_td
[i
].tm
, &time_data
);
908 ok(retA
== strlen(buf
), "%d) ret = %ld\n", i
, retA
);
909 todo_wine_if(tests_td
[i
].todo
) {
910 ok(!strcmp(buf
, tests_td
[i
].ret
), "%d) buf = \"%s\", expected \"%s\"\n",
911 i
, buf
, tests_td
[i
].ret
);
916 static void test_asctime(void)
922 if(!p_asctime
|| !p_gmtime
)
924 win_skip("asctime or gmtime is not available\n");
929 gmt_tm
= p_gmtime(&gmt
);
930 ret
= p_asctime(gmt_tm
);
931 ok(!strcmp(ret
, "Thu Jan 01 00:00:00 1970\n"), "asctime returned %s\n", ret
);
934 gmt_tm
= p_gmtime(&gmt
);
935 ret
= p_asctime(gmt_tm
);
936 ok(!strcmp(ret
, "Mon Nov 26 02:58:41 1979\n"), "asctime returned %s\n", ret
);
938 /* Week day is only checked if it's in 0..6 range */
940 ret
= p_asctime(gmt_tm
);
941 ok(!strcmp(ret
, "Wed Nov 26 02:58:41 1979\n"), "asctime returned %s\n", ret
);
945 ret
= p_asctime(gmt_tm
);
946 ok(!ret
|| broken(!ret
[0]), "asctime returned %s\n", ret
);
947 ok(errno
==EINVAL
|| broken(errno
==0xdeadbeef), "errno = %d\n", errno
);
949 /* Year day is ignored */
951 gmt_tm
->tm_yday
= 1300;
952 ret
= p_asctime(gmt_tm
);
953 ok(!strcmp(ret
, "Wed Nov 26 02:58:41 1979\n"), "asctime returned %s\n", ret
);
955 /* Dates that can't be displayed using 26 characters are broken */
956 gmt_tm
->tm_mday
= 28;
957 gmt_tm
->tm_year
= 8100;
958 ret
= p_asctime(gmt_tm
);
959 ok(!strcmp(ret
, "Wed Nov 28 02:58:41 :000\n"), "asctime returned %s\n", ret
);
961 gmt_tm
->tm_year
= 264100;
962 ret
= p_asctime(gmt_tm
);
963 ok(!strcmp(ret
, "Wed Nov 28 02:58:41 :000\n"), "asctime returned %s\n", ret
);
965 /* asctime works from year 1900 */
967 gmt_tm
->tm_year
= -1;
968 ret
= p_asctime(gmt_tm
);
969 ok(!ret
|| broken(!strcmp(ret
, "Wed Nov 28 02:58:41 190/\n")), "asctime returned %s\n", ret
);
970 ok(errno
==EINVAL
|| broken(errno
== 0xdeadbeef), "errno = %d\n", errno
);
974 gmt_tm
->tm_mday
= 30;
975 gmt_tm
->tm_year
= 79;
976 ret
= p_asctime(gmt_tm
);
977 ok(!ret
|| broken(!strcmp(ret
, "Wed Feb 30 02:58:41 1979\n")), "asctime returned %s\n", ret
);
978 ok(errno
==EINVAL
|| broken(errno
==0xdeadbeef), "errno = %d\n", errno
);
981 static void test__tzset(void)
986 if (sizeof(void*) != sizeof(int))
988 ok(!p___p__daylight
, "___p__daylight() should be 32-bit only\n");
989 ok(!p___p__timezone
, "___p__timezone() should be 32-bit only\n");
990 ok(!p___p__dstbias
, "___p__dstbias() should be 32-bit only\n");
996 ok(ret
== -3600, "*__dstbias() = %d\n", ret
);
997 ret
= *p___p__dstbias();
998 ok(ret
== -3600, "*__p__dstbias() = %d\n", ret
);
1001 win_skip("__dstbias() is not available.\n");
1003 _snprintf(TZ_env
,255,"TZ=%s",(getenv("TZ")?getenv("TZ"):""));
1005 ret
= *p___p__daylight();
1006 ok(ret
== 1, "*__p__daylight() = %d\n", ret
);
1007 ret
= *p___p__timezone();
1008 ok(ret
== 28800, "*__p__timezone() = %d\n", ret
);
1009 ret
= *p___p__dstbias();
1010 ok(ret
== -3600, "*__p__dstbias() = %d\n", ret
);
1012 _putenv("TZ=xxx+1yyy");
1014 ret
= *p___p__daylight();
1015 ok(ret
== 121, "*__p__daylight() = %d\n", ret
);
1016 ret
= *p___p__timezone();
1017 ok(ret
== 3600, "*__p__timezone() = %d\n", ret
);
1018 ret
= *p___p__dstbias();
1019 ok(ret
== -3600, "*__p__dstbias() = %d\n", ret
);
1021 *p___p__dstbias() = 0;
1022 _putenv("TZ=xxx+1:3:5zzz");
1024 ret
= *p___p__daylight();
1025 ok(ret
== 122, "*__p__daylight() = %d\n", ret
);
1026 ret
= *p___p__timezone();
1027 ok(ret
== 3785, "*__p__timezone() = %d\n", ret
);
1028 ret
= *p___p__dstbias();
1029 ok(ret
== 0, "*__p__dstbias() = %d\n", ret
);
1049 test_localtime32_s();
1050 test_localtime64_s();