1 /* 2 * Test the RTAS interface 3 */ 4 5 #include <libcflat.h> 6 #include <util.h> 7 #include <asm/rtas.h> 8 9 #define DAYS(y,m,d) (365UL * (y) + ((y) / 4) - ((y) / 100) + ((y) / 400) + \ 10 367UL * (m) / 12 + \ 11 (d)) 12 13 static unsigned long mktime(int year, int month, int day, 14 int hour, int minute, int second) 15 { 16 unsigned long epoch; 17 18 /* Put February at end of the year to avoid leap day this year */ 19 20 month -= 2; 21 if (month <= 0) { 22 month += 12; 23 year -= 1; 24 } 25 26 /* compute epoch: substract DAYS(since_March(1-1-1970)) */ 27 28 epoch = DAYS(year, month, day) - DAYS(1969, 11, 1); 29 30 epoch = epoch * 24 + hour; 31 epoch = epoch * 60 + minute; 32 epoch = epoch * 60 + second; 33 34 return epoch; 35 } 36 37 #define DELAY 1 38 #define MAX_LOOP 10000000 39 40 static void check_get_time_of_day(unsigned long start) 41 { 42 uint32_t token; 43 int ret; 44 int now[8]; 45 unsigned long t1, t2, count; 46 47 ret = rtas_token("get-time-of-day", &token); 48 report("token available", ret == 0); 49 if (ret) 50 return; 51 52 ret = rtas_call(token, 0, 8, now); 53 report("execution", ret == 0); 54 55 report("second", now[5] >= 0 && now[5] <= 59); 56 report("minute", now[4] >= 0 && now[4] <= 59); 57 report("hour", now[3] >= 0 && now[3] <= 23); 58 report("day", now[2] >= 1 && now[2] <= 31); 59 report("month", now[1] >= 1 && now[1] <= 12); 60 report("year", now[0] >= 1970); 61 report("accuracy (< 3s)", mktime(now[0], now[1], now[2], 62 now[3], now[4], now[5]) - start < 3); 63 64 ret = rtas_call(token, 0, 8, now); 65 t1 = mktime(now[0], now[1], now[2], now[3], now[4], now[5]); 66 count = 0; 67 do { 68 ret = rtas_call(token, 0, 8, now); 69 t2 = mktime(now[0], now[1], now[2], now[3], now[4], now[5]); 70 count++; 71 } while (t1 + DELAY > t2 && count < MAX_LOOP); 72 report("running", t1 + DELAY <= t2); 73 } 74 75 static void check_set_time_of_day(void) 76 { 77 uint32_t stod_token, gtod_token; 78 int ret; 79 int date[8]; 80 unsigned long t1, t2, count; 81 82 ret = rtas_token("set-time-of-day", &stod_token); 83 report("token available", ret == 0); 84 if (ret) 85 return; 86 87 /* 23:59:59 28/2/2000 */ 88 89 ret = rtas_call(stod_token, 7, 1, NULL, 2000, 2, 28, 23, 59, 59); 90 report("execution", ret == 0); 91 92 /* check it has worked */ 93 ret = rtas_token("get-time-of-day", >od_token); 94 assert(ret == 0); 95 ret = rtas_call(gtod_token, 0, 8, date); 96 report("re-read", ret == 0); 97 t1 = mktime(2000, 2, 28, 23, 59, 59); 98 t2 = mktime(date[0], date[1], date[2], 99 date[3], date[4], date[5]); 100 report("result", t2 - t1 < 2); 101 102 /* check it is running */ 103 count = 0; 104 do { 105 ret = rtas_call(gtod_token, 0, 8, date); 106 t2 = mktime(date[0], date[1], date[2], 107 date[3], date[4], date[5]); 108 count++; 109 } while (t1 + DELAY > t2 && count < MAX_LOOP); 110 report("running", t1 + DELAY <= t2); 111 } 112 113 int main(int argc, char **argv) 114 { 115 int len; 116 long val; 117 118 report_prefix_push("rtas"); 119 120 if (argc < 2) 121 report_abort("no test specified"); 122 123 report_prefix_push(argv[1]); 124 125 if (strcmp(argv[1], "get-time-of-day") == 0) { 126 127 len = parse_keyval(argv[2], &val); 128 if (len == -1) { 129 printf("Missing parameter \"date\"\n"); 130 abort(); 131 } 132 argv[2][len] = '\0'; 133 134 check_get_time_of_day(val); 135 136 } else if (strcmp(argv[1], "set-time-of-day") == 0) { 137 138 check_set_time_of_day(); 139 140 } else { 141 printf("Unknown subtest\n"); 142 abort(); 143 } 144 145 report_prefix_pop(); 146 147 report_prefix_pop(); 148 149 return report_summary(); 150 } 151