db_expr.c revision 1.2 1 /*
2 * Mach Operating System
3 * Copyright (c) 1991,1990 Carnegie Mellon University
4 * All Rights Reserved.
5 *
6 * Permission to use, copy, modify and distribute this software and its
7 * documentation is hereby granted, provided that both the copyright
8 * notice and this permission notice appear in all copies of the
9 * software, derivative works or modified versions, and any portions
10 * thereof, and that both notices appear in supporting documentation.
11 *
12 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
13 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
14 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
15 *
16 * Carnegie Mellon requests users of this software to return to
17 *
18 * Software Distribution Coordinator or Software.Distribution (at) CS.CMU.EDU
19 * School of Computer Science
20 * Carnegie Mellon University
21 * Pittsburgh PA 15213-3890
22 *
23 * any improvements or extensions that they make and grant Carnegie the
24 * rights to redistribute these changes.
25 */
26 /*
27 * $Id: db_expr.c,v 1.2 1993/05/20 03:39:13 cgd Exp $
28 *
29 * HISTORY
30 * $Log: db_expr.c,v $
31 * Revision 1.2 1993/05/20 03:39:13 cgd
32 * add explicit rcs id
33 *
34 * Revision 1.1.1.1 1993/03/21 09:46:26 cgd
35 * initial import of 386bsd-0.1 sources
36 *
37 * Revision 1.1 1992/03/25 21:45:09 pace
38 * Initial revision
39 *
40 * Revision 2.3 91/02/05 17:06:25 mrt
41 * Changed to new Mach copyright
42 * [91/01/31 16:17:46 mrt]
43 *
44 * Revision 2.2 90/08/27 21:50:57 dbg
45 * Use '..' instead of '$$' for db_prev.
46 * Use '+' for db_next.
47 * [90/08/22 dbg]
48 *
49 * Allow repeated unary operators.
50 * [90/08/20 dbg]
51 *
52 * Reflected back rename of db_symbol_value->db_value_of_name
53 * [90/08/20 af]
54 * Reduce lint.
55 * [90/08/07 dbg]
56 * Created.
57 * [90/07/25 dbg]
58 *
59 */
60 /*
61 * Author: David B. Golub, Carnegie Mellon University
62 * Date: 7/90
63 */
64 #include "param.h"
65 #include "proc.h"
66 #include <machine/db_machdep.h>
67 #include <ddb/db_lex.h>
68 #include <ddb/db_access.h>
69 #include <ddb/db_command.h>
70
71 boolean_t
72 db_term(valuep)
73 db_expr_t *valuep;
74 {
75 int t;
76
77 t = db_read_token();
78 if (t == tIDENT) {
79 if (!db_value_of_name(db_tok_string, valuep)) {
80 db_error("Symbol not found\n");
81 /*NOTREACHED*/
82 }
83 return (TRUE);
84 }
85 if (t == tNUMBER) {
86 *valuep = (db_expr_t)db_tok_number;
87 return (TRUE);
88 }
89 if (t == tDOT) {
90 *valuep = (db_expr_t)db_dot;
91 return (TRUE);
92 }
93 if (t == tDOTDOT) {
94 *valuep = (db_expr_t)db_prev;
95 return (TRUE);
96 }
97 if (t == tPLUS) {
98 *valuep = (db_expr_t) db_next;
99 return (TRUE);
100 }
101 if (t == tDITTO) {
102 *valuep = (db_expr_t)db_last_addr;
103 return (TRUE);
104 }
105 if (t == tDOLLAR) {
106 if (!db_get_variable(valuep))
107 return (FALSE);
108 return (TRUE);
109 }
110 if (t == tLPAREN) {
111 if (!db_expression(valuep)) {
112 db_error("Syntax error\n");
113 /*NOTREACHED*/
114 }
115 t = db_read_token();
116 if (t != tRPAREN) {
117 db_error("Syntax error\n");
118 /*NOTREACHED*/
119 }
120 return (TRUE);
121 }
122 db_unread_token(t);
123 return (FALSE);
124 }
125
126 boolean_t
127 db_unary(valuep)
128 db_expr_t *valuep;
129 {
130 int t;
131
132 t = db_read_token();
133 if (t == tMINUS) {
134 if (!db_unary(valuep)) {
135 db_error("Syntax error\n");
136 /*NOTREACHED*/
137 }
138 *valuep = -*valuep;
139 return (TRUE);
140 }
141 if (t == tSTAR) {
142 /* indirection */
143 if (!db_unary(valuep)) {
144 db_error("Syntax error\n");
145 /*NOTREACHED*/
146 }
147 *valuep = db_get_value((db_addr_t)*valuep, sizeof(int), FALSE);
148 return (TRUE);
149 }
150 db_unread_token(t);
151 return (db_term(valuep));
152 }
153
154 boolean_t
155 db_mult_expr(valuep)
156 db_expr_t *valuep;
157 {
158 db_expr_t lhs, rhs;
159 int t;
160
161 if (!db_unary(&lhs))
162 return (FALSE);
163
164 t = db_read_token();
165 while (t == tSTAR || t == tSLASH || t == tPCT || t == tHASH) {
166 if (!db_term(&rhs)) {
167 db_error("Syntax error\n");
168 /*NOTREACHED*/
169 }
170 if (t == tSTAR)
171 lhs *= rhs;
172 else {
173 if (rhs == 0) {
174 db_error("Divide by 0\n");
175 /*NOTREACHED*/
176 }
177 if (t == tSLASH)
178 lhs /= rhs;
179 else if (t == tPCT)
180 lhs %= rhs;
181 else
182 lhs = ((lhs+rhs-1)/rhs)*rhs;
183 }
184 t = db_read_token();
185 }
186 db_unread_token(t);
187 *valuep = lhs;
188 return (TRUE);
189 }
190
191 boolean_t
192 db_add_expr(valuep)
193 db_expr_t *valuep;
194 {
195 db_expr_t lhs, rhs;
196 int t;
197
198 if (!db_mult_expr(&lhs))
199 return (FALSE);
200
201 t = db_read_token();
202 while (t == tPLUS || t == tMINUS) {
203 if (!db_mult_expr(&rhs)) {
204 db_error("Syntax error\n");
205 /*NOTREACHED*/
206 }
207 if (t == tPLUS)
208 lhs += rhs;
209 else
210 lhs -= rhs;
211 t = db_read_token();
212 }
213 db_unread_token(t);
214 *valuep = lhs;
215 return (TRUE);
216 }
217
218 boolean_t
219 db_shift_expr(valuep)
220 db_expr_t *valuep;
221 {
222 db_expr_t lhs, rhs;
223 int t;
224
225 if (!db_add_expr(&lhs))
226 return (FALSE);
227
228 t = db_read_token();
229 while (t == tSHIFT_L || t == tSHIFT_R) {
230 if (!db_add_expr(&rhs)) {
231 db_error("Syntax error\n");
232 /*NOTREACHED*/
233 }
234 if (rhs < 0) {
235 db_error("Negative shift amount\n");
236 /*NOTREACHED*/
237 }
238 if (t == tSHIFT_L)
239 lhs <<= rhs;
240 else {
241 /* Shift right is unsigned */
242 lhs = (unsigned) lhs >> rhs;
243 }
244 t = db_read_token();
245 }
246 db_unread_token(t);
247 *valuep = lhs;
248 return (TRUE);
249 }
250
251 int
252 db_expression(valuep)
253 db_expr_t *valuep;
254 {
255 return (db_shift_expr(valuep));
256 }
257