1 /* 2 * caljulian - determine the Julian date from an NTP time. 3 */ 4 #include <sys/types.h> 5 6 #include "ntp_types.h" 7 #include "ntp_calendar.h" 8 #include "ntp_stdlib.h" 9 10 /* 11 * calmonthtab - days-in-the-month table 12 */ 13 static u_short calmonthtab[11] = { 14 JAN, 15 FEB, 16 MAR, 17 APR, 18 MAY, 19 JUN, 20 JUL, 21 AUG, 22 SEP, 23 OCT, 24 NOV 25 }; 26 27 void 28 caljulian( 29 u_long ntptime, 30 register struct calendar *jt 31 ) 32 { 33 u_long ntp_day; 34 u_long minutes; 35 /* 36 * Absolute, zero-adjusted Christian era day, starting from the 37 * mythical day 12/1/1 BC 38 */ 39 u_long acez_day; 40 41 u_long d400; /* Days into a Gregorian cycle */ 42 u_long d100; /* Days into a normal century */ 43 u_long d4; /* Days into a 4-year cycle */ 44 u_long n400; /* # of Gregorian cycles */ 45 u_long n100; /* # of normal centuries */ 46 u_long n4; /* # of 4-year cycles */ 47 u_long n1; /* # of years into a leap year */ 48 /* cycle */ 49 50 /* 51 * Do the easy stuff first: take care of hh:mm:ss, ignoring leap 52 * seconds 53 */ 54 jt->second = (u_char)(ntptime % SECSPERMIN); 55 minutes = ntptime / SECSPERMIN; 56 jt->minute = (u_char)(minutes % MINSPERHR); 57 jt->hour = (u_char)((minutes / MINSPERHR) % HRSPERDAY); 58 59 /* 60 * Find the day past 1900/01/01 00:00 UTC 61 */ 62 ntp_day = ntptime / SECSPERDAY; 63 acez_day = DAY_NTP_STARTS + ntp_day - 1; 64 n400 = acez_day/GREGORIAN_CYCLE_DAYS; 65 d400 = acez_day%GREGORIAN_CYCLE_DAYS; 66 n100 = d400 / GREGORIAN_NORMAL_CENTURY_DAYS; 67 d100 = d400 % GREGORIAN_NORMAL_CENTURY_DAYS; 68 n4 = d100 / GREGORIAN_NORMAL_LEAP_CYCLE_DAYS; 69 d4 = d100 % GREGORIAN_NORMAL_LEAP_CYCLE_DAYS; 70 n1 = d4 / DAYSPERYEAR; 71 72 /* 73 * Calculate the year and year-of-day 74 */ 75 jt->yearday = (u_short)(1 + d4%DAYSPERYEAR); 76 jt->year = (u_short)(400*n400 + 100*n100 + n4*4 + n1); 77 78 if (n100 == 4 || n1 == 4) 79 { 80 /* 81 * If the cycle year ever comes out to 4, it must be December 31st 82 * of a leap year. 83 */ 84 jt->month = 12; 85 jt->monthday = 31; 86 jt->yearday = 366; 87 } 88 else 89 { 90 /* 91 * Else, search forwards through the months to get the right month 92 * and date. 93 */ 94 int monthday; 95 96 jt->year++; 97 monthday = jt->yearday; 98 99 for (jt->month=0;jt->month<11; jt->month++) 100 { 101 int t; 102 103 t = monthday - calmonthtab[jt->month]; 104 if (jt->month == 1 && is_leapyear(jt->year)) 105 t--; 106 107 if (t > 0) 108 monthday = t; 109 else 110 break; 111 } 112 jt->month++; 113 jt->monthday = monthday; 114 } 115 } 116