xref: /illumos-gate/usr/src/cmd/tnf/prex/expr.c (revision 7c478bd9)
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  * Copyright (c) 1994, by Sun Microsytems, Inc.
24  */
25 
26 #pragma ident	"%Z%%M%	%I%	%E% SMI"
27 
28 /*
29  * Includes
30  */
31 
32 /* we need to define this to get strtok_r from string.h */
33 /* SEEMS LIKE A BUG TO ME */
34 #define	_REENTRANT
35 
36 #ifndef DEBUG
37 #define	NDEBUG	1
38 #endif
39 
40 #include <stdio.h>
41 #include <stdlib.h>
42 #include <string.h>
43 #include <libgen.h>
44 #include <assert.h>
45 #include "spec.h"
46 #include "expr.h"
47 #include "new.h"
48 
49 
50 /*
51  * Typedefs
52  */
53 
54 typedef enum {
55 	MATCH_NONE = 0,
56 	MATCH_FALSE,
57 	MATCH_TRUE
58 
59 
60 }			   match_t;
61 
62 
63 /*
64  * Declarations
65  */
66 
67 static boolean_t matchattrs(expr_t * expr_p, const char *attrs);
68 static void matchvals(spec_t * spec_p, char *attrstr,
69 	char *valstr, void *calldatap);
70 static void matched(spec_t * spec_p, char *valstr, void *calldatap);
71 
72 
73 /* ---------------------------------------------------------------- */
74 /* ----------------------- Public Functions ----------------------- */
75 /* ---------------------------------------------------------------- */
76 
77 /*
78  * expr() - builds an expr
79  */
80 
81 expr_t		 *
expr(spec_t * left_p,spec_t * right_p)82 expr(spec_t * left_p,
83 	spec_t * right_p)
84 {
85 	expr_t		 *new_p;
86 
87 	new_p = new(expr_t);
88 	queue_init(&new_p->qn);
89 	new_p->left_p = left_p;
90 	new_p->right_p = right_p;
91 
92 	return (new_p);
93 
94 }				/* end expr */
95 
96 
97 /*
98  * expr_dup() - duplicates an expression list
99  */
100 
101 expr_t		 *
expr_dup(expr_t * list_p)102 expr_dup(expr_t * list_p)
103 {
104 	expr_t		 *expr_p;
105 	expr_t		 *head_p;
106 
107 	if (!list_p)
108 		return (NULL);
109 
110 	/* copy the first node */
111 	head_p = expr(spec_dup(list_p->left_p),
112 		spec_dup(list_p->right_p));
113 
114 	/* append each additional node */
115 	expr_p = list_p;
116 	while (expr_p = (expr_t *) queue_next(&list_p->qn, &expr_p->qn)) {
117 		expr_t		 *new_p;
118 
119 		new_p = expr(spec_dup(expr_p->left_p),
120 			spec_dup(expr_p->right_p));
121 		(void) queue_append(&head_p->qn, &new_p->qn);
122 	}
123 
124 	return (head_p);
125 
126 }				/* end expr_dup */
127 
128 
129 /*
130  * expr_destroy() - destroys an expression list
131  */
132 
133 void
expr_destroy(expr_t * list_p)134 expr_destroy(expr_t * list_p)
135 {
136 	expr_t		 *expr_p;
137 
138 	while (expr_p = (expr_t *) queue_next(&list_p->qn, &list_p->qn)) {
139 		(void) queue_remove(&expr_p->qn);
140 
141 		if (expr_p->left_p)
142 			spec_destroy(expr_p->left_p);
143 		if (expr_p->right_p)
144 			spec_destroy(expr_p->right_p);
145 		free(expr_p);
146 	}
147 
148 	if (list_p->left_p)
149 		spec_destroy(list_p->left_p);
150 	if (list_p->right_p)
151 		spec_destroy(list_p->right_p);
152 	free(list_p);
153 
154 }				/* end expr_destroy */
155 
156 
157 /*
158  * expr_list() - append a expr_t to a list
159  */
160 
161 expr_t		 *
expr_list(expr_t * h,expr_t * f)162 expr_list(expr_t * h,
163 	expr_t * f)
164 {
165 	/* queue append handles the NULL cases OK */
166 	return ((expr_t *) queue_append(&h->qn, &f->qn));
167 
168 }				/* end expr_list */
169 
170 
171 /*
172  * expr_print() - pretty prints an expr list
173  */
174 
175 void
expr_print(FILE * stream,expr_t * list_p)176 expr_print(FILE * stream,
177 	expr_t * list_p)
178 {
179 	expr_t		 *expr_p = NULL;
180 
181 	while ((expr_p = (expr_t *) queue_next(&list_p->qn, &expr_p->qn))) {
182 		spec_print(stream, expr_p->left_p);
183 		(void) fprintf(stream, "=");
184 		spec_print(stream, expr_p->right_p);
185 		(void) fprintf(stream, " ");
186 	}
187 
188 }				/* end expr_print */
189 
190 
191 /*
192  * expr_match() - figures out whether a probe matches in an expression list
193  */
194 
195 boolean_t
expr_match(expr_t * list_p,const char * attrs)196 expr_match(expr_t * list_p,
197 	const char *attrs)
198 {
199 	expr_t		 *expr_p = NULL;
200 
201 	while ((expr_p = (expr_t *) queue_next(&list_p->qn, &expr_p->qn))) {
202 		if (matchattrs(expr_p, attrs))
203 			return (B_TRUE);
204 	}
205 
206 	return (B_FALSE);
207 
208 }				/* end expr_match */
209 
210 
211 /* ---------------------------------------------------------------- */
212 /* ----------------------- Private Functions ---------------------- */
213 /* ---------------------------------------------------------------- */
214 
215 typedef struct matchargs {
216 	spec_t		 *spec_p;
217 	boolean_t	   match;
218 
219 }			   matchargs_t;
220 
221 static		  boolean_t
matchattrs(expr_t * expr_p,const char * attrs)222 matchattrs(expr_t * expr_p,
223 	const char *attrs)
224 {
225 	matchargs_t	 args;
226 
227 	args.spec_p = expr_p->right_p;
228 	args.match = B_FALSE;
229 
230 	spec_attrtrav(expr_p->left_p,
231 		(char *) attrs, matchvals, (void *) &args);
232 
233 	return (args.match);
234 
235 }				/* end matchattrs */
236 
237 
238 /*ARGSUSED*/
239 static void
matchvals(spec_t * spec_p,char * attrstr,char * valstr,void * calldatap)240 matchvals(spec_t * spec_p,
241 	char *attrstr,
242 	char *valstr,
243 	void *calldatap)
244 {
245 	matchargs_t	*args_p = (matchargs_t *) calldatap;
246 
247 	spec_valtrav(args_p->spec_p, valstr, matched, calldatap);
248 
249 }				/* matchvals */
250 
251 
252 /*ARGSUSED*/
253 static void
matched(spec_t * spec_p,char * valstr,void * calldatap)254 matched(spec_t * spec_p,
255 	char *valstr,
256 	void *calldatap)
257 {
258 	matchargs_t	*args_p = (matchargs_t *) calldatap;
259 
260 	args_p->match = B_TRUE;
261 
262 }				/* end matched */
263