home *** CD-ROM | disk | FTP | other *** search
/ Columbia Kermit / kermit.zip / old / ckermit60 / ckustr.c < prev    next >
C/C++ Source or Header  |  2020-01-01  |  7KB  |  420 lines

  1. /*
  2.   Copyright (C) 1985, 1996, Trustees of Columbia University in the City of New
  3.   York.  The C-Kermit software may not be, in whole or in part, licensed or
  4.   sold for profit as a software product itself, nor may it be included in or
  5.   distributed with commercial products or otherwise distributed by commercial
  6.   concerns to their clients or customers without written permission of the
  7.   Office of Kermit Development and Distribution, Columbia University.  This
  8.   copyright notice must not be removed, altered, or obscured.
  9. */
  10.  
  11. /*
  12.  * ckustr.c - string extraction/restoration routines
  13. */
  14.  
  15. #include <stdio.h>
  16. #include <sysexits.h>
  17. #include <varargs.h>
  18. #include <paths.h>
  19.  
  20. /*
  21.   STR_FILE must be defined as a quoted string on the cc command line,
  22.   for example:
  23.  
  24.       -DSTR_FILE=\\\"/usr/local/lib/cku192.sr\\\"
  25.  
  26.   This is the file where the strings go, and where C-Kermit looks for them
  27.   at runtime.
  28. */
  29.  
  30. #ifdef STR_FILE
  31. char    *StringFile = STR_FILE;
  32. #else
  33. char    *StringFile = "/usr/local/lib/cku192.sr";
  34. #endif /* STR_FILE */
  35.  
  36. /*
  37.  * If _PATH_CTIMED is defined (in <paths.h>) then use that definition.  2.11BSD
  38.  * has this defined but 2.10BSD and other systems do not.
  39. */
  40.  
  41. #ifndef _PATH_CTIMED
  42. #define    _PATH_CTIMED STR_CTIMED
  43. #endif
  44.  
  45. extern int errno;
  46. static int strfile = -1, ourpid = 0;
  47.  
  48. #define BUFLEN 256
  49.  
  50. errprep(offset, buf)
  51. unsigned short offset;
  52. char *buf;
  53. {
  54. register int pid = getpid();
  55.  
  56.     if (pid != ourpid) {
  57.         ourpid = pid;
  58.         if (strfile >= 0) {
  59.             close(strfile);
  60.             strfile = -1;
  61.         }
  62.     }
  63.     if (strfile < 0) {
  64.             char *p, *getenv();
  65.         if (p = getenv("KSTR"))
  66.           if (strlen(p))
  67.             StringFile = p;
  68.         strfile = open(StringFile, 0);
  69.         if (strfile < 0) {
  70. oops:
  71.             fprintf(stderr, "Cannot find %s\r\n", StringFile);
  72.             exit(EX_OSFILE);
  73.         }
  74.     }
  75.     if (lseek(strfile, (long) offset, 0) < 0
  76.             || read(strfile, buf, BUFLEN) <= 0)
  77.         goto oops;
  78. }
  79.  
  80. /* extracted string front end for printf() */
  81. /*VARARGS1*/
  82. strprerror(fmt, va_alist)
  83.     int fmt;
  84.     va_dcl
  85. {
  86.     va_list    ap;
  87.     char buf[BUFLEN];
  88.  
  89.     errprep(fmt, buf);
  90.     va_start(ap);
  91.     vprintf(buf, ap);
  92.     va_end(ap);
  93. }
  94.  
  95. /* extracted string front end for sprintf() */
  96. /*VARARGS1*/
  97. strsrerror(fmt, obuf, va_alist)
  98.     int fmt;
  99.     char *obuf;
  100.     va_dcl
  101. {
  102.     char buf[BUFLEN];
  103.     va_list    ap;
  104.  
  105.     errprep(fmt, buf);
  106.     va_start(ap);
  107.     vsprintf(obuf, buf, ap);
  108.     va_end(ap);
  109. }
  110.  
  111. /* extracted string front end for fprintf() */
  112. /*VARARGS1*/
  113. strfrerror(fmt, fd, va_alist)
  114.     int fmt;
  115.     FILE *fd;
  116.     va_dcl
  117. {
  118.     va_list    ap;
  119.     char buf[BUFLEN];
  120.  
  121.     errprep(fmt, buf);
  122.     va_start(ap);
  123.     vfprintf(fd, buf, ap);
  124.     va_end(ap);
  125. }
  126.  
  127. /* extracted string front end for perror() */
  128. strperror(fmt)
  129.     int fmt;
  130. {
  131.     char buf[BUFLEN];
  132.     register int saverr = errno;
  133.  
  134.     errprep(fmt, buf);
  135.     errno = saverr;
  136.     perror(buf);
  137. }
  138.  
  139. perror(str)
  140.     char    *str;
  141.     {
  142.  
  143.     printf("%s: errno %d\n", str, errno);
  144.     }
  145.  
  146. /*
  147.  * The following is needed _only_ on systems which do not have the C library
  148.  * stubs for the ctime() and getpw*() functions.  In 2.11BSD these are
  149.  * present in the libstubs.a library and accessed via "-lstubs" at link time.
  150.  *
  151.  * 2.10BSD's cpp has the BSD2_10 symbol builtin.  Other systems without 
  152.  * libstubs.a will need to define (via a -D option in CFLAGS) 'BSD2_10'.
  153. */
  154.  
  155. #ifdef    BSD2_10
  156.  
  157. #include <sys/types.h>
  158. #include <sys/time.h>
  159. #include <pwd.h>
  160. #include <utmp.h>
  161.  
  162. #define    SEND_FD    W[1]
  163. #define    RECV_FD    R[0]
  164.  
  165. #define    CTIME    1
  166. #define    ASCTIME    2
  167. #define    TZSET    3
  168. #define    LOCALTIME 4
  169. #define    GMTIME    5
  170. #define    OFFTIME    6
  171.  
  172. #define GETPWENT        7
  173. #define GETPWNAM        8
  174. #define GETPWUID        9
  175. #define SETPASSENT      10
  176. #define ENDPWENT        11
  177.  
  178.     static    int    R[2], W[2], inited;
  179.     static    char    result[256 + 4];
  180.     static    struct    tm    tmtmp;
  181.     static    struct    passwd    _pw, *getandfixpw();
  182.  
  183. char    *
  184. ctime(t)
  185.     time_t    *t;
  186.     {
  187.     u_char    fnc = CTIME;
  188.  
  189.     sewer();
  190.     write(SEND_FD, &fnc, sizeof fnc);
  191.     write(SEND_FD, t, sizeof (*t));
  192.     getb(RECV_FD, result, 26);
  193.     return(result);
  194.     }
  195.  
  196. char    *
  197. asctime(tp)
  198.     struct    tm    *tp;
  199.     {
  200.     u_char    fnc = ASCTIME;
  201.  
  202.     sewer();
  203.     write(SEND_FD, &fnc, sizeof fnc);
  204.     write(SEND_FD, tp, sizeof (*tp));
  205.     getb(RECV_FD, result, 26);
  206.     return(result);
  207.     }
  208.  
  209. void
  210. tzset()
  211.     {
  212.     u_char    fnc = TZSET;
  213.  
  214.     sewer();
  215.     write(SEND_FD, &fnc, sizeof fnc);
  216.     }
  217.  
  218. struct    tm *
  219. localtime(tp)
  220.     time_t    *tp;
  221.     {
  222.     u_char    fnc = LOCALTIME;
  223.  
  224.     sewer();
  225.     write(SEND_FD, &fnc, sizeof fnc);
  226.     write(SEND_FD, tp, sizeof (*tp));
  227.     getb(RECV_FD, &tmtmp, sizeof tmtmp);
  228.     getb(RECV_FD, result, 24);
  229.     tmtmp.tm_zone = result;
  230.     return(&tmtmp);
  231.     }
  232.  
  233. struct    tm *
  234. gmtime(tp)
  235.     time_t    *tp;
  236.     {
  237.     u_char    fnc = GMTIME;
  238.  
  239.     sewer();
  240.     write(SEND_FD, &fnc, sizeof fnc);
  241.     write(SEND_FD, tp, sizeof (*tp));
  242.     getb(RECV_FD, &tmtmp, sizeof tmtmp);
  243.     getb(RECV_FD, result, 24);
  244.     tmtmp.tm_zone = result;
  245.     return(&tmtmp);
  246.     }
  247.  
  248. struct    tm *
  249. offtime(clock, offset)
  250.     time_t    *clock;
  251.     long    offset;
  252.     {
  253.     u_char    fnc = OFFTIME;
  254.  
  255.     sewer();
  256.     write(SEND_FD, &fnc, sizeof fnc);
  257.     write(SEND_FD, clock, sizeof (*clock));
  258.     write(SEND_FD, &offset, sizeof offset);
  259.     getb(RECV_FD, &tmtmp, sizeof tmtmp);
  260.     tmtmp.tm_zone = "";
  261.     return(&tmtmp);
  262.     }
  263.  
  264. struct passwd *
  265. getpwent()
  266.     {
  267.     u_char    fnc = GETPWENT;
  268.  
  269.     sewer();
  270.     write(SEND_FD, &fnc, sizeof fnc);
  271.     return(getandfixpw());
  272.     }
  273.  
  274. struct    passwd *
  275. getpwnam(nam)
  276.     char    *nam;
  277.     {
  278.     u_char    fnc = GETPWNAM;
  279.     char    lnam[UT_NAMESIZE + 1];
  280.     int    len;
  281.  
  282.     len = strlen(nam);
  283.     if    (len > UT_NAMESIZE)
  284.         len = UT_NAMESIZE;
  285.     bcopy(nam, lnam, len);
  286.     lnam[len] = '\0';
  287.  
  288.     sewer();
  289.     write(SEND_FD, &fnc, 1);
  290.     write(SEND_FD, &len, sizeof (int));
  291.     write(SEND_FD, lnam, len);
  292.     return(getandfixpw());
  293.     }
  294.  
  295. struct    passwd    *
  296. getpwuid(uid)
  297.     uid_t    uid;
  298.     {
  299.     u_char    fnc = GETPWUID;
  300.  
  301.     sewer();
  302.     write(SEND_FD, &fnc, sizeof fnc);
  303.     write(SEND_FD, &uid, sizeof (uid_t));
  304.     return(getandfixpw());
  305.     }
  306.  
  307. setpwent()
  308.     {
  309.     return(setpassent(0));
  310.     }
  311.  
  312. setpassent(stayopen)
  313.     int    stayopen;
  314.     {
  315.     u_char    fnc = SETPASSENT;
  316.     int    sts;
  317.  
  318.     sewer();
  319.     write(SEND_FD, &fnc, sizeof fnc);
  320.     write(SEND_FD, &stayopen, sizeof (int));
  321.     getb(RECV_FD, &sts, sizeof (int));
  322.     return(sts);
  323.     }
  324.  
  325. void
  326. endpwent()
  327.     {
  328.     u_char    fnc = ENDPWENT;
  329.  
  330.     sewer();
  331.     write(SEND_FD, &fnc, sizeof fnc);
  332.     return;
  333.     }
  334.  
  335. /* setpwfile() is deprecated */
  336. void
  337. setpwfile(file)
  338.     char    *file;
  339.     {
  340.     return;
  341.     }
  342.  
  343. struct passwd *
  344. getandfixpw()
  345.     {
  346.     short    sz;
  347.  
  348.     getb(RECV_FD, &sz, sizeof (int));
  349.     if    (sz == 0)
  350.         return(NULL);
  351.     getb(RECV_FD, &_pw, sizeof (_pw));
  352.     getb(RECV_FD, result, sz);
  353.     _pw.pw_name += (int)result;
  354.     _pw.pw_passwd += (int)result;
  355.     _pw.pw_class += (int)result;
  356.     _pw.pw_gecos += (int)result;
  357.     _pw.pw_dir += (int)result;
  358.     _pw.pw_shell += (int)result;
  359.     return(&_pw);
  360.     }
  361.  
  362. getb(f, p, n)
  363.     register int f, n;
  364.     register char *p;
  365.     {
  366.     int    i;
  367.  
  368.     while    (n)
  369.         {
  370.         i = read(f, p, n);
  371.         if    (i <= 0)
  372.             return;
  373.         p += i;
  374.         n -= i;
  375.         }
  376.     }
  377.  
  378. sewer()
  379.     {
  380.     register int    pid, ourpid = getpid();
  381.  
  382.     if    (inited == ourpid)
  383.         return;
  384.     if    (inited)
  385.         {
  386.         close(SEND_FD);
  387.         close(RECV_FD);
  388.         }
  389.     pipe(W);
  390.     pipe(R);
  391.     pid = vfork();
  392.     if    (pid == 0)
  393.         {            /* child */
  394.         alarm(0);        /* cancel alarms */
  395.         dup2(W[0], 0);        /* parent write side to our stdin */
  396.         dup2(R[1], 1);        /* parent read side to our stdout */
  397.         close(SEND_FD);        /* copies made, close the... */
  398.         close(RECV_FD);        /* originals now */
  399.         execl(_PATH_CTIMED, "ctimed", 0);
  400.         _exit(EX_OSFILE);
  401.         }
  402.     if    (pid == -1)
  403.         abort();        /* nothing else really to do */
  404.     close(W[0]);            /* close read side of SEND channel */
  405.     close(R[1]);            /* close write side of RECV channel */
  406.     inited = ourpid;        /* don't do this again in this proc */
  407.     }
  408.  
  409. XXctime()
  410.     {
  411.  
  412.     if    (SEND_FD)
  413.         close(SEND_FD);
  414.     if    (RECV_FD)
  415.         close(RECV_FD);
  416.     SEND_FD = RECV_FD = 0;
  417.     inited = 0;
  418.     }
  419. #endif    /* BSD2_10 */
  420.