home *** CD-ROM | disk | FTP | other *** search
/ The Fred Fish Collection 1.5 / ffcollection-1-5-1992-11.iso / ff_disks / 300-399 / ff398.lzh / DClock / DClockChip.c < prev    next >
C/C++ Source or Header  |  1990-11-01  |  5KB  |  230 lines

  1. /* DClockChip.c *************************************************************
  2.  *
  3.  *    DClockChip ----    Real time clock support routines for DClock.
  4.  *
  5.  *    Author --------    Olaf 'Olsen' Barthel, MXM
  6.  *            Brabeckstrasse 35
  7.  *            D-3000 Hannover 71
  8.  *
  9.  *            Federal Republic of Germany
  10.  *
  11.  *    This  program  truly is in the PUBLIC DOMAIN.  Written on a cold
  12.  *    and  damp  September  evening,  hoping the next morning would be
  13.  *    better.
  14.  *
  15.  *    Compiled using Aztec C 5.0b, CygnusEd Professional 2 & ARexx.
  16.  *
  17.  ***************************************************************************/
  18.  
  19.     /* Various definitions needed by the datestamp
  20.      * conversion routine.
  21.      */
  22.  
  23. #define MINS_PER_HOUR    60
  24. #define SECS_PER_MIN    60
  25. #define SECS_PER_HOUR    (SECS_PER_MIN * MINS_PER_HOUR)
  26. #define SECS_PER_DAY    (SECS_PER_HOUR * 24)
  27. #define TICS_PER_SEC    50
  28.  
  29. #define FEB        1
  30. #define DAYS_PER_YEAR    365
  31. #define YEARS_PER_LEAP    4
  32. #define START_YEAR    1978
  33. #define FIRST_LEAP_YEAR    1980
  34. #define LEAP_ADJUST    (FIRST_LEAP_YEAR - START_YEAR)
  35. #define LEAP_FEB_DAYS    29
  36. #define NORM_FEB_DAYS    28
  37.  
  38.     /* Alias names for clock chip registers. */
  39.  
  40. #define Clock_Second1    (clock . Second1    & 0xF)
  41. #define Clock_Second10    (clock . Second10    & 0xF)
  42. #define Clock_Minute1    (clock . Minute1    & 0xF)
  43. #define Clock_Minute10    (clock . Minute10    & 0xF)
  44. #define Clock_Hour1    (clock . Hour1        & 0xF)
  45. #define Clock_Hour10    (clock . Hour10        & 0xF)
  46. #define Clock_Day1    (clock . Day1        & 0xF)
  47. #define Clock_Day10    (clock . Day10        & 0xF)
  48. #define Clock_Month1    (clock . Month1        & 0xF)
  49. #define Clock_Month10    (clock . Month10    & 0xF)
  50. #define Clock_Year1    (clock . Year1        & 0xF)
  51. #define Clock_Year10    (clock . Year10        & 0xF)
  52.  
  53.     /* The builtin clock chip (OKI MSM624SRS) consists of
  54.      * sixteen registers of which each contains four bits
  55.      * of relevant information. The following structure
  56.      * tries to come as close to the register map as
  57.      * possible, even though bitfields would have been
  58.      * the better approach. Unfortunately Aztec 'C' 5.0b
  59.      * forces bitfields to be long word aligned rather than
  60.      * word aligned which causes a whole lot of confusion.
  61.      */
  62.  
  63. struct ClockChip
  64. {
  65.     UWORD        pad0;
  66.     volatile UWORD    Second1;
  67.     UWORD        pad1;
  68.     volatile UWORD    Second10;
  69.     UWORD        pad2;
  70.     volatile UWORD    Minute1;
  71.     UWORD        pad3;
  72.     volatile UWORD    Minute10;
  73.     UWORD        pad4;
  74.     volatile UWORD    Hour1;
  75.     UWORD        pad5;
  76.     volatile UWORD    Hour10;
  77.     UWORD        pad6;
  78.     volatile UWORD    Day1;
  79.     UWORD        pad7;
  80.     volatile UWORD    Day10;
  81.     UWORD        pad8;
  82.     volatile UWORD    Month1;
  83.     UWORD        pad9;
  84.     volatile UWORD    Month10;
  85.     UWORD        pad10;
  86.     volatile UWORD    Year1;
  87.     UWORD        pad11;
  88.     volatile UWORD    Year10;
  89.     ULONG        pad12;
  90.     UWORD        pad13;
  91.     volatile UWORD    Adjust;
  92. };
  93.  
  94.     /* Easy way to access the builtin clock chip. */
  95.  
  96. #define clock (*((struct ClockChip *)0xdc0000))
  97.  
  98.     /* DateToTimeVal(struct DateTag *Date,struct timeval *TimeVal):
  99.      *
  100.      *    Converts the contents of a DateTag into a timeval
  101.      *    as used by timer.device.
  102.      */
  103.  
  104. VOID
  105. DateToTimeVal(struct DateTag *Date,struct timeval *TimeVal)
  106. {
  107.     LONG    DaysElapsed,YearsElapsed,LeapYears;
  108.     SHORT    i;
  109.  
  110.         /* Number of days in each month. */
  111.  
  112.     static UBYTE Months[12] =
  113.     {
  114.         31,28,31,30,
  115.         31,30,31,31,
  116.         30,31,30,31
  117.     };
  118.  
  119.         /* Is this a leap year? */
  120.  
  121.     if(Date -> Year % YEARS_PER_LEAP)
  122.         Months[FEB] = NORM_FEB_DAYS;
  123.     else
  124.         Months[FEB] = LEAP_FEB_DAYS;
  125.  
  126.         /* Calculate elapsed time. */
  127.  
  128.     YearsElapsed    = Date -> Year - START_YEAR;
  129.     LeapYears    = (YearsElapsed + LEAP_ADJUST - 1) / YEARS_PER_LEAP;
  130.     DaysElapsed    = (YearsElapsed * DAYS_PER_YEAR) + LeapYears;
  131.  
  132.         /* Add the days already passed in this year. */
  133.  
  134.     for(i = 0; i < Date -> Month - 1 ; i++)
  135.         DaysElapsed += Months[i];
  136.  
  137.         /* Add the days in the current month. */
  138.  
  139.     DaysElapsed += Date -> Day - 1;
  140.  
  141.         /* Calculate number of seconds. */
  142.  
  143.     TimeVal -> tv_secs    = DaysElapsed * SECS_PER_DAY + (Date -> Hour * MINS_PER_HOUR + Date -> Minute) * SECS_PER_MIN + Date -> Second;
  144.     TimeVal -> tv_micro    = 0;
  145. }
  146.  
  147.     /* ReadClock():
  148.      *
  149.      *    Read the system clock and set the system time
  150.      *    accordingly.
  151.      */
  152.  
  153. BYTE
  154. ReadClock()
  155. {
  156.     struct MsgPort        *TimePort;
  157.     struct timerequest    *TimeRequest;
  158.     struct DateTag         Date;
  159.     UBYTE             LastTick;
  160.     BYTE             Success = FALSE;
  161.  
  162.         /* Check the second timer. */
  163.  
  164.     LastTick = Clock_Second1;
  165.  
  166.         /* Wait two seconds. */
  167.  
  168.     Delay(TICS_PER_SEC * 2);
  169.  
  170.         /* If the value has changed, we have a
  171.          * clock chip installed.
  172.          */
  173.  
  174.     if(LastTick != Clock_Second1)
  175.     {
  176.         if(TimePort = CreatePort(NULL,0))
  177.         {
  178.             if(TimeRequest = (struct timerequest *)CreateExtIO(TimePort,sizeof(struct timerequest)))
  179.             {
  180.                 if(!OpenDevice(TIMERNAME,UNIT_VBLANK,TimeRequest,0))
  181.                 {
  182.                     TimeRequest -> tr_node . io_Command = TR_SETSYSTIME;
  183.  
  184.                     Forbid();
  185.  
  186.                         /* Stop the clock. */
  187.  
  188.                     clock . Adjust |= 1;
  189.  
  190.                         /* Wait for it to calm down. */
  191.  
  192.                     while(clock . Adjust & 2);
  193.  
  194.                         /* Convert the clock entries into a DateTag. */
  195.  
  196.                     Date . Year    = (Clock_Year10 < 7 ? 10 + Clock_Year10 : Clock_Year10) * 10 + Clock_Year1 + 1900;
  197.                     Date . Month    = Clock_Month10 * 10 + Clock_Month1;
  198.                     Date . Day    = Clock_Day10 * 10 + Clock_Day1;
  199.  
  200.                     Date . Hour    = Clock_Hour10 * 10 + Clock_Hour1;
  201.                     Date . Minute    = Clock_Minute10 * 10 + Clock_Minute1;
  202.                     Date . Second    = Clock_Second10 * 10 + Clock_Second1;
  203.  
  204.                         /* Restart the clock. */
  205.  
  206.                     clock . Adjust &= ~1;
  207.  
  208.                     DateToTimeVal(&Date,&TimeRequest -> tr_time);
  209.  
  210.                         /* Set the system time. */
  211.  
  212.                     DoIO(TimeRequest);
  213.  
  214.                     Permit();
  215.  
  216.                     Success = TRUE;
  217.  
  218.                     CloseDevice(TimeRequest);
  219.                 }
  220.  
  221.                 DeleteExtIO(TimeRequest);
  222.             }
  223.  
  224.             DeletePort(TimePort);
  225.         }
  226.     }
  227.  
  228.     return(Success);
  229. }
  230.