134 lines · c
1/* Time bounds setting test2 * by: john stultz (johnstul@us.ibm.com)3 * (C) Copyright IBM 20124 * Licensed under the GPLv25 *6 * NOTE: This is a meta-test which sets the time to edge cases then7 * uses other tests to detect problems. Thus this test requires that8 * the inconsistency-check and nanosleep tests be present in the same9 * directory it is run from.10 *11 * To build:12 * $ gcc set-2038.c -o set-2038 -lrt13 *14 * This program is free software: you can redistribute it and/or modify15 * it under the terms of the GNU General Public License as published by16 * the Free Software Foundation, either version 2 of the License, or17 * (at your option) any later version.18 *19 * This program is distributed in the hope that it will be useful,20 * but WITHOUT ANY WARRANTY; without even the implied warranty of21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the22 * GNU General Public License for more details.23 */24 25#include <stdio.h>26#include <stdlib.h>27#include <unistd.h>28#include <time.h>29#include <sys/time.h>30#include "../kselftest.h"31 32#define NSEC_PER_SEC 1000000000LL33 34#define KTIME_MAX ((long long)~((unsigned long long)1 << 63))35#define KTIME_SEC_MAX (KTIME_MAX / NSEC_PER_SEC)36 37#define YEAR_1901 (-0x7fffffffL)38#define YEAR_1970 139#define YEAR_2038 0x7fffffffL /*overflows 32bit time_t */40#define YEAR_2262 KTIME_SEC_MAX /*overflows 64bit ktime_t */41#define YEAR_MAX ((long long)((1ULL<<63)-1)) /*overflows 64bit time_t */42 43int is32bits(void)44{45 return (sizeof(long) == 4);46}47 48int settime(long long time)49{50 struct timeval now;51 int ret;52 53 now.tv_sec = (time_t)time;54 now.tv_usec = 0;55 56 ret = settimeofday(&now, NULL);57 58 printf("Setting time to 0x%lx: %d\n", (long)time, ret);59 return ret;60}61 62int do_tests(void)63{64 int ret;65 66 ret = system("date");67 ret = system("./inconsistency-check -c 0 -t 20");68 ret |= system("./nanosleep");69 ret |= system("./nsleep-lat");70 return ret;71 72}73 74int main(int argc, char *argv[])75{76 int ret = 0;77 int opt, dangerous = 0;78 time_t start;79 80 /* Process arguments */81 while ((opt = getopt(argc, argv, "d")) != -1) {82 switch (opt) {83 case 'd':84 dangerous = 1;85 }86 }87 88 start = time(0);89 90 /* First test that crazy values don't work */91 if (!settime(YEAR_1901)) {92 ret = -1;93 goto out;94 }95 if (!settime(YEAR_MAX)) {96 ret = -1;97 goto out;98 }99 if (!is32bits() && !settime(YEAR_2262)) {100 ret = -1;101 goto out;102 }103 104 /* Now test behavior near edges */105 settime(YEAR_1970);106 ret = do_tests();107 if (ret)108 goto out;109 110 settime(YEAR_2038 - 600);111 ret = do_tests();112 if (ret)113 goto out;114 115 /* The rest of the tests can blowup on 32bit systems */116 if (is32bits() && !dangerous)117 goto out;118 /* Test rollover behavior 32bit edge */119 settime(YEAR_2038 - 10);120 ret = do_tests();121 if (ret)122 goto out;123 124 settime(YEAR_2262 - 600);125 ret = do_tests();126 127out:128 /* restore clock */129 settime(start);130 if (ret)131 ksft_exit_fail();132 ksft_exit_pass();133}134