settime.c 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149
  1. #include <u.h>
  2. #include <libc.h>
  3. #include <auth.h>
  4. #include <fcall.h>
  5. #include "../boot/boot.h"
  6. static long lusertime(char*);
  7. char *timeserver = "#s/boot";
  8. void
  9. settime(int islocal, int afd, char *rp)
  10. {
  11. int n, f;
  12. int timeset;
  13. Dir dir[2];
  14. char timebuf[64];
  15. print("time...");
  16. timeset = 0;
  17. if(islocal){
  18. /*
  19. * set the time from the real time clock
  20. */
  21. f = open("#r/rtc", ORDWR);
  22. if(f >= 0){
  23. if((n = read(f, timebuf, sizeof(timebuf)-1)) > 0){
  24. timebuf[n] = '\0';
  25. timeset = 1;
  26. }
  27. close(f);
  28. }else do{
  29. strcpy(timebuf, "yymmddhhmm[ss]");
  30. outin("\ndate/time ", timebuf, sizeof(timebuf));
  31. }while((timeset=lusertime(timebuf)) <= 0);
  32. }
  33. if(timeset == 0){
  34. /*
  35. * set the time from the access time of the root
  36. */
  37. f = open(timeserver, ORDWR);
  38. if(f < 0)
  39. return;
  40. if(mount(f, afd, "/tmp", MREPL, rp) < 0){
  41. warning("settime mount");
  42. close(f);
  43. return;
  44. }
  45. close(f);
  46. if(stat("/tmp", statbuf, sizeof statbuf) < 0)
  47. fatal("stat");
  48. convM2D(statbuf, sizeof statbuf, &dir[0], (char*)&dir[1]);
  49. sprint(timebuf, "%ld", dir[0].atime);
  50. unmount(0, "/tmp");
  51. }
  52. f = open("#c/time", OWRITE);
  53. if(write(f, timebuf, strlen(timebuf)) < 0)
  54. warning("can't set #c/time");
  55. close(f);
  56. print("\n");
  57. }
  58. #define SEC2MIN 60L
  59. #define SEC2HOUR (60L*SEC2MIN)
  60. #define SEC2DAY (24L*SEC2HOUR)
  61. int
  62. g2(char **pp)
  63. {
  64. int v;
  65. v = 10*((*pp)[0]-'0') + (*pp)[1]-'0';
  66. *pp += 2;
  67. return v;
  68. }
  69. /*
  70. * days per month plus days/year
  71. */
  72. static int dmsize[] =
  73. {
  74. 365, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
  75. };
  76. static int ldmsize[] =
  77. {
  78. 366, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
  79. };
  80. /*
  81. * return the days/month for the given year
  82. */
  83. static int *
  84. yrsize(int y)
  85. {
  86. if((y%4) == 0 && ((y%100) != 0 || (y%400) == 0))
  87. return ldmsize;
  88. else
  89. return dmsize;
  90. }
  91. /*
  92. * compute seconds since Jan 1 1970
  93. */
  94. static long
  95. lusertime(char *argbuf)
  96. {
  97. char *buf;
  98. ulong secs;
  99. int i, y, m;
  100. int *d2m;
  101. buf = argbuf;
  102. i = strlen(buf);
  103. if(i != 10 && i != 12)
  104. return -1;
  105. secs = 0;
  106. y = g2(&buf);
  107. m = g2(&buf);
  108. if(y < 70)
  109. y += 2000;
  110. else
  111. y += 1900;
  112. /*
  113. * seconds per year
  114. */
  115. for(i = 1970; i < y; i++){
  116. d2m = yrsize(i);
  117. secs += d2m[0] * SEC2DAY;
  118. }
  119. /*
  120. * seconds per month
  121. */
  122. d2m = yrsize(y);
  123. for(i = 1; i < m; i++)
  124. secs += d2m[i] * SEC2DAY;
  125. secs += (g2(&buf)-1) * SEC2DAY;
  126. secs += g2(&buf) * SEC2HOUR;
  127. secs += g2(&buf) * SEC2MIN;
  128. if(*buf)
  129. secs += g2(&buf);
  130. sprint(argbuf, "%ld", secs);
  131. return secs;
  132. }