1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License, Version 1.0 only
   6  * (the "License").  You may not use this file except in compliance
   7  * with the License.
   8  *
   9  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
  10  * or http://www.opensolaris.org/os/licensing.
  11  * See the License for the specific language governing permissions
  12  * and limitations under the License.
  13  *
  14  * When distributing Covered Code, include this CDDL HEADER in each
  15  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  16  * If applicable, add the following below this CDDL HEADER, with the
  17  * fields enclosed by brackets "[]" replaced with your own identifying
  18  * information: Portions Copyright [yyyy] [name of copyright owner]
  19  *
  20  * CDDL HEADER END
  21  */
  22 
  23 /*
  24  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
  25  * Use is subject to license terms.
  26  */
  27 
  28 /*      Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T     */
  29 /*        All Rights Reserved   */
  30 
  31 #pragma ident   "%Z%%M% %I%     %E% SMI"
  32 
  33 #define DEBUG
  34 #include "awk.h"
  35 #include "y.tab.h"
  36 
  37 Node *
  38 nodealloc(int n)
  39 {
  40         register Node *x;
  41 
  42         x = (Node *)malloc(sizeof (Node) + (n - 1) * sizeof (Node *));
  43         if (x == NULL)
  44                 ERROR "out of space in nodealloc" FATAL;
  45         x->nnext = NULL;
  46         x->lineno = lineno;
  47         return (x);
  48 }
  49 
  50 Node *
  51 exptostat(Node *a)
  52 {
  53         a->ntype = NSTAT;
  54         return (a);
  55 }
  56 
  57 Node *
  58 node1(int a, Node *b)
  59 {
  60         register Node *x;
  61 
  62         x = nodealloc(1);
  63         x->nobj = a;
  64         x->narg[0] = b;
  65         return (x);
  66 }
  67 
  68 Node *
  69 node2(int a, Node *b, Node *c)
  70 {
  71         register Node *x;
  72 
  73         x = nodealloc(2);
  74         x->nobj = a;
  75         x->narg[0] = b;
  76         x->narg[1] = c;
  77         return (x);
  78 }
  79 
  80 Node *
  81 node3(int a, Node *b, Node *c, Node *d)
  82 {
  83         register Node *x;
  84 
  85         x = nodealloc(3);
  86         x->nobj = a;
  87         x->narg[0] = b;
  88         x->narg[1] = c;
  89         x->narg[2] = d;
  90         return (x);
  91 }
  92 
  93 Node *
  94 node4(int a, Node *b, Node *c, Node *d, Node *e)
  95 {
  96         register Node *x;
  97         x = nodealloc(4);
  98         x->nobj = a;
  99         x->narg[0] = b;
 100         x->narg[1] = c;
 101         x->narg[2] = d;
 102         x->narg[3] = e;
 103         return (x);
 104 }
 105 
 106 Node *
 107 stat3(int a, Node *b, Node *c, Node *d)
 108 {
 109         register Node *x;
 110 
 111         x = node3(a, b, c, d);
 112         x->ntype = NSTAT;
 113         return (x);
 114 }
 115 
 116 Node *
 117 op2(int a, Node *b, Node *c)
 118 {
 119         register Node *x;
 120 
 121         x = node2(a, b, c);
 122         x->ntype = NEXPR;
 123         return (x);
 124 }
 125 
 126 Node *
 127 op1(int a, Node *b)
 128 {
 129         register Node *x;
 130 
 131         x = node1(a, b);
 132         x->ntype = NEXPR;
 133         return (x);
 134 }
 135 
 136 Node *
 137 stat1(int a, Node *b)
 138 {
 139         register Node *x;
 140 
 141         x = node1(a, b);
 142         x->ntype = NSTAT;
 143         return (x);
 144 }
 145 
 146 Node *
 147 op3(int a, Node *b, Node *c, Node *d)
 148 {
 149         register Node *x;
 150 
 151         x = node3(a, b, c, d);
 152         x->ntype = NEXPR;
 153         return (x);
 154 }
 155 
 156 Node *
 157 op4(int a, Node *b, Node *c, Node *d, Node *e)
 158 {
 159         register Node *x;
 160 
 161         x = node4(a, b, c, d, e);
 162         x->ntype = NEXPR;
 163         return (x);
 164 }
 165 
 166 Node *
 167 stat2(int a, Node *b, Node *c)
 168 {
 169         register Node *x;
 170 
 171         x = node2(a, b, c);
 172         x->ntype = NSTAT;
 173         return (x);
 174 }
 175 
 176 Node *
 177 stat4(int a, Node *b, Node *c, Node *d, Node *e)
 178 {
 179         register Node *x;
 180 
 181         x = node4(a, b, c, d, e);
 182         x->ntype = NSTAT;
 183         return (x);
 184 }
 185 
 186 Node *
 187 valtonode(Cell *a, int b)
 188 {
 189         register Node *x;
 190 
 191         a->ctype = OCELL;
 192         a->csub = b;
 193         x = node1(0, (Node *)a);
 194         x->ntype = NVALUE;
 195         return (x);
 196 }
 197 
 198 Node *
 199 rectonode(void)
 200 {
 201         /* return valtonode(lookup("$0", symtab), CFLD); */
 202         return (valtonode(recloc, CFLD));
 203 }
 204 
 205 Node *
 206 makearr(Node *p)
 207 {
 208         Cell *cp;
 209 
 210         if (isvalue(p)) {
 211                 cp = (Cell *)(p->narg[0]);
 212                 if (isfunc(cp))
 213                         ERROR "%s is a function, not an array", cp->nval SYNTAX;
 214                 else if (!isarr(cp)) {
 215                         xfree(cp->sval);
 216                         cp->sval = (uchar *)makesymtab(NSYMTAB);
 217                         cp->tval = ARR;
 218                 }
 219         }
 220         return (p);
 221 }
 222 
 223 Node *
 224 pa2stat(Node *a, Node *b, Node *c)
 225 {
 226         register Node *x;
 227 
 228         x = node4(PASTAT2, a, b, c, (Node *)paircnt);
 229         paircnt++;
 230         x->ntype = NSTAT;
 231         return (x);
 232 }
 233 
 234 Node *
 235 linkum(Node *a, Node *b)
 236 {
 237         register Node *c;
 238 
 239         if (errorflag)  /* don't link things that are wrong */
 240                 return (a);
 241         if (a == NULL)
 242                 return (b);
 243         else if (b == NULL)
 244                 return (a);
 245         for (c = a; c->nnext != NULL; c = c->nnext)
 246                 ;
 247         c->nnext = b;
 248         return (a);
 249 }
 250 
 251 void
 252 defn(Cell *v, Node *vl, Node *st)       /* turn on FCN bit in definition */
 253 {
 254         Node *p;
 255         int n;
 256 
 257         if (isarr(v)) {
 258                 ERROR "`%s' is an array name and a function name",
 259                     v->nval SYNTAX;
 260                 return;
 261         }
 262         v->tval = FCN;
 263         v->sval = (uchar *)st;
 264         n = 0;  /* count arguments */
 265         for (p = vl; p; p = p->nnext)
 266                 n++;
 267         v->fval = n;
 268         dprintf(("defining func %s (%d args)\n", v->nval, n));
 269 }
 270 
 271 int
 272 isarg(uchar *s) /* is s in argument list for current function? */
 273 {
 274         extern Node *arglist;
 275         Node *p = arglist;
 276         int n;
 277 
 278         for (n = 0; p != 0; p = p->nnext, n++) {
 279                 if (strcmp((char *)((Cell *)(p->narg[0]))->nval,
 280                     (char *)s) == 0) {
 281                         return (n);
 282                 }
 283         }
 284         return (-1);
 285 }