home *** CD-ROM | disk | FTP | other *** search
/ minnie.tuhs.org / unixen.tar / unixen / PDP-11 / Trees / V7 / usr / src / cmd / awk / tran.c < prev   
Encoding:
C/C++ Source or Header  |  1979-05-06  |  5.2 KB  |  242 lines

  1. #include "stdio.h"
  2. #include "awk.def"
  3. #include "awk.h"
  4.  
  5. cell *symtab[MAXSYM];    /* symbol table pointers */
  6.  
  7. char    **FS;    /* initial field sep */
  8. char    **RS;    /* initial record sep */
  9. char    **OFS;    /* output field sep */
  10. char    **ORS;    /* output record sep */
  11. char    **OFMT;    /*output format for numbers*/
  12. awkfloat *NF;    /* number of fields in current record */
  13. awkfloat *NR;    /* number of current record */
  14. char    **FILENAME;    /* current filename argument */
  15.  
  16. cell    *recloc;    /* location of record */
  17. cell    *nrloc;        /* NR */
  18. cell    *nfloc;        /* NF */
  19.  
  20. syminit()
  21. {
  22.     setsymtab("0", tostring("0"), 0.0, NUM|STR|CON|FLD, symtab);
  23.     recloc = setsymtab("$record", record, 0.0, STR|FLD, symtab);
  24.     dprintf("recloc %o lookup %o\n", recloc, lookup("$record", symtab), NULL);
  25.     FS = &setsymtab("FS", tostring(" "), 0.0, STR|FLD, symtab)->sval;
  26.     RS = &setsymtab("RS", tostring("\n"), 0.0, STR|FLD, symtab)->sval;
  27.     OFS = &setsymtab("OFS", tostring(" "), 0.0, STR|FLD, symtab)->sval;
  28.     ORS = &setsymtab("ORS", tostring("\n"), 0.0, STR|FLD, symtab)->sval;
  29.     OFMT = &setsymtab("OFMT", tostring("%.6g"), 0.0, STR|FLD, symtab)->sval;
  30.     FILENAME = &setsymtab("FILENAME", NULL, 0.0, STR|FLD, symtab)->sval;
  31.     nfloc = setsymtab("NF", NULL, 0.0, NUM, symtab);
  32.     NF = &nfloc->fval;
  33.     nrloc = setsymtab("NR", NULL, 0.0, NUM, symtab);
  34.     NR = &nrloc->fval;
  35. }
  36.  
  37. cell **makesymtab()
  38. {
  39.     int i;
  40.     cell **cp;
  41.  
  42.     cp = (char *) malloc(MAXSYM * sizeof(cell *));
  43.     if (cp == NULL)
  44.         error(FATAL, "out of space in makesymtab");
  45.     for (i = 0; i < MAXSYM; i++)
  46.         *((cell **) cp + i) = 0;
  47.     return(cp);
  48. }
  49.  
  50. freesymtab(ap)    /* free symbol table */
  51. cell *ap;
  52. {
  53.     cell *cp, **tp;
  54.     int i;
  55.  
  56.     if (!(ap->tval & ARR))
  57.         return;
  58.     tp = (cell **) ap->sval;
  59.     for (i = 0; i < MAXSYM; i++) {
  60.         for (cp = tp[i]; cp != NULL; cp = cp->nextval) {
  61.             xfree(cp->nval);
  62.             xfree(cp->sval);
  63.             free(cp);
  64.         }
  65.     }
  66.     xfree(tp);
  67. }
  68.  
  69. cell *setsymtab(n, s, f, t, tab)
  70. char *n, *s;
  71. awkfloat f;
  72. unsigned t;
  73. cell **tab;
  74. {
  75.     register h;
  76.     register cell *p;
  77.     cell *lookup();
  78.  
  79.     if (n != NULL && (p = lookup(n, tab)) != NULL) {
  80.         xfree(s);
  81.         dprintf("setsymtab found %o: %s", p, p->nval, NULL);
  82.         dprintf(" %s %g %o\n", p->sval, p->fval, p->tval);
  83.         return(p);
  84.     }
  85.     p = (cell *) malloc(sizeof(cell));
  86.     if (p == NULL)
  87.         error(FATAL, "symbol table overflow at %s", n);
  88.     p->nval = tostring(n);
  89.     p->sval = s;
  90.     p->fval = f;
  91.     p->tval = t;
  92.     h = hash(n);
  93.     p->nextval = tab[h];
  94.     tab[h] = p;
  95.     dprintf("setsymtab set %o: %s", p, p->nval, NULL);
  96.     dprintf(" %s %g %o\n", p->sval, p->fval, p->tval);
  97.     return(p);
  98. }
  99.  
  100. hash(s)    /* form hash value for string s */
  101. register char *s;
  102. {
  103.     register int hashval;
  104.  
  105.     for (hashval = 0; *s != '\0'; )
  106.         hashval += *s++;
  107.     return(hashval % MAXSYM);
  108. }
  109.  
  110. cell *lookup(s, tab)    /* look for s in tab */
  111. register char *s;
  112. cell **tab;
  113. {
  114.     register cell *p;
  115.  
  116.     for (p = tab[hash(s)]; p != NULL; p = p->nextval)
  117.         if (strcmp(s, p->nval) == 0)
  118.             return(p);    /* found it */
  119.     return(NULL);    /* not found */
  120. }
  121.  
  122. awkfloat setfval(vp, f)
  123. register cell *vp;
  124. awkfloat f;
  125. {
  126.     dprintf("setfval: %o %g\n", vp, f, NULL);
  127.     checkval(vp);
  128.     if (vp == recloc)
  129.         error(FATAL, "can't set $0");
  130.     vp->tval &= ~STR;    /* mark string invalid */
  131.     vp->tval |= NUM;    /* mark number ok */
  132.     if ((vp->tval & FLD) && vp->nval == 0)
  133.         donerec = 0;
  134.     return(vp->fval = f);
  135. }
  136.  
  137. char *setsval(vp, s)
  138. register cell *vp;
  139. char *s;
  140. {
  141.     dprintf("setsval: %o %s\n", vp, s, NULL);
  142.     checkval(vp);
  143.     if (vp == recloc)
  144.         error(FATAL, "can't set $0");
  145.     vp->tval &= ~NUM;
  146.     vp->tval |= STR;
  147.     if ((vp->tval & FLD) && vp->nval == 0)
  148.         donerec = 0;
  149.     if (!(vp->tval&FLD))
  150.         xfree(vp->sval);
  151.     vp->tval &= ~FLD;
  152.     return(vp->sval = tostring(s));
  153. }
  154.  
  155. awkfloat getfval(vp)
  156. register cell *vp;
  157. {
  158.     awkfloat atof();
  159.  
  160.     if (vp->sval == record && donerec == 0)
  161.         recbld();
  162.     dprintf("getfval: %o", vp, NULL, NULL);
  163.     checkval(vp);
  164.     if ((vp->tval & NUM) == 0) {
  165.         /* the problem is to make non-numeric things */
  166.         /* have unlikely numeric variables, so that */
  167.         /* $1 == $2 comparisons sort of make sense when */
  168.         /* one or the other is numeric */
  169.         if (isnumber(vp->sval)) {
  170.             vp->fval = atof(vp->sval);
  171.             if (!(vp->tval & CON))    /* don't change type of a constant */
  172.                 vp->tval |= NUM;
  173.         }
  174.         else
  175.             vp->fval = 0.0;    /* not a very good idea */
  176.     }
  177.     dprintf("  %g\n", vp->fval, NULL, NULL);
  178.     return(vp->fval);
  179. }
  180.  
  181. char *getsval(vp)
  182. register cell *vp;
  183. {
  184.     char s[100];
  185.  
  186.     if (vp->sval == record && donerec == 0)
  187.         recbld();
  188.     dprintf("getsval: %o", vp, NULL, NULL);
  189.     checkval(vp);
  190.     if ((vp->tval & STR) == 0) {
  191.         if (!(vp->tval&FLD))
  192.             xfree(vp->sval);
  193.         if ((long)vp->fval==vp->fval)
  194.             sprintf(s, "%.20g", vp->fval);
  195.         else
  196.             sprintf(s, *OFMT, vp->fval);
  197.         vp->sval = tostring(s);
  198.         vp->tval &= ~FLD;
  199.         vp->tval |= STR;
  200.     }
  201.     dprintf("  %s\n", vp->sval, NULL, NULL);
  202.     return(vp->sval);
  203. }
  204.  
  205. checkval(vp)
  206. register cell *vp;
  207. {
  208.     if (vp->tval & ARR)
  209.         error(FATAL, "illegal reference to array %s", vp->nval);
  210.     if ((vp->tval & (NUM | STR)) == 0)
  211.         error(FATAL, "funny variable %o: %s %s %g %o", vp, vp->nval,
  212.             vp->sval, vp->fval, vp->tval);
  213. }
  214.  
  215. char *tostring(s)
  216. register char *s;
  217. {
  218.     register char *p;
  219.  
  220.     p = malloc(strlen(s)+1);
  221.     if (p == NULL)
  222.         error(FATAL, "out of space in tostring on %s", s);
  223.     strcpy(p, s);
  224.     return(p);
  225. }
  226. #ifndef yfree
  227. yfree(a) char *a;
  228. {
  229.     printf("%o\n", a);
  230.     free(a);
  231. }
  232. #endif
  233. #ifdef malloc
  234. #undef malloc
  235. char *ymalloc(u) unsigned u;
  236. {    char *p;
  237.     p = malloc(u);
  238.     printf("%o %o\n", u, p);
  239.     return(p);
  240. }
  241. #endif
  242.