home *** CD-ROM | disk | FTP | other *** search
/ Power-Programmierung / CD2.mdf / c / library / dos / datetime / navytime / navytime.c < prev    next >
Encoding:
C/C++ Source or Header  |  1987-08-15  |  6.8 KB  |  282 lines

  1. /* navytime -- get time from usnaval observatory                            */
  2.  
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <time.h>
  6. #include <string.h>
  7. #include <dos.h>
  8. #include <ctype.h>
  9. #include "comm.h"
  10. #include "timer.h"
  11.  
  12. #ifndef TRUE
  13. #define TRUE            1
  14. #endif
  15. #ifndef FALSE
  16. #define FALSE           0
  17. #endif
  18.  
  19. #define RCFILE          "c:\\etc\\navytime.rc"
  20. #define MAXCMD          128           /* Max size command to modem */
  21. #define LINESIZE        32            /* Max line from modem */
  22. #define MAXRESPONSE     16            /* Max number modem response strings */
  23. #define COMINIT         0x9a          /* 1200 baud, even, 1, 8 */
  24.  
  25. #define SECONDS_PER_MINUTE    60l
  26. #define SECONDS_PER_HOUR      (60l * 60l)
  27. #define SECONDS_PER_DAY       (60l * 60l * 24l)
  28. #define NAVY_TO_UNIX          (-40587l)
  29.  
  30. int                     unit;            /* COM1 = 0, COM2 = 1 */
  31. int                     verbose = 0;
  32.  
  33. char                    dialcmd[MAXCMD + 1] = "",
  34.                         hangcmd[MAXCMD + 1] = "";
  35.  
  36. char                    response_str[MAXRESPONSE][LINESIZE + 1];
  37. int                     nresponse = 0;
  38.  
  39. FILE                    *rcfile;
  40.  
  41. long                    navytime(void);
  42. void                    noconnect(char *s);
  43. void                    sendcom(char *msg);
  44. void                    getcomline(char *buf, int maxlen);
  45. void                    putcom(int);
  46. void                    chk_abort(void);
  47. void                    delay(unsigned);
  48. void                    timeout(void);
  49.  
  50. extern void             settz(void);
  51.  
  52. main(argc, argv)
  53.   int                   argc;
  54.   char                  *argv[];
  55. {
  56.   long                  timewk;
  57.   int                   c;
  58.   int                   i;
  59.   char                  *fname;
  60.   char                  unit_str[8];
  61.  
  62.   /* input configuration file */
  63.   fname = getenv("NAVYTIME");
  64.   if ((rcfile = fopen((fname != NULL) ? fname : RCFILE, "r")) == NULL)
  65.   {
  66.     fputs("navytime: cannot open configuration file\n", stderr);
  67.     exit(1);
  68.   }
  69.  
  70.   if (fgets(unit_str, 7, rcfile) == NULL
  71.    || !isdigit(unit_str[0])
  72.    || unit_str[0] == '0'
  73.    || fgets(dialcmd, MAXCMD, rcfile) == NULL
  74.    || fgets(hangcmd, MAXCMD, rcfile) == NULL)
  75.   {
  76.     fputs("navytime: invalid configuration file\n", stderr);
  77.     exit(1);
  78.   }
  79.   unit = unit_str[0] - '0' - 1;
  80.  
  81.   for (nresponse = 0; nresponse < MAXRESPONSE;)
  82.   {
  83.     if (fgets(response_str[nresponse], LINESIZE, rcfile) == NULL)
  84.       break;
  85.     for (i = strlen(response_str[nresponse]) - 1;
  86.          i >= 0 && !isprint(response_str[nresponse][i]);
  87.          --i)
  88.       ;
  89.     if (i < 0)
  90.       break;
  91.     response_str[nresponse][i + 1] = '\0';
  92.     ++nresponse;
  93.   }
  94.  
  95.   if (nresponse == 0)
  96.   {
  97.     fputs("navytime: invalid configuration file\n", stderr);
  98.     exit(1);
  99.   }
  100.  
  101.   fclose(rcfile);
  102.  
  103.   while ((c = getopt(argc, argv, "v")) != EOF)
  104.     switch (c)
  105.     {
  106.       case 'v':         ++verbose;
  107.     }
  108.  
  109.   comm_open(unit, 1200, 'e', 1, 7);
  110.  
  111.   settz();
  112.   set_timer(60, timeout);
  113.   timewk = navytime();
  114.   set_timer(0, (void (*)()) NULL);
  115.   stime(&timewk);
  116.  
  117.   if (verbose)
  118.   {
  119.     printf("GMT: %s", asctime(gmtime(&timewk)));
  120.     printf("LOC: %s", asctime(localtime(&timewk)));
  121.   }
  122.  
  123.   sendcom(hangcmd);
  124.   comm_close(unit);
  125. }
  126.  
  127. /* get the time                                                             */
  128. long navytime(void)
  129. {
  130.   char                  line[LINESIZE + 1];
  131.   long                  navy_julian, navy_hour, navy_min, navy_sec;
  132.   char                  navy_utc[LINESIZE + 1];
  133.   int                   i;
  134.   long                  ntime;
  135.  
  136.   sendcom(dialcmd);
  137.   comm_clr(unit);
  138.   do
  139.   {
  140.     getcomline(line, LINESIZE);
  141.     if (verbose > 1)
  142.       printf("%s\n", line);
  143.     for (i = 0; i < nresponse; ++i)
  144.       if (strstr(line, response_str[i]) != NULL)
  145.         break;
  146.   } while (i == nresponse);
  147.  
  148.   if (i > 0)
  149.     noconnect(line);
  150.  
  151.   do
  152.   {
  153.     do
  154.     {
  155.       getcomline(line, LINESIZE);
  156.     }  while (line[0] != '*');
  157.  
  158.     getcomline(line, LINESIZE);
  159.     if (verbose > 1)
  160.       printf("%s\n", line);
  161.   } while (sscanf(line, "%ld %*s %2ld %2ld %2ld %s",
  162.                   &navy_julian, &navy_hour, &navy_min, &navy_sec,
  163.                   navy_utc) != 5
  164.      || strcmp(navy_utc, "UTC") != 0);
  165.  
  166.   ntime = (navy_julian + NAVY_TO_UNIX) * SECONDS_PER_DAY
  167.          + navy_hour * SECONDS_PER_HOUR + navy_min * SECONDS_PER_MINUTE
  168.          + navy_sec;
  169.  
  170.   while (comm_getc(unit) != '*')
  171.     chk_abort();
  172.  
  173.   return ntime;
  174. }
  175.  
  176. /* abort after no connect message from modem                                */
  177. void noconnect(char *s)
  178. {
  179.   comm_close_all();
  180.   fprintf(stderr, "navytime: %s\n", s);
  181.   exit(1);
  182. }
  183.   
  184. /* send a message to the modem                                              */
  185. void sendcom(char *msg)
  186. {
  187.   while (*msg != '\0')
  188.   {
  189.     switch (*msg)
  190.     {
  191.       case '"':       while (*++msg != '\0' && *msg != '"')
  192.                         putcom(*msg);
  193.                       if (*msg == '"')
  194.                         ++msg;
  195.                       break;
  196.  
  197.       case '^':       if (*++msg != '\0')
  198.                         putcom(*(msg++) & 0x1f);
  199.                       break;
  200.  
  201.       default:        if (isdigit(*msg))
  202.                       {
  203.                         delay(atoi(msg));
  204.                         while (isdigit(*msg))
  205.                         ++msg;
  206.                       }
  207.                       else
  208.                         ++msg;
  209.     }
  210.   }
  211. }
  212.  
  213. /* put one character to modem                                             */
  214. void putcom(int c)
  215. {
  216.   while (!comm_putc(unit, c))
  217.     chk_abort();
  218. }
  219.  
  220. /* get a line from the modem                                              */
  221. void getcomline(char *buf, int maxlen)
  222. {
  223.   int                   c;
  224.   int                   empty;
  225.  
  226.   empty = TRUE;
  227.   for (;;)
  228.   {
  229.     do
  230.     {
  231.       chk_abort();
  232.     } while ((c = comm_getc(unit)) == -1);
  233.  
  234.    c &= 0x7f;
  235.    if (c == '\r' || c == '\n')
  236.       if (empty)
  237.         continue;
  238.       else
  239.       {
  240.         *buf = '\0';
  241.         return;
  242.       }
  243.     empty = FALSE;
  244.     if (maxlen > 0)
  245.     {
  246.       *(buf++) = c;
  247.       --maxlen;
  248.     }
  249.   }
  250. }
  251.  
  252. /* check for ^C or time out                                                 */
  253. void chk_abort(void)
  254. {
  255.   if ((bdos(0x06, 0x00ff, 0) & 0xff) == '\003')
  256.     exit(1);
  257.   chk_timer();
  258. }
  259.  
  260. /* delay t/10 seconds                                                       */
  261. #define DOSTIMER        ((unsigned volatile far *) MK_FP(0x40, 0x6c))
  262. void delay(unsigned t)
  263. {
  264.   unsigned              d;
  265.  
  266.   t *= 183;
  267.   t /= 100;
  268.   t += (d = *DOSTIMER);
  269.   if (t < d)
  270.     while (*DOSTIMER > t)
  271.       ;
  272.   while (*DOSTIMER < t)
  273.     ;
  274. }
  275.  
  276. /* handle time out                                                          */
  277. void timeout(void)
  278. {
  279.   fputs("navytime: timeout\n", stderr);
  280.   exit(0);
  281. }
  282.