Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

182 lines
6.3 KiB

  1. /*
  2. * TIME.C - Various time subroutines needed by NetWare Login Script
  3. *
  4. * Copyright (c) 1995 Microsoft Corporation
  5. */
  6. #include "common.h"
  7. // Needed to convert netware net date to DOS date
  8. #define _70_to_80_bias 0x012CEA600L
  9. #define SECS_IN_DAY (60L*60L*24L)
  10. #define SEC2S_IN_DAY (30L*60L*24L)
  11. #define FOURYEARS (3*365+366)
  12. WORD MonTotal[] = { 0, // dummy entry for month 0
  13. 0, // days before Jan 1
  14. 31, // days before Feb 1
  15. 31+28, // days before Mar 1
  16. 31+28+31, // days before Apr 1
  17. 31+28+31+30, // days before May 1
  18. 31+28+31+30+31, // days before Jun 1
  19. 31+28+31+30+31+30, // days before Jul 1
  20. 31+28+31+30+31+30+31, // days before Aug 1
  21. 31+28+31+30+31+30+31+31, // days before Sep 1
  22. 31+28+31+30+31+30+31+31+30, // days before Oct 1
  23. 31+28+31+30+31+30+31+31+30+31, // days before Nov 1
  24. 31+28+31+30+31+30+31+31+30+31+30, // days before Dec 1
  25. 31+28+31+30+31+30+31+31+30+31+30+31 // days before end of year
  26. };
  27. #define YR_MASK 0xFE00
  28. #define LEAPYR_MASK 0x0600
  29. #define YR_BITS 7
  30. #define MON_MASK 0x01E0
  31. #define MON_BITS 4
  32. #define DAY_MASK 0x001F
  33. #define DAY_BITS 5
  34. #define HOUR_MASK 0xF800
  35. #define HOUR_BITS 5
  36. #define MIN_MASK 0x07E0
  37. #define MIN_BITS 6
  38. #define SEC2_MASK 0x001F
  39. #define SEC2_BITS 5
  40. static void NetToDosDate( DWORD time, WORD * dosdate, WORD * dostime )
  41. {
  42. DWORD secs, days;
  43. WORD r;
  44. time = (time - _70_to_80_bias) / 2; // # of 2 second periods since 1980
  45. secs = time % SEC2S_IN_DAY; // 2 second period into day
  46. days = time / SEC2S_IN_DAY; // days since Jan 1 1980
  47. r = (WORD) ( secs % 30 ); // # of 2 second steps
  48. secs /= 30;
  49. r |= (secs % 60) << SEC2_BITS; // # of minutes
  50. r |= (secs / 60) << (SEC2_BITS+MIN_BITS); // # of hours
  51. *dostime = r;
  52. r = (WORD) ( days / FOURYEARS );// (r) = four year period past 1980
  53. days %= FOURYEARS; // (days) = days into four year period
  54. r *= 4; // (r) = years since 1980 (within 3)
  55. if (days == 31+28) {
  56. //* Special case for FEB 29th
  57. r = (r<<(MON_BITS+DAY_BITS)) + (2<<DAY_BITS) + 29;
  58. } else {
  59. if (days > 31+28)
  60. --days; // compensate for leap year
  61. while (days >= 365) {
  62. ++r;
  63. days -= 365;
  64. }
  65. for (secs = 1; days >= MonTotal[secs+1] ; ++secs)
  66. ;
  67. days -= MonTotal[secs];
  68. r <<= MON_BITS;
  69. r += (WORD)secs;
  70. r <<= DAY_BITS;
  71. r += (WORD)days+1;
  72. }
  73. *dosdate = r;
  74. }
  75. void nwShowLastLoginTime(VOID)
  76. {
  77. LONG lTime = 0L;
  78. SYSTEMTIME st;
  79. FILETIME ft;
  80. TIME_ZONE_INFORMATION tz;
  81. WCHAR szTimeBuf[TIMEDATE_SIZE];
  82. WCHAR szDateBuf[TIMEDATE_SIZE];
  83. int ret;
  84. WORD dostime, dosdate;
  85. DWORD tzStat;
  86. if ( ret = NDSGetUserProperty ("Last Login Time", (PBYTE)&lTime,
  87. 4, NULL, NULL) )
  88. {
  89. #ifdef DEBUG
  90. OutputDebugString("NWLSPROC: error getting LOGIN TIME\n\r");
  91. #endif
  92. return;
  93. }
  94. // From NetWare we get seconds from 1970, need to go through
  95. // several conversions to get system time for NLS
  96. // First deduct bias from UTC time to correct for local time
  97. tzStat = GetTimeZoneInformation(&tz);
  98. if ( tzStat != (DWORD)-1 ) {
  99. if (tzStat == TIME_ZONE_ID_STANDARD)
  100. tz.Bias += tz.StandardBias;
  101. else if (tzStat == TIME_ZONE_ID_DAYLIGHT)
  102. tz.Bias += tz.DaylightBias;
  103. lTime -= tz.Bias*60;
  104. }
  105. #ifdef DEBUG
  106. else {
  107. OutputDebugString("NWLSPROC: GetTimeZoneInformation failed\n\r");
  108. }
  109. #endif // DEBUG
  110. NetToDosDate( lTime, &dosdate, &dostime );
  111. DosDateTimeToFileTime ( dosdate, dostime, &ft );
  112. FileTimeToSystemTime ( &ft, &st );
  113. #ifdef notdef
  114. // I don't understand this comment, this code doesn't seem to be
  115. // needed for NT. - terry
  116. //
  117. // This code will work on NT, but not on Win95.
  118. // Convert the resulting system (UTC) time to local time
  119. if ( GetTimeZoneInformation(&tz) != (DWORD)-1 ) {
  120. SYSTEMTIME utcTime = st;
  121. SystemTimeToTzSpecificLocalTime ( &tz, &utcTime, &st );
  122. }
  123. #ifdef DEBUG
  124. else {
  125. OutputDebugString("NWLSPROC: GetTimeZoneInformation failed\n\r");
  126. }
  127. #endif // DEBUG
  128. #endif
  129. wcscpy(szTimeBuf, L"");
  130. ret = GetTimeFormat ( GetSystemDefaultLCID(),
  131. TIME_FORCE24HOURFORMAT|TIME_NOTIMEMARKER,
  132. &st,
  133. NULL,
  134. szTimeBuf,
  135. TIMEDATE_SIZE );
  136. #ifdef DEBUG
  137. if ( !ret ) {
  138. char buf[80];
  139. wsprintf(buf,"NWLSPROC: GetTimeFormatA failure: %d sec:%ld\n\r",
  140. GetLastError(), lTime );
  141. OutputDebugString(buf);
  142. }
  143. #endif
  144. ret = GetDateFormat(LOCALE_USER_DEFAULT,
  145. DATE_LONGDATE,
  146. &st,
  147. NULL,
  148. szDateBuf,
  149. TIMEDATE_SIZE );
  150. #ifdef DEBUG
  151. if ( !ret ) {
  152. char buf[80];
  153. wsprintf(buf,"NWLSPROC: GetDateFormatA failure: %d sec:%ld\n\r",
  154. GetLastError(), lTime );
  155. OutputDebugString(buf);
  156. }
  157. #endif
  158. DisplayMessage( IDR_LASTLOGIN, szDateBuf, szTimeBuf );
  159. }