home *** CD-ROM | disk | FTP | other *** search
/ Serving the Web / ServingTheWeb1995.disc1of1.iso / linux / slacksrce / d / libc / libc-4.6 / libc-4 / libc-linux / nls / gencat.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-10-24  |  7.1 KB  |  260 lines

  1.  
  2. /***********************************************************
  3. Copyright 1990, by Alfalfa Software Incorporated, Cambridge, Massachusetts.
  4.  
  5.                         All Rights Reserved
  6.  
  7. Permission to use, copy, modify, and distribute this software and its
  8. documentation for any purpose and without fee is hereby granted,
  9. provided that the above copyright notice appear in all copies and that
  10. both that copyright notice and this permission notice appear in
  11. supporting documentation, and that Alfalfa's name not be used in
  12. advertising or publicity pertaining to distribution of the software
  13. without specific, written prior permission.
  14.  
  15. ALPHALPHA DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
  16. ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
  17. ALPHALPHA BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
  18. ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
  19. WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
  20. ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
  21. SOFTWARE.
  22.  
  23. If you make any modifications, bugfixes or other changes to this software
  24. we'd appreciate it if you could send a copy to us so we can keep things
  25. up-to-date.  Many thanks.
  26.                 Kee Hinckley
  27.                 Alfalfa Software, Inc.
  28.                 267 Allston St., #3
  29.                 Cambridge, MA 02139  USA
  30.                 nazgul@alfalfa.com
  31.     
  32. ******************************************************************/
  33.  
  34. /* Edit History
  35.  
  36. 01/18/91   3 hamilton    #if not reparsed
  37. 01/12/91   2 schulert    conditionally use prototypes
  38. 12/23/90   2 hamilton    Fix fd == NULL to fd < 0
  39. 11/03/90   1 hamilton    Alphalpha->Alfalfa & OmegaMail->Poste
  40. 08/13/90   1 schulert    move from ua to omu
  41. */
  42.  
  43. #include <stdio.h>
  44. #include <sys/types.h>
  45. #ifdef SYSV
  46. #include <sys/fcntl.h>
  47. #include <string.h>
  48. #else
  49. #include <strings.h>
  50. #endif
  51. #include <sys/file.h>
  52. #include <sys/stat.h>
  53. #include "gencat.h"
  54.  
  55. #ifndef L_SET
  56. #define L_SET SEEK_SET
  57. #endif
  58.  
  59. #ifndef L_INCR
  60. #define L_INCR SEEK_CUR
  61. #endif
  62.  
  63. /*
  64.  * The spec says the syntax is "gencat catfile msgfile...".
  65.  * We extend it to:
  66.  *     gencat [-new] [-or] [-lang C|C++|ANSIC] catfile msgfile
  67.  *           [-h <header-file>]...
  68.  * Flags are order dependant, we'll take whatever lang was most recently chosen
  69.  * and use it to generate the next header file.  The header files are generated
  70.  * at the point in the command line they are listed.  Thus the sequence:
  71.  *    gencat -lang C foo.cat foo.mcs -h foo.h -lang C++ bar.mcs -h bar.H
  72.  * will put constants from foo.mcs into foo.h and constants from bar.mcs into
  73.  * bar.h.  Constants are not saved in the catalog file, so nothing will come
  74.  * from that, even if things have been defined before.  The constants in foo.h
  75.  * will be in C syntax, in bar.H in C++ syntax.
  76.  */
  77.  
  78. static void writeIfChanged(
  79. #if defined(__STDC__) || defined(__cplusplus)
  80.         char *fname, int lang, int orConsts
  81. #endif
  82. );
  83.  
  84. void usage() {
  85.     fprintf(stderr, "Use: gencat [-new] [-or] [-lang C|C++|ANSIC] catfile msgfile [-h <header-file>]...\n");
  86. }
  87.  
  88. void main(
  89. #if defined(__STDC__) || defined(__cplusplus)
  90.         int argc, char *argv[])
  91. #else
  92.         argc, argv)
  93. int argc;
  94. char *argv[];
  95. #endif
  96. {
  97.     int        ofd, ifd, i;
  98.     FILE    *fptr;
  99.     char    *catfile = NULL;
  100.     char    *input = NULL;
  101.     int        lang = MCLangC;
  102.     int        new = False;
  103.     int        orConsts = False;
  104.     
  105.     for (i = 1; i < argc; ++i) {
  106.     if (argv[i][0] == '-') {
  107.         if (strcmp(argv[i], "-lang") == 0) {
  108.         ++i;
  109.         if (strcmp(argv[i], "C") == 0) lang = MCLangC;
  110.         else if (strcmp(argv[i], "C++") == 0) lang = MCLangCPlusPlus;
  111.         else if (strcmp(argv[i], "ANSIC") == 0) lang = MCLangANSIC;
  112.         else {
  113.             fprintf(stderr, "gencat: Unrecognized language: %s\n", argv[i]);
  114.             exit(1);
  115.         } 
  116.         } else if (strncmp(argv[i], "-h", 2) == 0) {
  117.         if (!input) {
  118.             fprintf(stderr, "gencat: Can't write to a header before reading something.\n");
  119.             exit(1);
  120.         }
  121.         ++i;
  122.         writeIfChanged(argv[i], lang, orConsts);
  123.         } else if (strncmp(argv[i], "-new", 4) == 0) {
  124.         if (catfile) {
  125.             fprintf(stderr, "gencat: You must specify -new before the catalog file name\n");
  126.             exit(1);
  127.         }
  128.         new = True;
  129.         } else if (strncmp(argv[i], "-or", 3) == 0) {
  130.         orConsts = ~orConsts;
  131.         } else {
  132.         usage();
  133.         exit(1);
  134.         }
  135.         } else {
  136.         if (!catfile) {
  137.         catfile = argv[i];
  138.         if (new) {
  139.             if ((ofd = open(catfile, O_WRONLY|O_TRUNC|O_CREAT, 0666)) < 0) {
  140.             fprintf(stderr, "gencat: Unable to create a new %s.\n", catfile);
  141.             exit(1);
  142.             }
  143.         } else if ((ofd = open(catfile, O_RDONLY)) < 0) {
  144.             if ((ofd = open(catfile, O_WRONLY|O_CREAT, 0666)) < 0) {
  145.             fprintf(stderr, "gencat: Unable to create %s.\n", catfile);
  146.             exit(1);
  147.             }
  148.         } else {
  149.             MCReadCat(ofd);
  150.             close(ofd);
  151.             if ((ofd = open(catfile, O_WRONLY|O_TRUNC)) < 0) {
  152.             fprintf(stderr, "gencat: Unable to truncate %s.\n", catfile);
  153.             exit(1);
  154.             }
  155.         }
  156.         } else {
  157.         input = argv[i];
  158.         if ((ifd = open(input, O_RDONLY)) < 0) {
  159.             fprintf(stderr, "gencat: Unable to read %s\n", input);
  160.             exit(1);
  161.         }
  162.         MCParse(ifd);
  163.         close(ifd);
  164.         }
  165.     }
  166.     }
  167.     if (catfile) {
  168.     MCWriteCat(ofd);
  169.     exit(0);
  170.     } else {
  171.     usage();
  172.     exit(1);
  173.     }
  174. }
  175.  
  176. static void writeIfChanged(
  177. #if defined(__STDC__) || defined(__cplusplus)
  178.         char *fname, int lang, int orConsts)
  179. #else
  180.         fname, lang, orConsts)
  181. char *fname;
  182. int lang;
  183. int orConsts;
  184. #endif
  185. {
  186.     char    tmpname[32];
  187.     char    buf[BUFSIZ], tbuf[BUFSIZ], *cptr, *tptr;
  188.     int        fd, tfd;
  189.     int        diff = False;
  190.     int        c, len, tlen;
  191.     struct stat    sbuf;
  192.  
  193.     /* If it doesn't exist, just create it */
  194.     if (stat(fname, &sbuf)) {
  195.     if ((fd = open(fname, O_WRONLY|O_CREAT, 0666)) < 0) {
  196.         fprintf(stderr, "gencat: Unable to create header file %s.\n", fname);
  197.         exit(1);
  198.     }
  199.     MCWriteConst(fd, lang, orConsts);
  200.     close(fd);
  201.     return;
  202.     }
  203.  
  204.     /* If it does exist, create a temp file for now */
  205.     sprintf(tmpname, "/tmp/gencat.%d", (int) getpid());
  206.     if ((tfd = open(tmpname, O_RDWR|O_CREAT, 0666)) < 0) {
  207.     fprintf(stderr, "gencat: Unable to open temporary file: %s\n", tmpname);
  208.     exit(1);
  209.     }
  210.     unlink(tmpname);
  211.  
  212.     /* Write to the temp file and rewind */
  213.     MCWriteConst(tfd, lang, orConsts);
  214.  
  215.     /* Open the real header file */
  216.     if ((fd = open(fname, O_RDONLY)) < 0) {
  217.     fprintf(stderr, "gencat: Unable to read header file: %s\n", fname);
  218.     exit(1);
  219.     }
  220.  
  221.     /* Backup to the start of the temp file */
  222.     if (lseek(tfd, 0L, L_SET) < 0) {
  223.     fprintf(stderr, "gencat: Unable to seek in tempfile: %s\n", tmpname);
  224.     exit(1);
  225.     }
  226.  
  227.     /* Now compare them */
  228.     while ((tlen = read(tfd, tbuf, BUFSIZ)) > 0) {
  229.     if ((len = read(fd, buf, BUFSIZ)) != tlen) {
  230.         diff = True;
  231.         goto done;
  232.     }
  233.     for (cptr = buf, tptr = tbuf; cptr < buf+len; ++cptr, ++tptr) {
  234.         if (*tptr != *cptr) {
  235.         diff = True;
  236.         goto done;
  237.         }
  238.     }
  239.     }
  240. done:    
  241.     if (diff) {
  242.     if (lseek(tfd, 0L, L_SET) < 0) {
  243.         fprintf(stderr, "gencat: Unable to seek in tempfile: %s\n", tmpname);
  244.         exit(1);
  245.     }
  246.     close(fd);
  247.     if ((fd = open(fname, O_WRONLY|O_TRUNC)) < 0) {
  248.         fprintf(stderr, "gencat: Unable to truncate header file: %s\n", fname);
  249.         exit(1);
  250.     }
  251.     while ((len = read(tfd, buf, BUFSIZ)) > 0) {
  252.         if (write(fd, buf, len) != len) {
  253.         fprintf(stderr, "gencat: Error writing to header file: %s\n", fname);
  254.         }
  255.     }
  256.     }
  257.     close(fd);
  258.     close(tfd);
  259. }
  260.