1: #ifndef lint
2: static char sccsid[] = "@(#)parser5.c 3.9 4/24/85";
3: #endif
4:
5: /*
6: * Copyright (c) 1983 Regents of the University of California,
7: * All rights reserved. Redistribution permitted subject to
8: * the terms of the Berkeley Software License Agreement.
9: */
10:
11: #include "parser.h"
12: #include "var.h"
13:
14: /*
15: * unary $ $? + - ! ~
16: */
17: p_expr11(v, flag)
18: register struct value *v;
19: char flag;
20: {
21: int op;
22: char *opname;
23:
24: switch (token) {
25: case T_DOLLAR:
26: opname = "$";
27: break;
28: case T_DQ:
29: opname = "$?";
30: break;
31: case T_PLUS:
32: opname = "unary +";
33: break;
34: case T_MINUS:
35: opname = "unary -";
36: break;
37: case T_NOT:
38: opname = "!";
39: break;
40: case T_COMP:
41: opname = "~";
42: break;
43: default:
44: return p_expr12(v, flag);
45: }
46: op = token;
47: (void) s_gettok();
48: if (p_expr11(v, flag) < 0)
49: return -1;
50: switch (v->v_type) {
51: case V_NUM:
52: break;
53: case V_STR:
54: switch (op) {
55: case T_MINUS:
56: case T_NOT:
57: case T_COMP:
58: p_error("%s: Numeric operand required.", opname);
59: str_free(v->v_str);
60: v->v_type = V_ERR;
61: return 0;
62: }
63: break;
64: case V_ERR:
65: return 0;
66: }
67: switch (op) {
68: case T_DOLLAR:
69: case T_DQ:
70: if (v->v_type == V_NUM) {
71: int tmp = cx.x_type == X_BUF && cx.x_arg != 0 &&
72: v->v_num > 0 && v->v_num <= cx.x_narg;
73: if (op == T_DQ)
74: v->v_num = tmp;
75: else if (tmp)
76: *v = cx.x_arg[v->v_num - 1];
77: else {
78: p_error("%d: No such argument.", v->v_num);
79: v->v_type = V_ERR;
80: }
81: } else {
82: char *name = v->v_str;
83: struct var *r = var_lookup(name);
84: if (op == T_DQ) {
85: v->v_type = V_NUM;
86: v->v_num = r != 0;
87: } else if (r != 0)
88: *v = r->r_val;
89: else {
90: p_error("%s: Undefined variable.", name);
91: v->v_type = V_ERR;
92: }
93: str_free(name);
94: }
95: if (v->v_type == V_STR && (v->v_str = str_cpy(v->v_str)) == 0) {
96: p_memerror();
97: return -1;
98: }
99: break;
100: case T_MINUS:
101: v->v_num = - v->v_num;
102: break;
103: case T_NOT:
104: v->v_num = ! v->v_num;
105: break;
106: case T_COMP:
107: v->v_num = ~ v->v_num;
108: break;
109: }
110: return 0;
111: }
112:
113: /*
114: * string, number, ( expr )
115: * Plus function calls.
116: *
117: * Always return v_type == V_ERR when flag == 0.
118: */
119: p_expr12(v, flag)
120: register struct value *v;
121: char flag;
122: {
123: v->v_type = V_ERR;
124: switch (token) {
125: case T_NUM:
126: if (flag) {
127: v->v_type = V_NUM;
128: v->v_num = token_num;
129: }
130: (void) s_gettok();
131: break;
132: case T_STR:
133: if (flag) {
134: v->v_type = V_STR;
135: v->v_str = token_str;
136: } else
137: str_free(token_str);
138: (void) s_gettok();
139: break;
140: case T_LP:
141: (void) s_gettok();
142: if (p_expr(v, flag) < 0) {
143: p_synerror();
144: return -1;
145: }
146: if (token != T_RP) {
147: p_synerror();
148: val_free(*v);
149: return -1;
150: }
151: (void) s_gettok();
152: break;
153: default:
154: return -1;
155: }
156: while (token == T_LP) {
157: char *cmd;
158:
159: if (p_convstr(v) < 0)
160: return -1;
161: cmd = v->v_type == V_STR ? v->v_str : 0;
162: if (p_function(cmd, v, flag) < 0) {
163: if (cmd)
164: str_free(cmd);
165: return -1;
166: }
167: if (cmd)
168: str_free(cmd);
169: }
170: return 0;
171: }
Defined functions
Defined variables
sccsid
defined in line
2;
never used