1 /*
2  * Copyright (C) 2013 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <time.h>
18 
19 #include <errno.h>
20 #include <gtest/gtest.h>
21 #include <pthread.h>
22 #include <signal.h>
23 #include <sys/syscall.h>
24 #include <sys/types.h>
25 #include <sys/wait.h>
26 #include <unistd.h>
27 
28 #include <atomic>
29 #include <chrono>
30 
31 #include "SignalUtils.h"
32 #include "utils.h"
33 
34 using namespace std::chrono_literals;
35 
TEST(time,time)36 TEST(time, time) {
37   // Acquire time
38   time_t p1, t1 = time(&p1);
39   // valid?
40   ASSERT_NE(static_cast<time_t>(0), t1);
41   ASSERT_NE(static_cast<time_t>(-1), t1);
42   ASSERT_EQ(p1, t1);
43 
44   // Acquire time one+ second later
45   usleep(1010000);
46   time_t p2, t2 = time(&p2);
47   // valid?
48   ASSERT_NE(static_cast<time_t>(0), t2);
49   ASSERT_NE(static_cast<time_t>(-1), t2);
50   ASSERT_EQ(p2, t2);
51 
52   // Expect time progression
53   ASSERT_LT(p1, p2);
54   ASSERT_LE(t2 - t1, static_cast<time_t>(2));
55 
56   // Expect nullptr call to produce same results
57   ASSERT_LE(t2, time(nullptr));
58   ASSERT_LE(time(nullptr) - t2, static_cast<time_t>(1));
59 }
60 
TEST(time,gmtime)61 TEST(time, gmtime) {
62   time_t t = 0;
63   tm* broken_down = gmtime(&t);
64   ASSERT_TRUE(broken_down != nullptr);
65   ASSERT_EQ(0, broken_down->tm_sec);
66   ASSERT_EQ(0, broken_down->tm_min);
67   ASSERT_EQ(0, broken_down->tm_hour);
68   ASSERT_EQ(1, broken_down->tm_mday);
69   ASSERT_EQ(0, broken_down->tm_mon);
70   ASSERT_EQ(1970, broken_down->tm_year + 1900);
71 }
72 
TEST(time,gmtime_r)73 TEST(time, gmtime_r) {
74   struct tm tm = {};
75   time_t t = 0;
76   struct tm* broken_down = gmtime_r(&t, &tm);
77   ASSERT_EQ(broken_down, &tm);
78   ASSERT_EQ(0, broken_down->tm_sec);
79   ASSERT_EQ(0, broken_down->tm_min);
80   ASSERT_EQ(0, broken_down->tm_hour);
81   ASSERT_EQ(1, broken_down->tm_mday);
82   ASSERT_EQ(0, broken_down->tm_mon);
83   ASSERT_EQ(1970, broken_down->tm_year + 1900);
84 }
85 
gmtime_no_stack_overflow_14313703_fn(void *)86 static void* gmtime_no_stack_overflow_14313703_fn(void*) {
87   const char* original_tz = getenv("TZ");
88   // Ensure we'll actually have to enter tzload by using a time zone that doesn't exist.
89   setenv("TZ", "gmtime_stack_overflow_14313703", 1);
90   tzset();
91   if (original_tz != nullptr) {
92     setenv("TZ", original_tz, 1);
93   }
94   tzset();
95   return nullptr;
96 }
97 
TEST(time,gmtime_no_stack_overflow_14313703)98 TEST(time, gmtime_no_stack_overflow_14313703) {
99   // Is it safe to call tzload on a thread with a small stack?
100   // http://b/14313703
101   // https://code.google.com/p/android/issues/detail?id=61130
102   pthread_attr_t a;
103   ASSERT_EQ(0, pthread_attr_init(&a));
104   ASSERT_EQ(0, pthread_attr_setstacksize(&a, PTHREAD_STACK_MIN));
105 
106   pthread_t t;
107   ASSERT_EQ(0, pthread_create(&t, &a, gmtime_no_stack_overflow_14313703_fn, nullptr));
108   ASSERT_EQ(0, pthread_join(t, nullptr));
109 }
110 
TEST(time,mktime_empty_TZ)111 TEST(time, mktime_empty_TZ) {
112   // tzcode used to have a bug where it didn't reinitialize some internal state.
113 
114   // Choose a time where DST is set.
115   struct tm t;
116   memset(&t, 0, sizeof(tm));
117   t.tm_year = 1980 - 1900;
118   t.tm_mon = 6;
119   t.tm_mday = 2;
120 
121   setenv("TZ", "America/Los_Angeles", 1);
122   tzset();
123   ASSERT_EQ(static_cast<time_t>(331372800U), mktime(&t));
124 
125   memset(&t, 0, sizeof(tm));
126   t.tm_year = 1980 - 1900;
127   t.tm_mon = 6;
128   t.tm_mday = 2;
129 
130   setenv("TZ", "", 1); // Implies UTC.
131   tzset();
132   ASSERT_EQ(static_cast<time_t>(331344000U), mktime(&t));
133 }
134 
TEST(time,mktime_10310929)135 TEST(time, mktime_10310929) {
136   struct tm t;
137   memset(&t, 0, sizeof(tm));
138   t.tm_year = 200;
139   t.tm_mon = 2;
140   t.tm_mday = 10;
141 
142 #if !defined(__LP64__)
143   // 32-bit bionic has a signed 32-bit time_t.
144   ASSERT_EQ(-1, mktime(&t));
145   ASSERT_EQ(EOVERFLOW, errno);
146 #else
147   // Everyone else should be using a signed 64-bit time_t.
148   ASSERT_GE(sizeof(time_t) * 8, 64U);
149 
150   setenv("TZ", "America/Los_Angeles", 1);
151   tzset();
152   errno = 0;
153   ASSERT_EQ(static_cast<time_t>(4108348800U), mktime(&t));
154   ASSERT_EQ(0, errno);
155 
156   setenv("TZ", "UTC", 1);
157   tzset();
158   errno = 0;
159   ASSERT_EQ(static_cast<time_t>(4108320000U), mktime(&t));
160   ASSERT_EQ(0, errno);
161 #endif
162 }
163 
TEST(time,mktime_EOVERFLOW)164 TEST(time, mktime_EOVERFLOW) {
165   struct tm t;
166   memset(&t, 0, sizeof(tm));
167 
168   // LP32 year range is 1901-2038, so this year is guaranteed not to overflow.
169   t.tm_year = 2016 - 1900;
170 
171   t.tm_mon = 2;
172   t.tm_mday = 10;
173 
174   errno = 0;
175   ASSERT_NE(static_cast<time_t>(-1), mktime(&t));
176   ASSERT_EQ(0, errno);
177 
178   // This will overflow for LP32 or LP64.
179   t.tm_year = INT_MAX;
180 
181   errno = 0;
182   ASSERT_EQ(static_cast<time_t>(-1), mktime(&t));
183   ASSERT_EQ(EOVERFLOW, errno);
184 }
185 
TEST(time,strftime)186 TEST(time, strftime) {
187   setenv("TZ", "UTC", 1);
188 
189   struct tm t;
190   memset(&t, 0, sizeof(tm));
191   t.tm_year = 200;
192   t.tm_mon = 2;
193   t.tm_mday = 10;
194 
195   char buf[64];
196 
197   // Seconds since the epoch.
198 #if defined(__BIONIC__) || defined(__LP64__) // Not 32-bit glibc.
199   EXPECT_EQ(10U, strftime(buf, sizeof(buf), "%s", &t));
200   EXPECT_STREQ("4108320000", buf);
201 #endif
202 
203   // Date and time as text.
204   EXPECT_EQ(24U, strftime(buf, sizeof(buf), "%c", &t));
205   EXPECT_STREQ("Sun Mar 10 00:00:00 2100", buf);
206 }
207 
TEST(time,strftime_null_tm_zone)208 TEST(time, strftime_null_tm_zone) {
209   // Netflix on Nexus Player wouldn't start (http://b/25170306).
210   struct tm t;
211   memset(&t, 0, sizeof(tm));
212 
213   char buf[64];
214 
215   setenv("TZ", "America/Los_Angeles", 1);
216   tzset();
217 
218   t.tm_isdst = 0; // "0 if Daylight Savings Time is not in effect".
219   EXPECT_EQ(5U, strftime(buf, sizeof(buf), "<%Z>", &t));
220   EXPECT_STREQ("<PST>", buf);
221 
222 #if defined(__BIONIC__) // glibc 2.19 only copes with tm_isdst being 0 and 1.
223   t.tm_isdst = 2; // "positive if Daylight Savings Time is in effect"
224   EXPECT_EQ(5U, strftime(buf, sizeof(buf), "<%Z>", &t));
225   EXPECT_STREQ("<PDT>", buf);
226 
227   t.tm_isdst = -123; // "and negative if the information is not available".
228   EXPECT_EQ(2U, strftime(buf, sizeof(buf), "<%Z>", &t));
229   EXPECT_STREQ("<>", buf);
230 #endif
231 
232   setenv("TZ", "UTC", 1);
233   tzset();
234 
235   t.tm_isdst = 0;
236   EXPECT_EQ(5U, strftime(buf, sizeof(buf), "<%Z>", &t));
237   EXPECT_STREQ("<UTC>", buf);
238 
239 #if defined(__BIONIC__) // glibc 2.19 thinks UTC DST is "UTC".
240   t.tm_isdst = 1; // UTC has no DST.
241   EXPECT_EQ(2U, strftime(buf, sizeof(buf), "<%Z>", &t));
242   EXPECT_STREQ("<>", buf);
243 #endif
244 }
245 
TEST(time,strftime_l)246 TEST(time, strftime_l) {
247   locale_t cloc = newlocale(LC_ALL, "C.UTF-8", nullptr);
248   locale_t old_locale = uselocale(cloc);
249 
250   setenv("TZ", "UTC", 1);
251 
252   struct tm t;
253   memset(&t, 0, sizeof(tm));
254   t.tm_year = 200;
255   t.tm_mon = 2;
256   t.tm_mday = 10;
257 
258   // Date and time as text.
259   char buf[64];
260   EXPECT_EQ(24U, strftime_l(buf, sizeof(buf), "%c", &t, cloc));
261   EXPECT_STREQ("Sun Mar 10 00:00:00 2100", buf);
262 
263   uselocale(old_locale);
264   freelocale(cloc);
265 }
266 
TEST(time,strptime)267 TEST(time, strptime) {
268   setenv("TZ", "UTC", 1);
269 
270   struct tm t;
271   char buf[64];
272 
273   memset(&t, 0, sizeof(t));
274   strptime("11:14", "%R", &t);
275   strftime(buf, sizeof(buf), "%H:%M", &t);
276   EXPECT_STREQ("11:14", buf);
277 
278   memset(&t, 0, sizeof(t));
279   strptime("09:41:53", "%T", &t);
280   strftime(buf, sizeof(buf), "%H:%M:%S", &t);
281   EXPECT_STREQ("09:41:53", buf);
282 }
283 
TEST(time,strptime_l)284 TEST(time, strptime_l) {
285   setenv("TZ", "UTC", 1);
286 
287   struct tm t;
288   char buf[64];
289 
290   memset(&t, 0, sizeof(t));
291   strptime_l("11:14", "%R", &t, LC_GLOBAL_LOCALE);
292   strftime_l(buf, sizeof(buf), "%H:%M", &t, LC_GLOBAL_LOCALE);
293   EXPECT_STREQ("11:14", buf);
294 
295   memset(&t, 0, sizeof(t));
296   strptime_l("09:41:53", "%T", &t, LC_GLOBAL_LOCALE);
297   strftime_l(buf, sizeof(buf), "%H:%M:%S", &t, LC_GLOBAL_LOCALE);
298   EXPECT_STREQ("09:41:53", buf);
299 }
300 
TEST(time,strptime_F)301 TEST(time, strptime_F) {
302   setenv("TZ", "UTC", 1);
303 
304   struct tm tm = {};
305   ASSERT_EQ('\0', *strptime("2019-03-26", "%F", &tm));
306   EXPECT_EQ(119, tm.tm_year);
307   EXPECT_EQ(2, tm.tm_mon);
308   EXPECT_EQ(26, tm.tm_mday);
309 }
310 
TEST(time,strptime_P_p)311 TEST(time, strptime_P_p) {
312   setenv("TZ", "UTC", 1);
313 
314   // For parsing, %P and %p are the same: case doesn't matter.
315 
316   struct tm tm = {.tm_hour = 12};
317   ASSERT_EQ('\0', *strptime("AM", "%p", &tm));
318   EXPECT_EQ(0, tm.tm_hour);
319 
320   tm = {.tm_hour = 12};
321   ASSERT_EQ('\0', *strptime("am", "%p", &tm));
322   EXPECT_EQ(0, tm.tm_hour);
323 
324   tm = {.tm_hour = 12};
325   ASSERT_EQ('\0', *strptime("AM", "%P", &tm));
326   EXPECT_EQ(0, tm.tm_hour);
327 
328   tm = {.tm_hour = 12};
329   ASSERT_EQ('\0', *strptime("am", "%P", &tm));
330   EXPECT_EQ(0, tm.tm_hour);
331 }
332 
TEST(time,strptime_u)333 TEST(time, strptime_u) {
334   setenv("TZ", "UTC", 1);
335 
336   struct tm tm = {};
337   ASSERT_EQ('\0', *strptime("2", "%u", &tm));
338   EXPECT_EQ(2, tm.tm_wday);
339 }
340 
TEST(time,strptime_v)341 TEST(time, strptime_v) {
342   setenv("TZ", "UTC", 1);
343 
344   struct tm tm = {};
345   ASSERT_EQ('\0', *strptime("26-Mar-1980", "%v", &tm));
346   EXPECT_EQ(80, tm.tm_year);
347   EXPECT_EQ(2, tm.tm_mon);
348   EXPECT_EQ(26, tm.tm_mday);
349 }
350 
TEST(time,strptime_V_G_g)351 TEST(time, strptime_V_G_g) {
352   setenv("TZ", "UTC", 1);
353 
354   // %V (ISO-8601 week number), %G (year of week number, without century), and
355   // %g (year of week number) have no effect when parsed, and are supported
356   // solely so that it's possible for strptime(3) to parse everything that
357   // strftime(3) can output.
358   struct tm tm = {};
359   ASSERT_EQ('\0', *strptime("1 2 3", "%V %G %g", &tm));
360   struct tm zero = {};
361   EXPECT_TRUE(memcmp(&tm, &zero, sizeof(tm)) == 0);
362 }
363 
TEST(time,strptime_Z)364 TEST(time, strptime_Z) {
365 #if defined(__BIONIC__)
366   // glibc doesn't handle %Z at all.
367   // The BSDs only handle hard-coded "GMT" and "UTC", plus whatever two strings
368   // are in the global `tzname` (which correspond to the current $TZ).
369   struct tm tm;
370   setenv("TZ", "Europe/Berlin", 1);
371 
372   // "GMT" always works.
373   tm = {};
374   ASSERT_EQ('\0', *strptime("GMT", "%Z", &tm));
375   EXPECT_STREQ("GMT", tm.tm_zone);
376   EXPECT_EQ(0, tm.tm_isdst);
377   EXPECT_EQ(0, tm.tm_gmtoff);
378 
379   // As does "UTC".
380   tm = {};
381   ASSERT_EQ('\0', *strptime("UTC", "%Z", &tm));
382   EXPECT_STREQ("UTC", tm.tm_zone);
383   EXPECT_EQ(0, tm.tm_isdst);
384   EXPECT_EQ(0, tm.tm_gmtoff);
385 
386   // Europe/Berlin is known as "CET" when there's no DST.
387   tm = {};
388   ASSERT_EQ('\0', *strptime("CET", "%Z", &tm));
389   EXPECT_STREQ("CET", tm.tm_zone);
390   EXPECT_EQ(0, tm.tm_isdst);
391   EXPECT_EQ(3600, tm.tm_gmtoff);
392 
393   // Europe/Berlin is known as "CEST" when there's no DST.
394   tm = {};
395   ASSERT_EQ('\0', *strptime("CEST", "%Z", &tm));
396   EXPECT_STREQ("CEST", tm.tm_zone);
397   EXPECT_EQ(1, tm.tm_isdst);
398   EXPECT_EQ(3600, tm.tm_gmtoff);
399 
400   // And as long as we're in Europe/Berlin, those are the only time zone
401   // abbreviations that are recognized.
402   tm = {};
403   ASSERT_TRUE(strptime("PDT", "%Z", &tm) == nullptr);
404 #endif
405 }
406 
TEST(time,strptime_z)407 TEST(time, strptime_z) {
408   struct tm tm;
409   setenv("TZ", "Europe/Berlin", 1);
410 
411   // "UT" is what RFC822 called UTC.
412   tm = {};
413   ASSERT_EQ('\0', *strptime("UT", "%z", &tm));
414   EXPECT_STREQ("UTC", tm.tm_zone);
415   EXPECT_EQ(0, tm.tm_isdst);
416   EXPECT_EQ(0, tm.tm_gmtoff);
417   // "GMT" is RFC822's other name for UTC.
418   tm = {};
419   ASSERT_EQ('\0', *strptime("GMT", "%z", &tm));
420   EXPECT_STREQ("UTC", tm.tm_zone);
421   EXPECT_EQ(0, tm.tm_isdst);
422   EXPECT_EQ(0, tm.tm_gmtoff);
423 
424   // "Z" ("Zulu") is a synonym for UTC.
425   tm = {};
426   ASSERT_EQ('\0', *strptime("Z", "%z", &tm));
427   EXPECT_STREQ("UTC", tm.tm_zone);
428   EXPECT_EQ(0, tm.tm_isdst);
429   EXPECT_EQ(0, tm.tm_gmtoff);
430 
431   // "PST"/"PDT" and the other common US zone abbreviations are all supported.
432   tm = {};
433   ASSERT_EQ('\0', *strptime("PST", "%z", &tm));
434   EXPECT_STREQ("PST", tm.tm_zone);
435   EXPECT_EQ(0, tm.tm_isdst);
436   EXPECT_EQ(-28800, tm.tm_gmtoff);
437   tm = {};
438   ASSERT_EQ('\0', *strptime("PDT", "%z", &tm));
439   EXPECT_STREQ("PDT", tm.tm_zone);
440   EXPECT_EQ(1, tm.tm_isdst);
441   EXPECT_EQ(-25200, tm.tm_gmtoff);
442 
443   // +-hh
444   tm = {};
445   ASSERT_EQ('\0', *strptime("+01", "%z", &tm));
446   EXPECT_EQ(3600, tm.tm_gmtoff);
447   EXPECT_TRUE(tm.tm_zone == nullptr);
448   EXPECT_EQ(0, tm.tm_isdst);
449   // +-hhmm
450   tm = {};
451   ASSERT_EQ('\0', *strptime("+0130", "%z", &tm));
452   EXPECT_EQ(5400, tm.tm_gmtoff);
453   EXPECT_TRUE(tm.tm_zone == nullptr);
454   EXPECT_EQ(0, tm.tm_isdst);
455   // +-hh:mm
456   tm = {};
457   ASSERT_EQ('\0', *strptime("+01:30", "%z", &tm));
458   EXPECT_EQ(5400, tm.tm_gmtoff);
459   EXPECT_TRUE(tm.tm_zone == nullptr);
460   EXPECT_EQ(0, tm.tm_isdst);
461 }
462 
SetTime(timer_t t,time_t value_s,time_t value_ns,time_t interval_s,time_t interval_ns)463 void SetTime(timer_t t, time_t value_s, time_t value_ns, time_t interval_s, time_t interval_ns) {
464   itimerspec ts;
465   ts.it_value.tv_sec = value_s;
466   ts.it_value.tv_nsec = value_ns;
467   ts.it_interval.tv_sec = interval_s;
468   ts.it_interval.tv_nsec = interval_ns;
469   ASSERT_EQ(0, timer_settime(t, 0, &ts, nullptr));
470 }
471 
NoOpNotifyFunction(sigval_t)472 static void NoOpNotifyFunction(sigval_t) {
473 }
474 
TEST(time,timer_create)475 TEST(time, timer_create) {
476   sigevent_t se;
477   memset(&se, 0, sizeof(se));
478   se.sigev_notify = SIGEV_THREAD;
479   se.sigev_notify_function = NoOpNotifyFunction;
480   timer_t timer_id;
481   ASSERT_EQ(0, timer_create(CLOCK_MONOTONIC, &se, &timer_id));
482 
483   pid_t pid = fork();
484   ASSERT_NE(-1, pid) << strerror(errno);
485 
486   if (pid == 0) {
487     // Timers are not inherited by the child.
488     ASSERT_EQ(-1, timer_delete(timer_id));
489     ASSERT_EQ(EINVAL, errno);
490     _exit(0);
491   }
492 
493   AssertChildExited(pid, 0);
494 
495   ASSERT_EQ(0, timer_delete(timer_id));
496 }
497 
498 static int timer_create_SIGEV_SIGNAL_signal_handler_invocation_count;
timer_create_SIGEV_SIGNAL_signal_handler(int signal_number)499 static void timer_create_SIGEV_SIGNAL_signal_handler(int signal_number) {
500   ++timer_create_SIGEV_SIGNAL_signal_handler_invocation_count;
501   ASSERT_EQ(SIGUSR1, signal_number);
502 }
503 
TEST(time,timer_create_SIGEV_SIGNAL)504 TEST(time, timer_create_SIGEV_SIGNAL) {
505   sigevent_t se;
506   memset(&se, 0, sizeof(se));
507   se.sigev_notify = SIGEV_SIGNAL;
508   se.sigev_signo = SIGUSR1;
509 
510   timer_t timer_id;
511   ASSERT_EQ(0, timer_create(CLOCK_MONOTONIC, &se, &timer_id));
512 
513   timer_create_SIGEV_SIGNAL_signal_handler_invocation_count = 0;
514   ScopedSignalHandler ssh(SIGUSR1, timer_create_SIGEV_SIGNAL_signal_handler);
515 
516   ASSERT_EQ(0, timer_create_SIGEV_SIGNAL_signal_handler_invocation_count);
517 
518   itimerspec ts;
519   ts.it_value.tv_sec =  0;
520   ts.it_value.tv_nsec = 1;
521   ts.it_interval.tv_sec = 0;
522   ts.it_interval.tv_nsec = 0;
523   ASSERT_EQ(0, timer_settime(timer_id, 0, &ts, nullptr));
524 
525   usleep(500000);
526   ASSERT_EQ(1, timer_create_SIGEV_SIGNAL_signal_handler_invocation_count);
527 }
528 
529 struct Counter {
530  private:
531   std::atomic<int> value;
532   timer_t timer_id;
533   sigevent_t se;
534   bool timer_valid;
535 
CreateCounter536   void Create() {
537     ASSERT_FALSE(timer_valid);
538     ASSERT_EQ(0, timer_create(CLOCK_REALTIME, &se, &timer_id));
539     timer_valid = true;
540   }
541 
542  public:
CounterCounter543   explicit Counter(void (*fn)(sigval_t)) : value(0), timer_valid(false) {
544     memset(&se, 0, sizeof(se));
545     se.sigev_notify = SIGEV_THREAD;
546     se.sigev_notify_function = fn;
547     se.sigev_value.sival_ptr = this;
548     Create();
549   }
DeleteTimerCounter550   void DeleteTimer() {
551     ASSERT_TRUE(timer_valid);
552     ASSERT_EQ(0, timer_delete(timer_id));
553     timer_valid = false;
554   }
555 
~CounterCounter556   ~Counter() {
557     if (timer_valid) {
558       DeleteTimer();
559     }
560   }
561 
ValueCounter562   int Value() const {
563     return value;
564   }
565 
SetTimeCounter566   void SetTime(time_t value_s, time_t value_ns, time_t interval_s, time_t interval_ns) {
567     ::SetTime(timer_id, value_s, value_ns, interval_s, interval_ns);
568   }
569 
ValueUpdatedCounter570   bool ValueUpdated() {
571     int current_value = value;
572     time_t start = time(nullptr);
573     while (current_value == value && (time(nullptr) - start) < 5) {
574     }
575     return current_value != value;
576   }
577 
CountNotifyFunctionCounter578   static void CountNotifyFunction(sigval_t value) {
579     Counter* cd = reinterpret_cast<Counter*>(value.sival_ptr);
580     ++cd->value;
581   }
582 
CountAndDisarmNotifyFunctionCounter583   static void CountAndDisarmNotifyFunction(sigval_t value) {
584     Counter* cd = reinterpret_cast<Counter*>(value.sival_ptr);
585     ++cd->value;
586 
587     // Setting the initial expiration time to 0 disarms the timer.
588     cd->SetTime(0, 0, 1, 0);
589   }
590 };
591 
TEST(time,timer_settime_0)592 TEST(time, timer_settime_0) {
593   Counter counter(Counter::CountAndDisarmNotifyFunction);
594   ASSERT_EQ(0, counter.Value());
595 
596   counter.SetTime(0, 500000000, 1, 0);
597   sleep(1);
598 
599   // The count should just be 1 because we disarmed the timer the first time it fired.
600   ASSERT_EQ(1, counter.Value());
601 }
602 
TEST(time,timer_settime_repeats)603 TEST(time, timer_settime_repeats) {
604   Counter counter(Counter::CountNotifyFunction);
605   ASSERT_EQ(0, counter.Value());
606 
607   counter.SetTime(0, 1, 0, 10);
608   ASSERT_TRUE(counter.ValueUpdated());
609   ASSERT_TRUE(counter.ValueUpdated());
610   ASSERT_TRUE(counter.ValueUpdated());
611   counter.DeleteTimer();
612   // Add a sleep as other threads may be calling the callback function when the timer is deleted.
613   usleep(500000);
614 }
615 
616 static int timer_create_NULL_signal_handler_invocation_count;
timer_create_NULL_signal_handler(int signal_number)617 static void timer_create_NULL_signal_handler(int signal_number) {
618   ++timer_create_NULL_signal_handler_invocation_count;
619   ASSERT_EQ(SIGALRM, signal_number);
620 }
621 
TEST(time,timer_create_NULL)622 TEST(time, timer_create_NULL) {
623   // A NULL sigevent* is equivalent to asking for SIGEV_SIGNAL for SIGALRM.
624   timer_t timer_id;
625   ASSERT_EQ(0, timer_create(CLOCK_MONOTONIC, nullptr, &timer_id));
626 
627   timer_create_NULL_signal_handler_invocation_count = 0;
628   ScopedSignalHandler ssh(SIGALRM, timer_create_NULL_signal_handler);
629 
630   ASSERT_EQ(0, timer_create_NULL_signal_handler_invocation_count);
631 
632   SetTime(timer_id, 0, 1, 0, 0);
633   usleep(500000);
634 
635   ASSERT_EQ(1, timer_create_NULL_signal_handler_invocation_count);
636 }
637 
TEST(time,timer_create_EINVAL)638 TEST(time, timer_create_EINVAL) {
639   clockid_t invalid_clock = 16;
640 
641   // A SIGEV_SIGNAL timer is easy; the kernel does all that.
642   timer_t timer_id;
643   ASSERT_EQ(-1, timer_create(invalid_clock, nullptr, &timer_id));
644   ASSERT_EQ(EINVAL, errno);
645 
646   // A SIGEV_THREAD timer is more interesting because we have stuff to clean up.
647   sigevent_t se;
648   memset(&se, 0, sizeof(se));
649   se.sigev_notify = SIGEV_THREAD;
650   se.sigev_notify_function = NoOpNotifyFunction;
651   ASSERT_EQ(-1, timer_create(invalid_clock, &se, &timer_id));
652   ASSERT_EQ(EINVAL, errno);
653 }
654 
TEST(time,timer_create_multiple)655 TEST(time, timer_create_multiple) {
656   Counter counter1(Counter::CountNotifyFunction);
657   Counter counter2(Counter::CountNotifyFunction);
658   Counter counter3(Counter::CountNotifyFunction);
659 
660   ASSERT_EQ(0, counter1.Value());
661   ASSERT_EQ(0, counter2.Value());
662   ASSERT_EQ(0, counter3.Value());
663 
664   counter2.SetTime(0, 500000000, 0, 0);
665   sleep(1);
666 
667   EXPECT_EQ(0, counter1.Value());
668   EXPECT_EQ(1, counter2.Value());
669   EXPECT_EQ(0, counter3.Value());
670 }
671 
672 // Test to verify that disarming a repeatable timer disables the callbacks.
TEST(time,timer_disarm_terminates)673 TEST(time, timer_disarm_terminates) {
674   Counter counter(Counter::CountNotifyFunction);
675   ASSERT_EQ(0, counter.Value());
676 
677   counter.SetTime(0, 1, 0, 1);
678   ASSERT_TRUE(counter.ValueUpdated());
679   ASSERT_TRUE(counter.ValueUpdated());
680   ASSERT_TRUE(counter.ValueUpdated());
681 
682   counter.SetTime(0, 0, 0, 0);
683   // Add a sleep as the kernel may have pending events when the timer is disarmed.
684   usleep(500000);
685   int value = counter.Value();
686   usleep(500000);
687 
688   // Verify the counter has not been incremented.
689   ASSERT_EQ(value, counter.Value());
690 }
691 
692 // Test to verify that deleting a repeatable timer disables the callbacks.
TEST(time,timer_delete_terminates)693 TEST(time, timer_delete_terminates) {
694   Counter counter(Counter::CountNotifyFunction);
695   ASSERT_EQ(0, counter.Value());
696 
697   counter.SetTime(0, 1, 0, 1);
698   ASSERT_TRUE(counter.ValueUpdated());
699   ASSERT_TRUE(counter.ValueUpdated());
700   ASSERT_TRUE(counter.ValueUpdated());
701 
702   counter.DeleteTimer();
703   // Add a sleep as other threads may be calling the callback function when the timer is deleted.
704   usleep(500000);
705   int value = counter.Value();
706   usleep(500000);
707 
708   // Verify the counter has not been incremented.
709   ASSERT_EQ(value, counter.Value());
710 }
711 
712 struct TimerDeleteData {
713   timer_t timer_id;
714   pid_t tid;
715   volatile bool complete;
716 };
717 
TimerDeleteCallback(sigval_t value)718 static void TimerDeleteCallback(sigval_t value) {
719   TimerDeleteData* tdd = reinterpret_cast<TimerDeleteData*>(value.sival_ptr);
720 
721   tdd->tid = gettid();
722   timer_delete(tdd->timer_id);
723   tdd->complete = true;
724 }
725 
TEST(time,timer_delete_from_timer_thread)726 TEST(time, timer_delete_from_timer_thread) {
727   TimerDeleteData tdd;
728   sigevent_t se;
729 
730   memset(&se, 0, sizeof(se));
731   se.sigev_notify = SIGEV_THREAD;
732   se.sigev_notify_function = TimerDeleteCallback;
733   se.sigev_value.sival_ptr = &tdd;
734 
735   tdd.complete = false;
736   ASSERT_EQ(0, timer_create(CLOCK_REALTIME, &se, &tdd.timer_id));
737 
738   itimerspec ts;
739   ts.it_value.tv_sec = 1;
740   ts.it_value.tv_nsec = 0;
741   ts.it_interval.tv_sec = 0;
742   ts.it_interval.tv_nsec = 0;
743   ASSERT_EQ(0, timer_settime(tdd.timer_id, 0, &ts, nullptr));
744 
745   time_t cur_time = time(nullptr);
746   while (!tdd.complete && (time(nullptr) - cur_time) < 5);
747   ASSERT_TRUE(tdd.complete);
748 
749 #if defined(__BIONIC__)
750   // Since bionic timers are implemented by creating a thread to handle the
751   // callback, verify that the thread actually completes.
752   cur_time = time(NULL);
753   while ((kill(tdd.tid, 0) != -1 || errno != ESRCH) && (time(NULL) - cur_time) < 5);
754   ASSERT_EQ(-1, kill(tdd.tid, 0));
755   ASSERT_EQ(ESRCH, errno);
756 #endif
757 }
758 
TEST(time,clock_gettime)759 TEST(time, clock_gettime) {
760   // Try to ensure that our vdso clock_gettime is working.
761   timespec ts0;
762   timespec ts1;
763   timespec ts2;
764   ASSERT_EQ(0, clock_gettime(CLOCK_MONOTONIC, &ts0));
765   ASSERT_EQ(0, syscall(__NR_clock_gettime, CLOCK_MONOTONIC, &ts1));
766   ASSERT_EQ(0, clock_gettime(CLOCK_MONOTONIC, &ts2));
767 
768   // Check we have a nice monotonic timestamp sandwich.
769   ASSERT_LE(ts0.tv_sec, ts1.tv_sec);
770   if (ts0.tv_sec == ts1.tv_sec) {
771     ASSERT_LE(ts0.tv_nsec, ts1.tv_nsec);
772   }
773   ASSERT_LE(ts1.tv_sec, ts2.tv_sec);
774   if (ts1.tv_sec == ts2.tv_sec) {
775     ASSERT_LE(ts1.tv_nsec, ts2.tv_nsec);
776   }
777 }
778 
TEST(time,clock_gettime_CLOCK_REALTIME)779 TEST(time, clock_gettime_CLOCK_REALTIME) {
780   timespec ts;
781   ASSERT_EQ(0, clock_gettime(CLOCK_REALTIME, &ts));
782 }
783 
TEST(time,clock_gettime_CLOCK_MONOTONIC)784 TEST(time, clock_gettime_CLOCK_MONOTONIC) {
785   timespec ts;
786   ASSERT_EQ(0, clock_gettime(CLOCK_MONOTONIC, &ts));
787 }
788 
TEST(time,clock_gettime_CLOCK_PROCESS_CPUTIME_ID)789 TEST(time, clock_gettime_CLOCK_PROCESS_CPUTIME_ID) {
790   timespec ts;
791   ASSERT_EQ(0, clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &ts));
792 }
793 
TEST(time,clock_gettime_CLOCK_THREAD_CPUTIME_ID)794 TEST(time, clock_gettime_CLOCK_THREAD_CPUTIME_ID) {
795   timespec ts;
796   ASSERT_EQ(0, clock_gettime(CLOCK_THREAD_CPUTIME_ID, &ts));
797 }
798 
TEST(time,clock_gettime_CLOCK_BOOTTIME)799 TEST(time, clock_gettime_CLOCK_BOOTTIME) {
800   timespec ts;
801   ASSERT_EQ(0, clock_gettime(CLOCK_BOOTTIME, &ts));
802 }
803 
TEST(time,clock_gettime_unknown)804 TEST(time, clock_gettime_unknown) {
805   errno = 0;
806   timespec ts;
807   ASSERT_EQ(-1, clock_gettime(-1, &ts));
808   ASSERT_EQ(EINVAL, errno);
809 }
810 
TEST(time,clock_getres_CLOCK_REALTIME)811 TEST(time, clock_getres_CLOCK_REALTIME) {
812   timespec ts;
813   ASSERT_EQ(0, clock_getres(CLOCK_REALTIME, &ts));
814   ASSERT_EQ(1, ts.tv_nsec);
815   ASSERT_EQ(0, ts.tv_sec);
816 }
817 
TEST(time,clock_getres_CLOCK_MONOTONIC)818 TEST(time, clock_getres_CLOCK_MONOTONIC) {
819   timespec ts;
820   ASSERT_EQ(0, clock_getres(CLOCK_MONOTONIC, &ts));
821   ASSERT_EQ(1, ts.tv_nsec);
822   ASSERT_EQ(0, ts.tv_sec);
823 }
824 
TEST(time,clock_getres_CLOCK_PROCESS_CPUTIME_ID)825 TEST(time, clock_getres_CLOCK_PROCESS_CPUTIME_ID) {
826   timespec ts;
827   ASSERT_EQ(0, clock_getres(CLOCK_PROCESS_CPUTIME_ID, &ts));
828 }
829 
TEST(time,clock_getres_CLOCK_THREAD_CPUTIME_ID)830 TEST(time, clock_getres_CLOCK_THREAD_CPUTIME_ID) {
831   timespec ts;
832   ASSERT_EQ(0, clock_getres(CLOCK_THREAD_CPUTIME_ID, &ts));
833 }
834 
TEST(time,clock_getres_CLOCK_BOOTTIME)835 TEST(time, clock_getres_CLOCK_BOOTTIME) {
836   timespec ts;
837   ASSERT_EQ(0, clock_getres(CLOCK_BOOTTIME, &ts));
838   ASSERT_EQ(1, ts.tv_nsec);
839   ASSERT_EQ(0, ts.tv_sec);
840 }
841 
TEST(time,clock_getres_unknown)842 TEST(time, clock_getres_unknown) {
843   errno = 0;
844   timespec ts = { -1, -1 };
845   ASSERT_EQ(-1, clock_getres(-1, &ts));
846   ASSERT_EQ(EINVAL, errno);
847   ASSERT_EQ(-1, ts.tv_nsec);
848   ASSERT_EQ(-1, ts.tv_sec);
849 }
850 
TEST(time,clock)851 TEST(time, clock) {
852   // clock(3) is hard to test, but a 1s sleep should cost less than 10ms on average.
853   static const clock_t N = 5;
854   static const clock_t mean_limit_ms = 10;
855   clock_t t0 = clock();
856   for (size_t i = 0; i < N; ++i) {
857     sleep(1);
858   }
859   clock_t t1 = clock();
860   ASSERT_LT(t1 - t0, N * mean_limit_ms * (CLOCKS_PER_SEC / 1000));
861 }
862 
GetInvalidPid()863 static pid_t GetInvalidPid() {
864   std::unique_ptr<FILE, decltype(&fclose)> fp{fopen("/proc/sys/kernel/pid_max", "r"), fclose};
865   long pid_max;
866   fscanf(fp.get(), "%ld", &pid_max);
867   return static_cast<pid_t>(pid_max + 1);
868 }
869 
TEST(time,clock_getcpuclockid_current)870 TEST(time, clock_getcpuclockid_current) {
871   clockid_t clockid;
872   ASSERT_EQ(0, clock_getcpuclockid(getpid(), &clockid));
873   timespec ts;
874   ASSERT_EQ(0, clock_gettime(clockid, &ts));
875 }
876 
TEST(time,clock_getcpuclockid_parent)877 TEST(time, clock_getcpuclockid_parent) {
878   clockid_t clockid;
879   ASSERT_EQ(0, clock_getcpuclockid(getppid(), &clockid));
880   timespec ts;
881   ASSERT_EQ(0, clock_gettime(clockid, &ts));
882 }
883 
TEST(time,clock_getcpuclockid_ESRCH)884 TEST(time, clock_getcpuclockid_ESRCH) {
885   // We can't use -1 for invalid pid here, because clock_getcpuclockid() can't detect it.
886   errno = 0;
887   // If this fails, your kernel needs commit e1b6b6ce to be backported.
888   clockid_t clockid;
889   ASSERT_EQ(ESRCH, clock_getcpuclockid(GetInvalidPid(), &clockid)) << "\n"
890     << "Please ensure that the following kernel patches or their replacements have been applied:\n"
891     << "* https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/"
892     << "commit/?id=e1b6b6ce55a0a25c8aa8af019095253b2133a41a\n"
893     << "* https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/"
894     << "commit/?id=c80ed088a519da53f27b798a69748eaabc66aadf\n";
895   ASSERT_EQ(0, errno);
896 }
897 
TEST(time,clock_settime)898 TEST(time, clock_settime) {
899   errno = 0;
900   timespec ts;
901   ASSERT_EQ(-1, clock_settime(-1, &ts));
902   ASSERT_EQ(EINVAL, errno);
903 }
904 
TEST(time,clock_nanosleep_EINVAL)905 TEST(time, clock_nanosleep_EINVAL) {
906   timespec in;
907   timespec out;
908   ASSERT_EQ(EINVAL, clock_nanosleep(-1, 0, &in, &out));
909 }
910 
TEST(time,clock_nanosleep_thread_cputime_id)911 TEST(time, clock_nanosleep_thread_cputime_id) {
912   timespec in;
913   in.tv_sec = 1;
914   in.tv_nsec = 0;
915   ASSERT_EQ(EINVAL, clock_nanosleep(CLOCK_THREAD_CPUTIME_ID, 0, &in, nullptr));
916 }
917 
TEST(time,clock_nanosleep)918 TEST(time, clock_nanosleep) {
919   auto t0 = std::chrono::steady_clock::now();
920   const timespec ts = {.tv_nsec = 5000000};
921   ASSERT_EQ(0, clock_nanosleep(CLOCK_MONOTONIC, 0, &ts, nullptr));
922   auto t1 = std::chrono::steady_clock::now();
923   ASSERT_GE(t1-t0, 5000000ns);
924 }
925 
TEST(time,nanosleep)926 TEST(time, nanosleep) {
927   auto t0 = std::chrono::steady_clock::now();
928   const timespec ts = {.tv_nsec = 5000000};
929   ASSERT_EQ(0, nanosleep(&ts, nullptr));
930   auto t1 = std::chrono::steady_clock::now();
931   ASSERT_GE(t1-t0, 5000000ns);
932 }
933 
TEST(time,nanosleep_EINVAL)934 TEST(time, nanosleep_EINVAL) {
935   timespec ts = {.tv_sec = -1};
936   errno = 0;
937   ASSERT_EQ(-1, nanosleep(&ts, nullptr));
938   ASSERT_EQ(EINVAL, errno);
939 }
940 
TEST(time,bug_31938693)941 TEST(time, bug_31938693) {
942   // User-visible symptoms in N:
943   // http://b/31938693
944   // https://code.google.com/p/android/issues/detail?id=225132
945 
946   // Actual underlying bug (the code change, not the tzdata upgrade that first exposed the bug):
947   // http://b/31848040
948 
949   // This isn't a great test, because very few time zones were actually affected, and there's
950   // no real logic to which ones were affected: it was just a coincidence of the data that came
951   // after them in the tzdata file.
952 
953   time_t t = 1475619727;
954   struct tm tm;
955 
956   setenv("TZ", "America/Los_Angeles", 1);
957   tzset();
958   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
959   EXPECT_EQ(15, tm.tm_hour);
960 
961   setenv("TZ", "Europe/London", 1);
962   tzset();
963   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
964   EXPECT_EQ(23, tm.tm_hour);
965 
966   setenv("TZ", "America/Atka", 1);
967   tzset();
968   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
969   EXPECT_EQ(13, tm.tm_hour);
970 
971   setenv("TZ", "Pacific/Apia", 1);
972   tzset();
973   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
974   EXPECT_EQ(12, tm.tm_hour);
975 
976   setenv("TZ", "Pacific/Honolulu", 1);
977   tzset();
978   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
979   EXPECT_EQ(12, tm.tm_hour);
980 
981   setenv("TZ", "Asia/Magadan", 1);
982   tzset();
983   ASSERT_TRUE(localtime_r(&t, &tm) != nullptr);
984   EXPECT_EQ(9, tm.tm_hour);
985 }
986 
TEST(time,bug_31339449)987 TEST(time, bug_31339449) {
988   // POSIX says localtime acts as if it calls tzset.
989   // tzset does two things:
990   //  1. it sets the time zone ctime/localtime/mktime/strftime will use.
991   //  2. it sets the global `tzname`.
992   // POSIX says localtime_r need not set `tzname` (2).
993   // Q: should localtime_r set the time zone (1)?
994   // Upstream tzcode (and glibc) answer "no", everyone else answers "yes".
995 
996   // Pick a time, any time...
997   time_t t = 1475619727;
998 
999   // Call tzset with a specific timezone.
1000   setenv("TZ", "America/Atka", 1);
1001   tzset();
1002 
1003   // If we change the timezone and call localtime, localtime should use the new timezone.
1004   setenv("TZ", "America/Los_Angeles", 1);
1005   struct tm* tm_p = localtime(&t);
1006   EXPECT_EQ(15, tm_p->tm_hour);
1007 
1008   // Reset the timezone back.
1009   setenv("TZ", "America/Atka", 1);
1010   tzset();
1011 
1012 #if defined(__BIONIC__)
1013   // If we change the timezone again and call localtime_r, localtime_r should use the new timezone.
1014   setenv("TZ", "America/Los_Angeles", 1);
1015   struct tm tm = {};
1016   localtime_r(&t, &tm);
1017   EXPECT_EQ(15, tm.tm_hour);
1018 #else
1019   // The BSDs agree with us, but glibc gets this wrong.
1020 #endif
1021 }
1022 
TEST(time,asctime)1023 TEST(time, asctime) {
1024   const struct tm tm = {};
1025   ASSERT_STREQ("Sun Jan  0 00:00:00 1900\n", asctime(&tm));
1026 }
1027 
TEST(time,asctime_r)1028 TEST(time, asctime_r) {
1029   const struct tm tm = {};
1030   char buf[256];
1031   ASSERT_EQ(buf, asctime_r(&tm, buf));
1032   ASSERT_STREQ("Sun Jan  0 00:00:00 1900\n", buf);
1033 }
1034 
TEST(time,ctime)1035 TEST(time, ctime) {
1036   setenv("TZ", "UTC", 1);
1037   const time_t t = 0;
1038   ASSERT_STREQ("Thu Jan  1 00:00:00 1970\n", ctime(&t));
1039 }
1040 
TEST(time,ctime_r)1041 TEST(time, ctime_r) {
1042   setenv("TZ", "UTC", 1);
1043   const time_t t = 0;
1044   char buf[256];
1045   ASSERT_EQ(buf, ctime_r(&t, buf));
1046   ASSERT_STREQ("Thu Jan  1 00:00:00 1970\n", buf);
1047 }
1048 
1049 // https://issuetracker.google.com/37128336
TEST(time,strftime_strptime_s)1050 TEST(time, strftime_strptime_s) {
1051   char buf[32];
1052   const struct tm tm0 = { .tm_year = 1982-1900, .tm_mon = 0, .tm_mday = 1 };
1053 
1054   setenv("TZ", "America/Los_Angeles", 1);
1055   strftime(buf, sizeof(buf), "<%s>", &tm0);
1056   EXPECT_STREQ("<378720000>", buf);
1057 
1058   setenv("TZ", "UTC", 1);
1059   strftime(buf, sizeof(buf), "<%s>", &tm0);
1060   EXPECT_STREQ("<378691200>", buf);
1061 
1062   struct tm tm;
1063 
1064   setenv("TZ", "America/Los_Angeles", 1);
1065   tzset();
1066   memset(&tm, 0xff, sizeof(tm));
1067   char* p = strptime("378720000x", "%s", &tm);
1068   ASSERT_EQ('x', *p);
1069   EXPECT_EQ(0, tm.tm_sec);
1070   EXPECT_EQ(0, tm.tm_min);
1071   EXPECT_EQ(0, tm.tm_hour);
1072   EXPECT_EQ(1, tm.tm_mday);
1073   EXPECT_EQ(0, tm.tm_mon);
1074   EXPECT_EQ(82, tm.tm_year);
1075   EXPECT_EQ(5, tm.tm_wday);
1076   EXPECT_EQ(0, tm.tm_yday);
1077   EXPECT_EQ(0, tm.tm_isdst);
1078 
1079   setenv("TZ", "UTC", 1);
1080   tzset();
1081   memset(&tm, 0xff, sizeof(tm));
1082   p = strptime("378691200x", "%s", &tm);
1083   ASSERT_EQ('x', *p);
1084   EXPECT_EQ(0, tm.tm_sec);
1085   EXPECT_EQ(0, tm.tm_min);
1086   EXPECT_EQ(0, tm.tm_hour);
1087   EXPECT_EQ(1, tm.tm_mday);
1088   EXPECT_EQ(0, tm.tm_mon);
1089   EXPECT_EQ(82, tm.tm_year);
1090   EXPECT_EQ(5, tm.tm_wday);
1091   EXPECT_EQ(0, tm.tm_yday);
1092   EXPECT_EQ(0, tm.tm_isdst);
1093 }
1094 
TEST(time,strptime_s_nothing)1095 TEST(time, strptime_s_nothing) {
1096   struct tm tm;
1097   ASSERT_EQ(nullptr, strptime("x", "%s", &tm));
1098 }
1099 
TEST(time,timespec_get)1100 TEST(time, timespec_get) {
1101 #if __BIONIC__
1102   timespec ts = {};
1103   ASSERT_EQ(0, timespec_get(&ts, 123));
1104   ASSERT_EQ(TIME_UTC, timespec_get(&ts, TIME_UTC));
1105 #else
1106   GTEST_SKIP() << "glibc doesn't have timespec_get until 2.21";
1107 #endif
1108 }
1109 
TEST(time,difftime)1110 TEST(time, difftime) {
1111   ASSERT_EQ(1.0, difftime(1, 0));
1112   ASSERT_EQ(-1.0, difftime(0, 1));
1113 }
1114