home *** CD-ROM | disk | FTP | other *** search
/ The CDPD Public Domain Collection for CDTV 3 / CDPDIII.bin / pd / programming / gnuc / string / rcs / strftime.c,v < prev    next >
Encoding:
Text File  |  1992-08-02  |  6.1 KB  |  303 lines

  1. head    1.1;
  2. access;
  3. symbols
  4.     version39-41:1.1;
  5. locks;
  6. comment    @ * @;
  7.  
  8.  
  9. 1.1
  10. date    92.06.08.17.58.42;    author mwild;    state Exp;
  11. branches;
  12. next    ;
  13.  
  14.  
  15. desc
  16. @initial checkin
  17. @
  18.  
  19.  
  20. 1.1
  21. log
  22. @Initial revision
  23. @
  24. text
  25. @/*
  26.  * Copyright (c) 1989 The Regents of the University of California.
  27.  * All rights reserved.
  28.  *
  29.  * Redistribution and use in source and binary forms are permitted
  30.  * provided that: (1) source distributions retain this entire copyright
  31.  * notice and comment, and (2) distributions including binaries display
  32.  * the following acknowledgement:  ``This product includes software
  33.  * developed by the University of California, Berkeley and its contributors''
  34.  * in the documentation or other materials provided with the distribution
  35.  * and in all advertising materials mentioning features or use of this
  36.  * software. Neither the name of the University nor the names of its
  37.  * contributors may be used to endorse or promote products derived
  38.  * from this software without specific prior written permission.
  39.  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
  40.  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
  41.  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  42.  */
  43.  
  44. #if defined(LIBC_SCCS) && !defined(lint)
  45. static char sccsid[] = "@@(#)strftime.c    5.8 (Berkeley) 6/1/90";
  46. #endif /* LIBC_SCCS and not lint */
  47.  
  48. /*
  49.  * NOTE: I used the older version of this file, since the 4.3bsd-net2
  50.  *     version uses mktime() from ctime.c, and ctime.c is badly suited
  51.  *     for inclusion in a shared library (too much static stuff...)
  52.  */
  53.  
  54.  
  55. #define KERNEL
  56. #include "ixemul.h"
  57.  
  58. #include <sys/types.h>
  59. #include <sys/time.h>
  60. #include <time.h>
  61. #include <tzfile.h>
  62. #include <string.h>
  63.  
  64. static char *afmt[] = {
  65.     "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat",
  66. };
  67. static char *Afmt[] = {
  68.     "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday",
  69.     "Saturday",
  70. };
  71. static char *bfmt[] = {
  72.     "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep",
  73.     "Oct", "Nov", "Dec",
  74. };
  75. static char *Bfmt[] = {
  76.     "January", "February", "March", "April", "May", "June", "July",
  77.     "August", "September", "October", "November", "December",
  78. };
  79.  
  80. static size_t gsize;
  81. static char *pt;
  82.  
  83. size_t
  84. strftime(s, maxsize, format, t)
  85.     char *s;
  86.     const char *format;
  87.     size_t maxsize;
  88.     const struct tm *t;
  89. {
  90.     size_t _fmt();
  91.     size_t res;
  92.  
  93.     ix_lock_base ();
  94.  
  95.     pt = s;
  96.     if ((gsize = maxsize) < 1)
  97.       {
  98.         res = 0;
  99.         goto unlock;
  100.       }
  101.     if (_fmt(format, t)) {
  102.         *pt = '\0';
  103.         res = maxsize - gsize;
  104.         goto unlock;
  105.     }
  106.     res = 0;
  107.  
  108. unlock:
  109.     ix_unlock_base ();
  110.     return res;
  111. }
  112.  
  113. static size_t
  114. _fmt(format, t)
  115.     register char *format;
  116.     struct tm *t;
  117. {
  118.     for (; *format; ++format) {
  119.         if (*format == '%')
  120.             switch(*++format) {
  121.             case '\0':
  122.                 --format;
  123.                 break;
  124.             case 'A':
  125.                 if (t->tm_wday < 0 || t->tm_wday > 6)
  126.                     return(0);
  127.                 if (!_add(Afmt[t->tm_wday]))
  128.                     return(0);
  129.                 continue;
  130.             case 'a':
  131.                 if (t->tm_wday < 0 || t->tm_wday > 6)
  132.                     return(0);
  133.                 if (!_add(afmt[t->tm_wday]))
  134.                     return(0);
  135.                 continue;
  136.             case 'B':
  137.                 if (t->tm_mon < 0 || t->tm_mon > 11)
  138.                     return(0);
  139.                 if (!_add(Bfmt[t->tm_mon]))
  140.                     return(0);
  141.                 continue;
  142.             case 'b':
  143.             case 'h':
  144.                 if (t->tm_mon < 0 || t->tm_mon > 11)
  145.                     return(0);
  146.                 if (!_add(bfmt[t->tm_mon]))
  147.                     return(0);
  148.                 continue;
  149.             case 'C':
  150.                 if (!_fmt("%a %b %e %H:%M:%S %Y", t))
  151.                     return(0);
  152.                 continue;
  153.             case 'c':
  154.                 if (!_fmt("%m/%d/%y %H:%M:%S", t))
  155.                     return(0);
  156.                 continue;
  157.             case 'e':
  158.                 if (!_conv(t->tm_mday, 2, ' '))
  159.                     return(0);
  160.                 continue;
  161.             case 'D':
  162.                 if (!_fmt("%m/%d/%y", t))
  163.                     return(0);
  164.                 continue;
  165.             case 'd':
  166.                 if (!_conv(t->tm_mday, 2, '0'))
  167.                     return(0);
  168.                 continue;
  169.             case 'H':
  170.                 if (!_conv(t->tm_hour, 2, '0'))
  171.                     return(0);
  172.                 continue;
  173.             case 'I':
  174.                 if (!_conv(t->tm_hour % 12 ?
  175.                     t->tm_hour % 12 : 12, 2, '0'))
  176.                     return(0);
  177.                 continue;
  178.             case 'j':
  179.                 if (!_conv(t->tm_yday + 1, 3, '0'))
  180.                     return(0);
  181.                 continue;
  182.             case 'k':
  183.                 if (!_conv(t->tm_hour, 2, ' '))
  184.                     return(0);
  185.                 continue;
  186.             case 'l':
  187.                 if (!_conv(t->tm_hour % 12 ?
  188.                     t->tm_hour % 12 : 12, 2, ' '))
  189.                     return(0);
  190.                 continue;
  191.             case 'M':
  192.                 if (!_conv(t->tm_min, 2, '0'))
  193.                     return(0);
  194.                 continue;
  195.             case 'm':
  196.                 if (!_conv(t->tm_mon + 1, 2, '0'))
  197.                     return(0);
  198.                 continue;
  199.             case 'n':
  200.                 if (!_add("\n"))
  201.                     return(0);
  202.                 continue;
  203.             case 'p':
  204.                 if (!_add(t->tm_hour >= 12 ? "PM" : "AM"))
  205.                     return(0);
  206.                 continue;
  207.             case 'R':
  208.                 if (!_fmt("%H:%M", t))
  209.                     return(0);
  210.                 continue;
  211.             case 'r':
  212.                 if (!_fmt("%I:%M:%S %p", t))
  213.                     return(0);
  214.                 continue;
  215.             case 'S':
  216.                 if (!_conv(t->tm_sec, 2, '0'))
  217.                     return(0);
  218.                 continue;
  219.             case 'T':
  220.             case 'X':
  221.                 if (!_fmt("%H:%M:%S", t))
  222.                     return(0);
  223.                 continue;
  224.             case 't':
  225.                 if (!_add("\t"))
  226.                     return(0);
  227.                 continue;
  228.             case 'U':
  229.                 if (!_conv((t->tm_yday + 7 - t->tm_wday) / 7,
  230.                     2, '0'))
  231.                     return(0);
  232.                 continue;
  233.             case 'W':
  234.                 if (!_conv((t->tm_yday + 7 -
  235.                     (t->tm_wday ? (t->tm_wday - 1) : 6))
  236.                     / 7, 2, '0'))
  237.                     return(0);
  238.                 continue;
  239.             case 'w':
  240.                 if (!_conv(t->tm_wday, 1, '0'))
  241.                     return(0);
  242.                 continue;
  243.             case 'x':
  244.                 if (!_fmt("%m/%d/%y", t))
  245.                     return(0);
  246.                 continue;
  247.             case 'y':
  248.                 if (!_conv((t->tm_year + TM_YEAR_BASE)
  249.                     % 100, 2, '0'))
  250.                     return(0);
  251.                 continue;
  252.             case 'Y':
  253.                 if (!_conv(t->tm_year + TM_YEAR_BASE, 4, '0'))
  254.                     return(0);
  255.                 continue;
  256.             case 'Z':
  257.                 if (!t->tm_zone || !_add(t->tm_zone))
  258.                     return(0);
  259.                 continue;
  260.             case '%':
  261.             /*
  262.              * X311J/88-090 (4.12.3.5): if conversion char is
  263.              * undefined, behavior is undefined.  Print out the
  264.              * character itself as printf(3) does.
  265.              */
  266.             default:
  267.                 break;
  268.         }
  269.         if (!gsize--)
  270.             return(0);
  271.         *pt++ = *format;
  272.     }
  273.     return(gsize);
  274. }
  275.  
  276. static
  277. _conv(n, digits, pad)
  278.     int n, digits;
  279.     char pad;
  280. {
  281.     static char buf[10];
  282.     register char *p;
  283.  
  284.     for (p = buf + sizeof(buf) - 2; n > 0 && p > buf; n /= 10, --digits)
  285.         *p-- = n % 10 + '0';
  286.     while (p > buf && digits-- > 0)
  287.         *p-- = pad;
  288.     return(_add(++p));
  289. }
  290.  
  291. static
  292. _add(str)
  293.     register char *str;
  294. {
  295.     for (;; ++pt, --gsize) {
  296.         if (!gsize)
  297.             return(0);
  298.         if (!(*pt = *str++))
  299.             return(1);
  300.     }
  301. }
  302. @
  303.