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 (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
24 * Copyright (c) 2015, Joyent Inc. All rights reserved.
25 * Copyright (c) 2012, 2016 by Delphix. All rights reserved.
26 */
27
28/*
29 * DTrace D Language Parser
30 *
31 * The D Parser is a lex/yacc parser consisting of the lexer dt_lex.l, the
32 * parsing grammar dt_grammar.y, and this file, dt_parser.c, which handles
33 * the construction of the parse tree nodes and their syntactic validation.
34 * The parse tree is constructed of dt_node_t structures (see <dt_parser.h>)
35 * that are built in two passes: (1) the "create" pass, where the parse tree
36 * nodes are allocated by calls from the grammar to dt_node_*() subroutines,
37 * and (2) the "cook" pass, where nodes are coalesced, assigned D types, and
38 * validated according to the syntactic rules of the language.
39 *
40 * All node allocations are performed using dt_node_alloc().  All node frees
41 * during the parsing phase are performed by dt_node_free(), which frees node-
42 * internal state but does not actually free the nodes.  All final node frees
43 * are done as part of the end of dt_compile() or as part of destroying
44 * persistent identifiers or translators which have embedded nodes.
45 *
46 * The dt_node_* routines that implement pass (1) may allocate new nodes.  The
47 * dt_cook_* routines that implement pass (2) may *not* allocate new nodes.
48 * They may free existing nodes using dt_node_free(), but they may not actually
49 * deallocate any dt_node_t's.  Currently dt_cook_op2() is an exception to this
50 * rule: see the comments therein for how this issue is resolved.
51 *
52 * The dt_cook_* routines are responsible for (at minimum) setting the final
53 * node type (dn_ctfp/dn_type) and attributes (dn_attr).  If dn_ctfp/dn_type
54 * are set manually (i.e. not by one of the type assignment functions), then
55 * the DT_NF_COOKED flag must be set manually on the node.
56 *
57 * The cooking pass can be applied to the same parse tree more than once (used
58 * in the case of a comma-separated list of probe descriptions).  As such, the
59 * cook routines must not perform any parse tree transformations which would
60 * be invalid if the tree were subsequently cooked using a different context.
61 *
62 * The dn_ctfp and dn_type fields form the type of the node.  This tuple can
63 * take on the following set of values, which form our type invariants:
64 *
65 * 1. dn_ctfp = NULL, dn_type = CTF_ERR
66 *
67 *    In this state, the node has unknown type and is not yet cooked.  The
68 *    DT_NF_COOKED flag is not yet set on the node.
69 *
70 * 2. dn_ctfp = DT_DYN_CTFP(dtp), dn_type = DT_DYN_TYPE(dtp)
71 *
72 *    In this state, the node is a dynamic D type.  This means that generic
73 *    operations are not valid on this node and only code that knows how to
74 *    examine the inner details of the node can operate on it.  A <DYN> node
75 *    must have dn_ident set to point to an identifier describing the object
76 *    and its type.  The DT_NF_REF flag is set for all nodes of type <DYN>.
77 *    At present, the D compiler uses the <DYN> type for:
78 *
79 *    - associative arrays that do not yet have a value type defined
80 *    - translated data (i.e. the result of the xlate operator)
81 *    - aggregations
82 *
83 * 3. dn_ctfp = DT_STR_CTFP(dtp), dn_type = DT_STR_TYPE(dtp)
84 *
85 *    In this state, the node is of type D string.  The string type is really
86 *    a char[0] typedef, but requires special handling throughout the compiler.
87 *
88 * 4. dn_ctfp != NULL, dn_type = any other type ID
89 *
90 *    In this state, the node is of some known D/CTF type.  The normal libctf
91 *    APIs can be used to learn more about the type name or structure.  When
92 *    the type is assigned, the DT_NF_SIGNED, DT_NF_REF, and DT_NF_BITFIELD
93 *    flags cache the corresponding attributes of the underlying CTF type.
94 */
95
96#include <sys/param.h>
97#include <sys/sysmacros.h>
98#include <limits.h>
99#include <setjmp.h>
100#include <strings.h>
101#include <assert.h>
102#include <alloca.h>
103#include <stdlib.h>
104#include <stdarg.h>
105#include <stdio.h>
106#include <errno.h>
107#include <ctype.h>
108
109#include <dt_impl.h>
110#include <dt_grammar.h>
111#include <dt_module.h>
112#include <dt_provider.h>
113#include <dt_string.h>
114#include <dt_as.h>
115
116dt_pcb_t *yypcb;	/* current control block for parser */
117dt_node_t *yypragma;	/* lex token list for control lines */
118char yyintprefix;	/* int token macro prefix (+/-) */
119char yyintsuffix[4];	/* int token suffix string [uU][lL] */
120int yyintdecimal;	/* int token format flag (1=decimal, 0=octal/hex) */
121
122static const char *
123opstr(int op)
124{
125	switch (op) {
126	case DT_TOK_COMMA:	return (",");
127	case DT_TOK_ELLIPSIS:	return ("...");
128	case DT_TOK_ASGN:	return ("=");
129	case DT_TOK_ADD_EQ:	return ("+=");
130	case DT_TOK_SUB_EQ:	return ("-=");
131	case DT_TOK_MUL_EQ:	return ("*=");
132	case DT_TOK_DIV_EQ:	return ("/=");
133	case DT_TOK_MOD_EQ:	return ("%=");
134	case DT_TOK_AND_EQ:	return ("&=");
135	case DT_TOK_XOR_EQ:	return ("^=");
136	case DT_TOK_OR_EQ:	return ("|=");
137	case DT_TOK_LSH_EQ:	return ("<<=");
138	case DT_TOK_RSH_EQ:	return (">>=");
139	case DT_TOK_QUESTION:	return ("?");
140	case DT_TOK_COLON:	return (":");
141	case DT_TOK_LOR:	return ("||");
142	case DT_TOK_LXOR:	return ("^^");
143	case DT_TOK_LAND:	return ("&&");
144	case DT_TOK_BOR:	return ("|");
145	case DT_TOK_XOR:	return ("^");
146	case DT_TOK_BAND:	return ("&");
147	case DT_TOK_EQU:	return ("==");
148	case DT_TOK_NEQ:	return ("!=");
149	case DT_TOK_LT:		return ("<");
150	case DT_TOK_LE:		return ("<=");
151	case DT_TOK_GT:		return (">");
152	case DT_TOK_GE:		return (">=");
153	case DT_TOK_LSH:	return ("<<");
154	case DT_TOK_RSH:	return (">>");
155	case DT_TOK_ADD:	return ("+");
156	case DT_TOK_SUB:	return ("-");
157	case DT_TOK_MUL:	return ("*");
158	case DT_TOK_DIV:	return ("/");
159	case DT_TOK_MOD:	return ("%");
160	case DT_TOK_LNEG:	return ("!");
161	case DT_TOK_BNEG:	return ("~");
162	case DT_TOK_ADDADD:	return ("++");
163	case DT_TOK_PREINC:	return ("++");
164	case DT_TOK_POSTINC:	return ("++");
165	case DT_TOK_SUBSUB:	return ("--");
166	case DT_TOK_PREDEC:	return ("--");
167	case DT_TOK_POSTDEC:	return ("--");
168	case DT_TOK_IPOS:	return ("+");
169	case DT_TOK_INEG:	return ("-");
170	case DT_TOK_DEREF:	return ("*");
171	case DT_TOK_ADDROF:	return ("&");
172	case DT_TOK_OFFSETOF:	return ("offsetof");
173	case DT_TOK_SIZEOF:	return ("sizeof");
174	case DT_TOK_STRINGOF:	return ("stringof");
175	case DT_TOK_XLATE:	return ("xlate");
176	case DT_TOK_LPAR:	return ("(");
177	case DT_TOK_RPAR:	return (")");
178	case DT_TOK_LBRAC:	return ("[");
179	case DT_TOK_RBRAC:	return ("]");
180	case DT_TOK_PTR:	return ("->");
181	case DT_TOK_DOT:	return (".");
182	case DT_TOK_STRING:	return ("<string>");
183	case DT_TOK_IDENT:	return ("<ident>");
184	case DT_TOK_TNAME:	return ("<type>");
185	case DT_TOK_INT:	return ("<int>");
186	default:		return ("<?>");
187	}
188}
189
190int
191dt_type_lookup(const char *s, dtrace_typeinfo_t *tip)
192{
193	static const char delimiters[] = " \t\n\r\v\f*`";
194	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
195	const char *p, *q, *r, *end, *obj;
196
197	for (p = s, end = s + strlen(s); *p != '\0'; p = q) {
198		while (isspace(*p))
199			p++;	/* skip leading whitespace prior to token */
200
201		if (p == end || (q = strpbrk(p + 1, delimiters)) == NULL)
202			break;	/* empty string or single token remaining */
203
204		if (*q == '`') {
205			char *object = alloca((size_t)(q - p) + 1);
206			char *type = alloca((size_t)(end - s) + 1);
207
208			/*
209			 * Copy from the start of the token (p) to the location
210			 * backquote (q) to extract the nul-terminated object.
211			 */
212			bcopy(p, object, (size_t)(q - p));
213			object[(size_t)(q - p)] = '\0';
214
215			/*
216			 * Copy the original string up to the start of this
217			 * token (p) into type, and then concatenate everything
218			 * after q.  This is the type name without the object.
219			 */
220			bcopy(s, type, (size_t)(p - s));
221			bcopy(q + 1, type + (size_t)(p - s), strlen(q + 1) + 1);
222
223			/*
224			 * There may be at most three delimeters. The second
225			 * delimeter is usually used to distinguish the type
226			 * within a given module, however, there could be a link
227			 * map id on the scene in which case that delimeter
228			 * would be the third. We determine presence of the lmid
229			 * if it rouglhly meets the from LM[0-9]
230			 */
231			if ((r = strchr(q + 1, '`')) != NULL &&
232			    ((r = strchr(r + 1, '`')) != NULL)) {
233				if (strchr(r + 1, '`') != NULL)
234					return (dt_set_errno(dtp,
235					    EDT_BADSCOPE));
236				if (q[1] != 'L' || q[2] != 'M')
237					return (dt_set_errno(dtp,
238					    EDT_BADSCOPE));
239			}
240
241			return (dtrace_lookup_by_type(dtp, object, type, tip));
242		}
243	}
244
245	if (yypcb->pcb_idepth != 0)
246		obj = DTRACE_OBJ_CDEFS;
247	else
248		obj = DTRACE_OBJ_EVERY;
249
250	return (dtrace_lookup_by_type(dtp, obj, s, tip));
251}
252
253/*
254 * When we parse type expressions or parse an expression with unary "&", we
255 * need to find a type that is a pointer to a previously known type.
256 * Unfortunately CTF is limited to a per-container view, so ctf_type_pointer()
257 * alone does not suffice for our needs.  We provide a more intelligent wrapper
258 * for the compiler that attempts to compute a pointer to either the given type
259 * or its base (that is, we try both "foo_t *" and "struct foo *"), and also
260 * to potentially construct the required type on-the-fly.
261 */
262int
263dt_type_pointer(dtrace_typeinfo_t *tip)
264{
265	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
266	ctf_file_t *ctfp = tip->dtt_ctfp;
267	ctf_id_t type = tip->dtt_type;
268	ctf_id_t base = ctf_type_resolve(ctfp, type);
269	uint_t bflags = tip->dtt_flags;
270
271	dt_module_t *dmp;
272	ctf_id_t ptr;
273
274	if ((ptr = ctf_type_pointer(ctfp, type)) != CTF_ERR ||
275	    (ptr = ctf_type_pointer(ctfp, base)) != CTF_ERR) {
276		tip->dtt_type = ptr;
277		return (0);
278	}
279
280	if (yypcb->pcb_idepth != 0)
281		dmp = dtp->dt_cdefs;
282	else
283		dmp = dtp->dt_ddefs;
284
285	if (ctfp != dmp->dm_ctfp && ctfp != ctf_parent_file(dmp->dm_ctfp) &&
286	    (type = ctf_add_type(dmp->dm_ctfp, ctfp, type)) == CTF_ERR) {
287		dtp->dt_ctferr = ctf_errno(dmp->dm_ctfp);
288		return (dt_set_errno(dtp, EDT_CTF));
289	}
290
291	ptr = ctf_add_pointer(dmp->dm_ctfp, CTF_ADD_ROOT, NULL, type);
292
293	if (ptr == CTF_ERR || ctf_update(dmp->dm_ctfp) == CTF_ERR) {
294		dtp->dt_ctferr = ctf_errno(dmp->dm_ctfp);
295		return (dt_set_errno(dtp, EDT_CTF));
296	}
297
298	tip->dtt_object = dmp->dm_name;
299	tip->dtt_ctfp = dmp->dm_ctfp;
300	tip->dtt_type = ptr;
301	tip->dtt_flags = bflags;
302
303	return (0);
304}
305
306const char *
307dt_type_name(ctf_file_t *ctfp, ctf_id_t type, char *buf, size_t len)
308{
309	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
310
311	if (ctfp == DT_FPTR_CTFP(dtp) && type == DT_FPTR_TYPE(dtp))
312		(void) snprintf(buf, len, "function pointer");
313	else if (ctfp == DT_FUNC_CTFP(dtp) && type == DT_FUNC_TYPE(dtp))
314		(void) snprintf(buf, len, "function");
315	else if (ctfp == DT_DYN_CTFP(dtp) && type == DT_DYN_TYPE(dtp))
316		(void) snprintf(buf, len, "dynamic variable");
317	else if (ctfp == NULL)
318		(void) snprintf(buf, len, "<none>");
319	else if (ctf_type_name(ctfp, type, buf, len) == NULL)
320		(void) snprintf(buf, len, "unknown");
321
322	return (buf);
323}
324
325/*
326 * Perform the "usual arithmetic conversions" to determine which of the two
327 * input operand types should be promoted and used as a result type.  The
328 * rules for this are described in ISOC[6.3.1.8] and K&R[A6.5].
329 */
330static void
331dt_type_promote(dt_node_t *lp, dt_node_t *rp, ctf_file_t **ofp, ctf_id_t *otype)
332{
333	ctf_file_t *lfp = lp->dn_ctfp;
334	ctf_id_t ltype = lp->dn_type;
335
336	ctf_file_t *rfp = rp->dn_ctfp;
337	ctf_id_t rtype = rp->dn_type;
338
339	ctf_id_t lbase = ctf_type_resolve(lfp, ltype);
340	uint_t lkind = ctf_type_kind(lfp, lbase);
341
342	ctf_id_t rbase = ctf_type_resolve(rfp, rtype);
343	uint_t rkind = ctf_type_kind(rfp, rbase);
344
345	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
346	ctf_encoding_t le, re;
347	uint_t lrank, rrank;
348
349	assert(lkind == CTF_K_INTEGER || lkind == CTF_K_ENUM);
350	assert(rkind == CTF_K_INTEGER || rkind == CTF_K_ENUM);
351
352	if (lkind == CTF_K_ENUM) {
353		lfp = DT_INT_CTFP(dtp);
354		ltype = lbase = DT_INT_TYPE(dtp);
355	}
356
357	if (rkind == CTF_K_ENUM) {
358		rfp = DT_INT_CTFP(dtp);
359		rtype = rbase = DT_INT_TYPE(dtp);
360	}
361
362	if (ctf_type_encoding(lfp, lbase, &le) == CTF_ERR) {
363		yypcb->pcb_hdl->dt_ctferr = ctf_errno(lfp);
364		longjmp(yypcb->pcb_jmpbuf, EDT_CTF);
365	}
366
367	if (ctf_type_encoding(rfp, rbase, &re) == CTF_ERR) {
368		yypcb->pcb_hdl->dt_ctferr = ctf_errno(rfp);
369		longjmp(yypcb->pcb_jmpbuf, EDT_CTF);
370	}
371
372	/*
373	 * Compute an integer rank based on the size and unsigned status.
374	 * If rank is identical, pick the "larger" of the equivalent types
375	 * which we define as having a larger base ctf_id_t.  If rank is
376	 * different, pick the type with the greater rank.
377	 */
378	lrank = le.cte_bits + ((le.cte_format & CTF_INT_SIGNED) == 0);
379	rrank = re.cte_bits + ((re.cte_format & CTF_INT_SIGNED) == 0);
380
381	if (lrank == rrank) {
382		if (lbase - rbase < 0)
383			goto return_rtype;
384		else
385			goto return_ltype;
386	} else if (lrank > rrank) {
387		goto return_ltype;
388	} else
389		goto return_rtype;
390
391return_ltype:
392	*ofp = lfp;
393	*otype = ltype;
394	return;
395
396return_rtype:
397	*ofp = rfp;
398	*otype = rtype;
399}
400
401void
402dt_node_promote(dt_node_t *lp, dt_node_t *rp, dt_node_t *dnp)
403{
404	dt_type_promote(lp, rp, &dnp->dn_ctfp, &dnp->dn_type);
405	dt_node_type_assign(dnp, dnp->dn_ctfp, dnp->dn_type, B_FALSE);
406	dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
407}
408
409const char *
410dt_node_name(const dt_node_t *dnp, char *buf, size_t len)
411{
412	char n1[DT_TYPE_NAMELEN];
413	char n2[DT_TYPE_NAMELEN];
414
415	const char *prefix = "", *suffix = "";
416	const dtrace_syminfo_t *dts;
417	char *s;
418
419	switch (dnp->dn_kind) {
420	case DT_NODE_INT:
421		(void) snprintf(buf, len, "integer constant 0x%llx",
422		    (u_longlong_t)dnp->dn_value);
423		break;
424	case DT_NODE_STRING:
425		s = strchr2esc(dnp->dn_string, strlen(dnp->dn_string));
426		(void) snprintf(buf, len, "string constant \"%s\"",
427		    s != NULL ? s : dnp->dn_string);
428		free(s);
429		break;
430	case DT_NODE_IDENT:
431		(void) snprintf(buf, len, "identifier %s", dnp->dn_string);
432		break;
433	case DT_NODE_VAR:
434	case DT_NODE_FUNC:
435	case DT_NODE_AGG:
436	case DT_NODE_INLINE:
437		switch (dnp->dn_ident->di_kind) {
438		case DT_IDENT_FUNC:
439		case DT_IDENT_AGGFUNC:
440		case DT_IDENT_ACTFUNC:
441			suffix = "( )";
442			break;
443		case DT_IDENT_AGG:
444			prefix = "@";
445			break;
446		}
447		(void) snprintf(buf, len, "%s %s%s%s",
448		    dt_idkind_name(dnp->dn_ident->di_kind),
449		    prefix, dnp->dn_ident->di_name, suffix);
450		break;
451	case DT_NODE_SYM:
452		dts = dnp->dn_ident->di_data;
453		(void) snprintf(buf, len, "symbol %s`%s",
454		    dts->dts_object, dts->dts_name);
455		break;
456	case DT_NODE_TYPE:
457		(void) snprintf(buf, len, "type %s",
458		    dt_node_type_name(dnp, n1, sizeof (n1)));
459		break;
460	case DT_NODE_OP1:
461	case DT_NODE_OP2:
462	case DT_NODE_OP3:
463		(void) snprintf(buf, len, "operator %s", opstr(dnp->dn_op));
464		break;
465	case DT_NODE_DEXPR:
466	case DT_NODE_DFUNC:
467		if (dnp->dn_expr)
468			return (dt_node_name(dnp->dn_expr, buf, len));
469		(void) snprintf(buf, len, "%s", "statement");
470		break;
471	case DT_NODE_PDESC:
472		if (dnp->dn_desc->dtpd_id == 0) {
473			(void) snprintf(buf, len,
474			    "probe description %s:%s:%s:%s",
475			    dnp->dn_desc->dtpd_provider, dnp->dn_desc->dtpd_mod,
476			    dnp->dn_desc->dtpd_func, dnp->dn_desc->dtpd_name);
477		} else {
478			(void) snprintf(buf, len, "probe description %u",
479			    dnp->dn_desc->dtpd_id);
480		}
481		break;
482	case DT_NODE_CLAUSE:
483		(void) snprintf(buf, len, "%s", "clause");
484		break;
485	case DT_NODE_MEMBER:
486		(void) snprintf(buf, len, "member %s", dnp->dn_membname);
487		break;
488	case DT_NODE_XLATOR:
489		(void) snprintf(buf, len, "translator <%s> (%s)",
490		    dt_type_name(dnp->dn_xlator->dx_dst_ctfp,
491		    dnp->dn_xlator->dx_dst_type, n1, sizeof (n1)),
492		    dt_type_name(dnp->dn_xlator->dx_src_ctfp,
493		    dnp->dn_xlator->dx_src_type, n2, sizeof (n2)));
494		break;
495	case DT_NODE_PROG:
496		(void) snprintf(buf, len, "%s", "program");
497		break;
498	default:
499		(void) snprintf(buf, len, "node <%u>", dnp->dn_kind);
500		break;
501	}
502
503	return (buf);
504}
505
506/*
507 * dt_node_xalloc() can be used to create new parse nodes from any libdtrace
508 * caller.  The caller is responsible for assigning dn_link appropriately.
509 */
510dt_node_t *
511dt_node_xalloc(dtrace_hdl_t *dtp, int kind)
512{
513	dt_node_t *dnp = dt_alloc(dtp, sizeof (dt_node_t));
514
515	if (dnp == NULL)
516		return (NULL);
517
518	dnp->dn_ctfp = NULL;
519	dnp->dn_type = CTF_ERR;
520	dnp->dn_kind = (uchar_t)kind;
521	dnp->dn_flags = 0;
522	dnp->dn_op = 0;
523	dnp->dn_line = -1;
524	dnp->dn_reg = -1;
525	dnp->dn_attr = _dtrace_defattr;
526	dnp->dn_list = NULL;
527	dnp->dn_link = NULL;
528	bzero(&dnp->dn_u, sizeof (dnp->dn_u));
529
530	return (dnp);
531}
532
533/*
534 * dt_node_alloc() is used to create new parse nodes from the parser.  It
535 * assigns the node location based on the current lexer line number and places
536 * the new node on the default allocation list.  If allocation fails, we
537 * automatically longjmp the caller back to the enclosing compilation call.
538 */
539static dt_node_t *
540dt_node_alloc(int kind)
541{
542	dt_node_t *dnp = dt_node_xalloc(yypcb->pcb_hdl, kind);
543
544	if (dnp == NULL)
545		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
546
547	dnp->dn_line = yylineno;
548	dnp->dn_link = yypcb->pcb_list;
549	yypcb->pcb_list = dnp;
550
551	return (dnp);
552}
553
554void
555dt_node_free(dt_node_t *dnp)
556{
557	uchar_t kind = dnp->dn_kind;
558
559	dnp->dn_kind = DT_NODE_FREE;
560
561	switch (kind) {
562	case DT_NODE_STRING:
563	case DT_NODE_IDENT:
564	case DT_NODE_TYPE:
565		free(dnp->dn_string);
566		dnp->dn_string = NULL;
567		break;
568
569	case DT_NODE_VAR:
570	case DT_NODE_FUNC:
571	case DT_NODE_PROBE:
572		if (dnp->dn_ident != NULL) {
573			if (dnp->dn_ident->di_flags & DT_IDFLG_ORPHAN)
574				dt_ident_destroy(dnp->dn_ident);
575			dnp->dn_ident = NULL;
576		}
577		dt_node_list_free(&dnp->dn_args);
578		break;
579
580	case DT_NODE_OP1:
581		if (dnp->dn_child != NULL) {
582			dt_node_free(dnp->dn_child);
583			dnp->dn_child = NULL;
584		}
585		break;
586
587	case DT_NODE_OP3:
588		if (dnp->dn_expr != NULL) {
589			dt_node_free(dnp->dn_expr);
590			dnp->dn_expr = NULL;
591		}
592		/*FALLTHRU*/
593	case DT_NODE_OP2:
594		if (dnp->dn_left != NULL) {
595			dt_node_free(dnp->dn_left);
596			dnp->dn_left = NULL;
597		}
598		if (dnp->dn_right != NULL) {
599			dt_node_free(dnp->dn_right);
600			dnp->dn_right = NULL;
601		}
602		break;
603
604	case DT_NODE_DEXPR:
605	case DT_NODE_DFUNC:
606		if (dnp->dn_expr != NULL) {
607			dt_node_free(dnp->dn_expr);
608			dnp->dn_expr = NULL;
609		}
610		break;
611
612	case DT_NODE_AGG:
613		if (dnp->dn_aggfun != NULL) {
614			dt_node_free(dnp->dn_aggfun);
615			dnp->dn_aggfun = NULL;
616		}
617		dt_node_list_free(&dnp->dn_aggtup);
618		break;
619
620	case DT_NODE_PDESC:
621		free(dnp->dn_spec);
622		dnp->dn_spec = NULL;
623		free(dnp->dn_desc);
624		dnp->dn_desc = NULL;
625		break;
626
627	case DT_NODE_CLAUSE:
628		if (dnp->dn_pred != NULL)
629			dt_node_free(dnp->dn_pred);
630		if (dnp->dn_locals != NULL)
631			dt_idhash_destroy(dnp->dn_locals);
632		dt_node_list_free(&dnp->dn_pdescs);
633		dt_node_list_free(&dnp->dn_acts);
634		break;
635
636	case DT_NODE_MEMBER:
637		free(dnp->dn_membname);
638		dnp->dn_membname = NULL;
639		if (dnp->dn_membexpr != NULL) {
640			dt_node_free(dnp->dn_membexpr);
641			dnp->dn_membexpr = NULL;
642		}
643		break;
644
645	case DT_NODE_PROVIDER:
646		dt_node_list_free(&dnp->dn_probes);
647		free(dnp->dn_provname);
648		dnp->dn_provname = NULL;
649		break;
650
651	case DT_NODE_PROG:
652		dt_node_list_free(&dnp->dn_list);
653		break;
654	}
655}
656
657void
658dt_node_attr_assign(dt_node_t *dnp, dtrace_attribute_t attr)
659{
660	if ((yypcb->pcb_cflags & DTRACE_C_EATTR) &&
661	    (dt_attr_cmp(attr, yypcb->pcb_amin) < 0)) {
662		char a[DTRACE_ATTR2STR_MAX];
663		char s[BUFSIZ];
664
665		dnerror(dnp, D_ATTR_MIN, "attributes for %s (%s) are less than "
666		    "predefined minimum\n", dt_node_name(dnp, s, sizeof (s)),
667		    dtrace_attr2str(attr, a, sizeof (a)));
668	}
669
670	dnp->dn_attr = attr;
671}
672
673void
674dt_node_type_assign(dt_node_t *dnp, ctf_file_t *fp, ctf_id_t type,
675    boolean_t user)
676{
677	ctf_id_t base = ctf_type_resolve(fp, type);
678	uint_t kind = ctf_type_kind(fp, base);
679	ctf_encoding_t e;
680
681	dnp->dn_flags &=
682	    ~(DT_NF_SIGNED | DT_NF_REF | DT_NF_BITFIELD | DT_NF_USERLAND);
683
684	if (kind == CTF_K_INTEGER && ctf_type_encoding(fp, base, &e) == 0) {
685		size_t size = e.cte_bits / NBBY;
686
687		if (size > 8 || (e.cte_bits % NBBY) != 0 || (size & (size - 1)))
688			dnp->dn_flags |= DT_NF_BITFIELD;
689
690		if (e.cte_format & CTF_INT_SIGNED)
691			dnp->dn_flags |= DT_NF_SIGNED;
692	}
693
694	if (kind == CTF_K_FLOAT && ctf_type_encoding(fp, base, &e) == 0) {
695		if (e.cte_bits / NBBY > sizeof (uint64_t))
696			dnp->dn_flags |= DT_NF_REF;
697	}
698
699	if (kind == CTF_K_STRUCT || kind == CTF_K_UNION ||
700	    kind == CTF_K_FORWARD ||
701	    kind == CTF_K_ARRAY || kind == CTF_K_FUNCTION)
702		dnp->dn_flags |= DT_NF_REF;
703	else if (yypcb != NULL && fp == DT_DYN_CTFP(yypcb->pcb_hdl) &&
704	    type == DT_DYN_TYPE(yypcb->pcb_hdl))
705		dnp->dn_flags |= DT_NF_REF;
706
707	if (user)
708		dnp->dn_flags |= DT_NF_USERLAND;
709
710	dnp->dn_flags |= DT_NF_COOKED;
711	dnp->dn_ctfp = fp;
712	dnp->dn_type = type;
713}
714
715void
716dt_node_type_propagate(const dt_node_t *src, dt_node_t *dst)
717{
718	assert(src->dn_flags & DT_NF_COOKED);
719	dst->dn_flags = src->dn_flags & ~DT_NF_LVALUE;
720	dst->dn_ctfp = src->dn_ctfp;
721	dst->dn_type = src->dn_type;
722}
723
724const char *
725dt_node_type_name(const dt_node_t *dnp, char *buf, size_t len)
726{
727	if (dt_node_is_dynamic(dnp) && dnp->dn_ident != NULL) {
728		(void) snprintf(buf, len, "%s",
729		    dt_idkind_name(dt_ident_resolve(dnp->dn_ident)->di_kind));
730		return (buf);
731	}
732
733	if (dnp->dn_flags & DT_NF_USERLAND) {
734		size_t n = snprintf(buf, len, "userland ");
735		len = len > n ? len - n : 0;
736		(void) dt_type_name(dnp->dn_ctfp, dnp->dn_type, buf + n, len);
737		return (buf);
738	}
739
740	return (dt_type_name(dnp->dn_ctfp, dnp->dn_type, buf, len));
741}
742
743size_t
744dt_node_type_size(const dt_node_t *dnp)
745{
746	ctf_id_t base;
747	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
748
749	if (dnp->dn_kind == DT_NODE_STRING)
750		return (strlen(dnp->dn_string) + 1);
751
752	if (dt_node_is_dynamic(dnp) && dnp->dn_ident != NULL)
753		return (dt_ident_size(dnp->dn_ident));
754
755	base = ctf_type_resolve(dnp->dn_ctfp, dnp->dn_type);
756
757	if (ctf_type_kind(dnp->dn_ctfp, base) == CTF_K_FORWARD)
758		return (0);
759
760	/*
761	 * Here we have a 32-bit user pointer that is being used with a 64-bit
762	 * kernel. When we're using it and its tagged as a userland reference --
763	 * then we need to keep it as a 32-bit pointer. However, if we are
764	 * referring to it as a kernel address, eg. being used after a copyin()
765	 * then we need to make sure that we actually return the kernel's size
766	 * of a pointer, 8 bytes.
767	 */
768	if (ctf_type_kind(dnp->dn_ctfp, base) == CTF_K_POINTER &&
769	    ctf_getmodel(dnp->dn_ctfp) == CTF_MODEL_ILP32 &&
770	    !(dnp->dn_flags & DT_NF_USERLAND) &&
771	    dtp->dt_conf.dtc_ctfmodel == CTF_MODEL_LP64)
772			return (8);
773
774	return (ctf_type_size(dnp->dn_ctfp, dnp->dn_type));
775}
776
777/*
778 * Determine if the specified parse tree node references an identifier of the
779 * specified kind, and if so return a pointer to it; otherwise return NULL.
780 * This function resolves the identifier itself, following through any inlines.
781 */
782dt_ident_t *
783dt_node_resolve(const dt_node_t *dnp, uint_t idkind)
784{
785	dt_ident_t *idp;
786
787	switch (dnp->dn_kind) {
788	case DT_NODE_VAR:
789	case DT_NODE_SYM:
790	case DT_NODE_FUNC:
791	case DT_NODE_AGG:
792	case DT_NODE_INLINE:
793	case DT_NODE_PROBE:
794		idp = dt_ident_resolve(dnp->dn_ident);
795		return (idp->di_kind == idkind ? idp : NULL);
796	}
797
798	if (dt_node_is_dynamic(dnp)) {
799		idp = dt_ident_resolve(dnp->dn_ident);
800		return (idp->di_kind == idkind ? idp : NULL);
801	}
802
803	return (NULL);
804}
805
806size_t
807dt_node_sizeof(const dt_node_t *dnp)
808{
809	dtrace_syminfo_t *sip;
810	GElf_Sym sym;
811	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
812
813	/*
814	 * The size of the node as used for the sizeof() operator depends on
815	 * the kind of the node.  If the node is a SYM, the size is obtained
816	 * from the symbol table; if it is not a SYM, the size is determined
817	 * from the node's type.  This is slightly different from C's sizeof()
818	 * operator in that (for example) when applied to a function, sizeof()
819	 * will evaluate to the length of the function rather than the size of
820	 * the function type.
821	 */
822	if (dnp->dn_kind != DT_NODE_SYM)
823		return (dt_node_type_size(dnp));
824
825	sip = dnp->dn_ident->di_data;
826
827	if (dtrace_lookup_by_name(dtp, sip->dts_object,
828	    sip->dts_name, &sym, NULL) == -1)
829		return (0);
830
831	return (sym.st_size);
832}
833
834int
835dt_node_is_integer(const dt_node_t *dnp)
836{
837	ctf_file_t *fp = dnp->dn_ctfp;
838	ctf_encoding_t e;
839	ctf_id_t type;
840	uint_t kind;
841
842	assert(dnp->dn_flags & DT_NF_COOKED);
843
844	type = ctf_type_resolve(fp, dnp->dn_type);
845	kind = ctf_type_kind(fp, type);
846
847	if (kind == CTF_K_INTEGER &&
848	    ctf_type_encoding(fp, type, &e) == 0 && IS_VOID(e))
849		return (0); /* void integer */
850
851	return (kind == CTF_K_INTEGER || kind == CTF_K_ENUM);
852}
853
854int
855dt_node_is_float(const dt_node_t *dnp)
856{
857	ctf_file_t *fp = dnp->dn_ctfp;
858	ctf_encoding_t e;
859	ctf_id_t type;
860	uint_t kind;
861
862	assert(dnp->dn_flags & DT_NF_COOKED);
863
864	type = ctf_type_resolve(fp, dnp->dn_type);
865	kind = ctf_type_kind(fp, type);
866
867	return (kind == CTF_K_FLOAT &&
868	    ctf_type_encoding(dnp->dn_ctfp, type, &e) == 0 && (
869	    e.cte_format == CTF_FP_SINGLE || e.cte_format == CTF_FP_DOUBLE ||
870	    e.cte_format == CTF_FP_LDOUBLE));
871}
872
873int
874dt_node_is_scalar(const dt_node_t *dnp)
875{
876	ctf_file_t *fp = dnp->dn_ctfp;
877	ctf_encoding_t e;
878	ctf_id_t type;
879	uint_t kind;
880
881	assert(dnp->dn_flags & DT_NF_COOKED);
882
883	type = ctf_type_resolve(fp, dnp->dn_type);
884	kind = ctf_type_kind(fp, type);
885
886	if (kind == CTF_K_INTEGER &&
887	    ctf_type_encoding(fp, type, &e) == 0 && IS_VOID(e))
888		return (0); /* void cannot be used as a scalar */
889
890	return (kind == CTF_K_INTEGER || kind == CTF_K_ENUM ||
891	    kind == CTF_K_POINTER);
892}
893
894int
895dt_node_is_arith(const dt_node_t *dnp)
896{
897	ctf_file_t *fp = dnp->dn_ctfp;
898	ctf_encoding_t e;
899	ctf_id_t type;
900	uint_t kind;
901
902	assert(dnp->dn_flags & DT_NF_COOKED);
903
904	type = ctf_type_resolve(fp, dnp->dn_type);
905	kind = ctf_type_kind(fp, type);
906
907	if (kind == CTF_K_INTEGER)
908		return (ctf_type_encoding(fp, type, &e) == 0 && !IS_VOID(e));
909	else
910		return (kind == CTF_K_ENUM);
911}
912
913int
914dt_node_is_vfptr(const dt_node_t *dnp)
915{
916	ctf_file_t *fp = dnp->dn_ctfp;
917	ctf_encoding_t e;
918	ctf_id_t type;
919	uint_t kind;
920
921	assert(dnp->dn_flags & DT_NF_COOKED);
922
923	type = ctf_type_resolve(fp, dnp->dn_type);
924	if (ctf_type_kind(fp, type) != CTF_K_POINTER)
925		return (0); /* type is not a pointer */
926
927	type = ctf_type_resolve(fp, ctf_type_reference(fp, type));
928	kind = ctf_type_kind(fp, type);
929
930	return (kind == CTF_K_FUNCTION || (kind == CTF_K_INTEGER &&
931	    ctf_type_encoding(fp, type, &e) == 0 && IS_VOID(e)));
932}
933
934int
935dt_node_is_dynamic(const dt_node_t *dnp)
936{
937	if (dnp->dn_kind == DT_NODE_VAR &&
938	    (dnp->dn_ident->di_flags & DT_IDFLG_INLINE)) {
939		const dt_idnode_t *inp = dnp->dn_ident->di_iarg;
940		return (inp->din_root ? dt_node_is_dynamic(inp->din_root) : 0);
941	}
942
943	return (dnp->dn_ctfp == DT_DYN_CTFP(yypcb->pcb_hdl) &&
944	    dnp->dn_type == DT_DYN_TYPE(yypcb->pcb_hdl));
945}
946
947int
948dt_node_is_string(const dt_node_t *dnp)
949{
950	return (dnp->dn_ctfp == DT_STR_CTFP(yypcb->pcb_hdl) &&
951	    dnp->dn_type == DT_STR_TYPE(yypcb->pcb_hdl));
952}
953
954int
955dt_node_is_stack(const dt_node_t *dnp)
956{
957	return (dnp->dn_ctfp == DT_STACK_CTFP(yypcb->pcb_hdl) &&
958	    dnp->dn_type == DT_STACK_TYPE(yypcb->pcb_hdl));
959}
960
961int
962dt_node_is_symaddr(const dt_node_t *dnp)
963{
964	return (dnp->dn_ctfp == DT_SYMADDR_CTFP(yypcb->pcb_hdl) &&
965	    dnp->dn_type == DT_SYMADDR_TYPE(yypcb->pcb_hdl));
966}
967
968int
969dt_node_is_usymaddr(const dt_node_t *dnp)
970{
971	return (dnp->dn_ctfp == DT_USYMADDR_CTFP(yypcb->pcb_hdl) &&
972	    dnp->dn_type == DT_USYMADDR_TYPE(yypcb->pcb_hdl));
973}
974
975int
976dt_node_is_strcompat(const dt_node_t *dnp)
977{
978	ctf_file_t *fp = dnp->dn_ctfp;
979	ctf_encoding_t e;
980	ctf_arinfo_t r;
981	ctf_id_t base;
982	uint_t kind;
983
984	assert(dnp->dn_flags & DT_NF_COOKED);
985
986	base = ctf_type_resolve(fp, dnp->dn_type);
987	kind = ctf_type_kind(fp, base);
988
989	if (kind == CTF_K_POINTER &&
990	    (base = ctf_type_reference(fp, base)) != CTF_ERR &&
991	    (base = ctf_type_resolve(fp, base)) != CTF_ERR &&
992	    ctf_type_encoding(fp, base, &e) == 0 && IS_CHAR(e))
993		return (1); /* promote char pointer to string */
994
995	if (kind == CTF_K_ARRAY && ctf_array_info(fp, base, &r) == 0 &&
996	    (base = ctf_type_resolve(fp, r.ctr_contents)) != CTF_ERR &&
997	    ctf_type_encoding(fp, base, &e) == 0 && IS_CHAR(e))
998		return (1); /* promote char array to string */
999
1000	return (0);
1001}
1002
1003int
1004dt_node_is_pointer(const dt_node_t *dnp)
1005{
1006	ctf_file_t *fp = dnp->dn_ctfp;
1007	uint_t kind;
1008
1009	assert(dnp->dn_flags & DT_NF_COOKED);
1010
1011	if (dt_node_is_string(dnp))
1012		return (0); /* string are pass-by-ref but act like structs */
1013
1014	kind = ctf_type_kind(fp, ctf_type_resolve(fp, dnp->dn_type));
1015	return (kind == CTF_K_POINTER || kind == CTF_K_ARRAY);
1016}
1017
1018int
1019dt_node_is_void(const dt_node_t *dnp)
1020{
1021	ctf_file_t *fp = dnp->dn_ctfp;
1022	ctf_encoding_t e;
1023	ctf_id_t type;
1024
1025	if (dt_node_is_dynamic(dnp))
1026		return (0); /* <DYN> is an alias for void but not the same */
1027
1028	if (dt_node_is_stack(dnp))
1029		return (0);
1030
1031	if (dt_node_is_symaddr(dnp) || dt_node_is_usymaddr(dnp))
1032		return (0);
1033
1034	type = ctf_type_resolve(fp, dnp->dn_type);
1035
1036	return (ctf_type_kind(fp, type) == CTF_K_INTEGER &&
1037	    ctf_type_encoding(fp, type, &e) == 0 && IS_VOID(e));
1038}
1039
1040int
1041dt_node_is_ptrcompat(const dt_node_t *lp, const dt_node_t *rp,
1042    ctf_file_t **fpp, ctf_id_t *tp)
1043{
1044	ctf_file_t *lfp = lp->dn_ctfp;
1045	ctf_file_t *rfp = rp->dn_ctfp;
1046
1047	ctf_id_t lbase = CTF_ERR, rbase = CTF_ERR;
1048	ctf_id_t lref = CTF_ERR, rref = CTF_ERR;
1049
1050	int lp_is_void, rp_is_void, lp_is_int, rp_is_int, compat;
1051	uint_t lkind, rkind;
1052	ctf_encoding_t e;
1053	ctf_arinfo_t r;
1054
1055	assert(lp->dn_flags & DT_NF_COOKED);
1056	assert(rp->dn_flags & DT_NF_COOKED);
1057
1058	if (dt_node_is_dynamic(lp) || dt_node_is_dynamic(rp))
1059		return (0); /* fail if either node is a dynamic variable */
1060
1061	lp_is_int = dt_node_is_integer(lp);
1062	rp_is_int = dt_node_is_integer(rp);
1063
1064	if (lp_is_int && rp_is_int)
1065		return (0); /* fail if both nodes are integers */
1066
1067	if (lp_is_int && (lp->dn_kind != DT_NODE_INT || lp->dn_value != 0))
1068		return (0); /* fail if lp is an integer that isn't 0 constant */
1069
1070	if (rp_is_int && (rp->dn_kind != DT_NODE_INT || rp->dn_value != 0))
1071		return (0); /* fail if rp is an integer that isn't 0 constant */
1072
1073	if ((lp_is_int == 0 && rp_is_int == 0) && (
1074	    (lp->dn_flags & DT_NF_USERLAND) ^ (rp->dn_flags & DT_NF_USERLAND)))
1075		return (0); /* fail if only one pointer is a userland address */
1076
1077	/*
1078	 * Resolve the left-hand and right-hand types to their base type, and
1079	 * then resolve the referenced type as well (assuming the base type
1080	 * is CTF_K_POINTER or CTF_K_ARRAY).  Otherwise [lr]ref = CTF_ERR.
1081	 */
1082	if (!lp_is_int) {
1083		lbase = ctf_type_resolve(lfp, lp->dn_type);
1084		lkind = ctf_type_kind(lfp, lbase);
1085
1086		if (lkind == CTF_K_POINTER) {
1087			lref = ctf_type_resolve(lfp,
1088			    ctf_type_reference(lfp, lbase));
1089		} else if (lkind == CTF_K_ARRAY &&
1090		    ctf_array_info(lfp, lbase, &r) == 0) {
1091			lref = ctf_type_resolve(lfp, r.ctr_contents);
1092		}
1093	}
1094
1095	if (!rp_is_int) {
1096		rbase = ctf_type_resolve(rfp, rp->dn_type);
1097		rkind = ctf_type_kind(rfp, rbase);
1098
1099		if (rkind == CTF_K_POINTER) {
1100			rref = ctf_type_resolve(rfp,
1101			    ctf_type_reference(rfp, rbase));
1102		} else if (rkind == CTF_K_ARRAY &&
1103		    ctf_array_info(rfp, rbase, &r) == 0) {
1104			rref = ctf_type_resolve(rfp, r.ctr_contents);
1105		}
1106	}
1107
1108	/*
1109	 * We know that one or the other type may still be a zero-valued
1110	 * integer constant.  To simplify the code below, set the integer
1111	 * type variables equal to the non-integer types and proceed.
1112	 */
1113	if (lp_is_int) {
1114		lbase = rbase;
1115		lkind = rkind;
1116		lref = rref;
1117		lfp = rfp;
1118	} else if (rp_is_int) {
1119		rbase = lbase;
1120		rkind = lkind;
1121		rref = lref;
1122		rfp = lfp;
1123	}
1124
1125	lp_is_void = ctf_type_encoding(lfp, lref, &e) == 0 && IS_VOID(e);
1126	rp_is_void = ctf_type_encoding(rfp, rref, &e) == 0 && IS_VOID(e);
1127
1128	/*
1129	 * The types are compatible if both are pointers to the same type, or
1130	 * if either pointer is a void pointer.  If they are compatible, set
1131	 * tp to point to the more specific pointer type and return it.
1132	 */
1133	compat = (lkind == CTF_K_POINTER || lkind == CTF_K_ARRAY) &&
1134	    (rkind == CTF_K_POINTER || rkind == CTF_K_ARRAY) &&
1135	    (lp_is_void || rp_is_void || ctf_type_compat(lfp, lref, rfp, rref));
1136
1137	if (compat) {
1138		if (fpp != NULL)
1139			*fpp = rp_is_void ? lfp : rfp;
1140		if (tp != NULL)
1141			*tp = rp_is_void ? lbase : rbase;
1142	}
1143
1144	return (compat);
1145}
1146
1147/*
1148 * The rules for checking argument types against parameter types are described
1149 * in the ANSI-C spec (see K&R[A7.3.2] and K&R[A7.17]).  We use the same rule
1150 * set to determine whether associative array arguments match the prototype.
1151 */
1152int
1153dt_node_is_argcompat(const dt_node_t *lp, const dt_node_t *rp)
1154{
1155	ctf_file_t *lfp = lp->dn_ctfp;
1156	ctf_file_t *rfp = rp->dn_ctfp;
1157
1158	assert(lp->dn_flags & DT_NF_COOKED);
1159	assert(rp->dn_flags & DT_NF_COOKED);
1160
1161	if (dt_node_is_integer(lp) && dt_node_is_integer(rp))
1162		return (1); /* integer types are compatible */
1163
1164	if (dt_node_is_strcompat(lp) && dt_node_is_strcompat(rp))
1165		return (1); /* string types are compatible */
1166
1167	if (dt_node_is_stack(lp) && dt_node_is_stack(rp))
1168		return (1); /* stack types are compatible */
1169
1170	if (dt_node_is_symaddr(lp) && dt_node_is_symaddr(rp))
1171		return (1); /* symaddr types are compatible */
1172
1173	if (dt_node_is_usymaddr(lp) && dt_node_is_usymaddr(rp))
1174		return (1); /* usymaddr types are compatible */
1175
1176	switch (ctf_type_kind(lfp, ctf_type_resolve(lfp, lp->dn_type))) {
1177	case CTF_K_FUNCTION:
1178	case CTF_K_STRUCT:
1179	case CTF_K_UNION:
1180		return (ctf_type_compat(lfp, lp->dn_type, rfp, rp->dn_type));
1181	default:
1182		return (dt_node_is_ptrcompat(lp, rp, NULL, NULL));
1183	}
1184}
1185
1186/*
1187 * We provide dt_node_is_posconst() as a convenience routine for callers who
1188 * wish to verify that an argument is a positive non-zero integer constant.
1189 */
1190int
1191dt_node_is_posconst(const dt_node_t *dnp)
1192{
1193	return (dnp->dn_kind == DT_NODE_INT && dnp->dn_value != 0 && (
1194	    (dnp->dn_flags & DT_NF_SIGNED) == 0 || (int64_t)dnp->dn_value > 0));
1195}
1196
1197int
1198dt_node_is_actfunc(const dt_node_t *dnp)
1199{
1200	return (dnp->dn_kind == DT_NODE_FUNC &&
1201	    dnp->dn_ident->di_kind == DT_IDENT_ACTFUNC);
1202}
1203
1204/*
1205 * The original rules for integer constant typing are described in K&R[A2.5.1].
1206 * However, since we support long long, we instead use the rules from ISO C99
1207 * clause 6.4.4.1 since that is where long longs are formally described.  The
1208 * rules require us to know whether the constant was specified in decimal or
1209 * in octal or hex, which we do by looking at our lexer's 'yyintdecimal' flag.
1210 * The type of an integer constant is the first of the corresponding list in
1211 * which its value can be represented:
1212 *
1213 * unsuffixed decimal:   int, long, long long
1214 * unsuffixed oct/hex:   int, unsigned int, long, unsigned long,
1215 *                       long long, unsigned long long
1216 * suffix [uU]:          unsigned int, unsigned long, unsigned long long
1217 * suffix [lL] decimal:  long, long long
1218 * suffix [lL] oct/hex:  long, unsigned long, long long, unsigned long long
1219 * suffix [uU][Ll]:      unsigned long, unsigned long long
1220 * suffix ll/LL decimal: long long
1221 * suffix ll/LL oct/hex: long long, unsigned long long
1222 * suffix [uU][ll/LL]:   unsigned long long
1223 *
1224 * Given that our lexer has already validated the suffixes by regexp matching,
1225 * there is an obvious way to concisely encode these rules: construct an array
1226 * of the types in the order int, unsigned int, long, unsigned long, long long,
1227 * unsigned long long.  Compute an integer array starting index based on the
1228 * suffix (e.g. none = 0, u = 1, ull = 5), and compute an increment based on
1229 * the specifier (dec/oct/hex) and suffix (u).  Then iterate from the starting
1230 * index to the end, advancing using the increment, and searching until we
1231 * find a limit that matches or we run out of choices (overflow).  To make it
1232 * even faster, we precompute the table of type information in dtrace_open().
1233 */
1234dt_node_t *
1235dt_node_int(uintmax_t value)
1236{
1237	dt_node_t *dnp = dt_node_alloc(DT_NODE_INT);
1238	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1239
1240	int n = (yyintdecimal | (yyintsuffix[0] == 'u')) + 1;
1241	int i = 0;
1242
1243	const char *p;
1244	char c;
1245
1246	dnp->dn_op = DT_TOK_INT;
1247	dnp->dn_value = value;
1248
1249	for (p = yyintsuffix; (c = *p) != '\0'; p++) {
1250		if (c == 'U' || c == 'u')
1251			i += 1;
1252		else if (c == 'L' || c == 'l')
1253			i += 2;
1254	}
1255
1256	for (; i < sizeof (dtp->dt_ints) / sizeof (dtp->dt_ints[0]); i += n) {
1257		if (value <= dtp->dt_ints[i].did_limit) {
1258			dt_node_type_assign(dnp,
1259			    dtp->dt_ints[i].did_ctfp,
1260			    dtp->dt_ints[i].did_type, B_FALSE);
1261
1262			/*
1263			 * If a prefix character is present in macro text, add
1264			 * in the corresponding operator node (see dt_lex.l).
1265			 */
1266			switch (yyintprefix) {
1267			case '+':
1268				return (dt_node_op1(DT_TOK_IPOS, dnp));
1269			case '-':
1270				return (dt_node_op1(DT_TOK_INEG, dnp));
1271			default:
1272				return (dnp);
1273			}
1274		}
1275	}
1276
1277	xyerror(D_INT_OFLOW, "integer constant 0x%llx cannot be represented "
1278	    "in any built-in integral type\n", (u_longlong_t)value);
1279	/*NOTREACHED*/
1280	return (NULL);		/* keep gcc happy */
1281}
1282
1283dt_node_t *
1284dt_node_string(char *string)
1285{
1286	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1287	dt_node_t *dnp;
1288
1289	if (string == NULL)
1290		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
1291
1292	dnp = dt_node_alloc(DT_NODE_STRING);
1293	dnp->dn_op = DT_TOK_STRING;
1294	dnp->dn_string = string;
1295	dt_node_type_assign(dnp, DT_STR_CTFP(dtp), DT_STR_TYPE(dtp), B_FALSE);
1296
1297	return (dnp);
1298}
1299
1300dt_node_t *
1301dt_node_ident(char *name)
1302{
1303	dt_ident_t *idp;
1304	dt_node_t *dnp;
1305
1306	if (name == NULL)
1307		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
1308
1309	/*
1310	 * If the identifier is an inlined integer constant, then create an INT
1311	 * node that is a clone of the inline parse tree node and return that
1312	 * immediately, allowing this inline to be used in parsing contexts
1313	 * that require constant expressions (e.g. scalar array sizes).
1314	 */
1315	if ((idp = dt_idstack_lookup(&yypcb->pcb_globals, name)) != NULL &&
1316	    (idp->di_flags & DT_IDFLG_INLINE)) {
1317		dt_idnode_t *inp = idp->di_iarg;
1318
1319		if (inp->din_root != NULL &&
1320		    inp->din_root->dn_kind == DT_NODE_INT) {
1321			free(name);
1322
1323			dnp = dt_node_alloc(DT_NODE_INT);
1324			dnp->dn_op = DT_TOK_INT;
1325			dnp->dn_value = inp->din_root->dn_value;
1326			dt_node_type_propagate(inp->din_root, dnp);
1327
1328			return (dnp);
1329		}
1330	}
1331
1332	dnp = dt_node_alloc(DT_NODE_IDENT);
1333	dnp->dn_op = name[0] == '@' ? DT_TOK_AGG : DT_TOK_IDENT;
1334	dnp->dn_string = name;
1335
1336	return (dnp);
1337}
1338
1339/*
1340 * Create an empty node of type corresponding to the given declaration.
1341 * Explicit references to user types (C or D) are assigned the default
1342 * stability; references to other types are _dtrace_typattr (Private).
1343 */
1344dt_node_t *
1345dt_node_type(dt_decl_t *ddp)
1346{
1347	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1348	dtrace_typeinfo_t dtt;
1349	dt_node_t *dnp;
1350	char *name = NULL;
1351	int err;
1352
1353	/*
1354	 * If 'ddp' is NULL, we get a decl by popping the decl stack.  This
1355	 * form of dt_node_type() is used by parameter rules in dt_grammar.y.
1356	 */
1357	if (ddp == NULL)
1358		ddp = dt_decl_pop_param(&name);
1359
1360	err = dt_decl_type(ddp, &dtt);
1361	dt_decl_free(ddp);
1362
1363	if (err != 0) {
1364		free(name);
1365		longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
1366	}
1367
1368	dnp = dt_node_alloc(DT_NODE_TYPE);
1369	dnp->dn_op = DT_TOK_IDENT;
1370	dnp->dn_string = name;
1371
1372	dt_node_type_assign(dnp, dtt.dtt_ctfp, dtt.dtt_type, dtt.dtt_flags);
1373
1374	if (dtt.dtt_ctfp == dtp->dt_cdefs->dm_ctfp ||
1375	    dtt.dtt_ctfp == dtp->dt_ddefs->dm_ctfp)
1376		dt_node_attr_assign(dnp, _dtrace_defattr);
1377	else
1378		dt_node_attr_assign(dnp, _dtrace_typattr);
1379
1380	return (dnp);
1381}
1382
1383/*
1384 * Create a type node corresponding to a varargs (...) parameter by just
1385 * assigning it type CTF_ERR.  The decl processing code will handle this.
1386 */
1387dt_node_t *
1388dt_node_vatype(void)
1389{
1390	dt_node_t *dnp = dt_node_alloc(DT_NODE_TYPE);
1391
1392	dnp->dn_op = DT_TOK_IDENT;
1393	dnp->dn_ctfp = yypcb->pcb_hdl->dt_cdefs->dm_ctfp;
1394	dnp->dn_type = CTF_ERR;
1395	dnp->dn_attr = _dtrace_defattr;
1396
1397	return (dnp);
1398}
1399
1400/*
1401 * Instantiate a decl using the contents of the current declaration stack.  As
1402 * we do not currently permit decls to be initialized, this function currently
1403 * returns NULL and no parse node is created.  When this function is called,
1404 * the topmost scope's ds_ident pointer will be set to NULL (indicating no
1405 * init_declarator rule was matched) or will point to the identifier to use.
1406 */
1407dt_node_t *
1408dt_node_decl(void)
1409{
1410	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1411	dt_scope_t *dsp = &yypcb->pcb_dstack;
1412	dt_dclass_t class = dsp->ds_class;
1413	dt_decl_t *ddp = dt_decl_top();
1414
1415	dt_module_t *dmp;
1416	dtrace_typeinfo_t dtt;
1417	ctf_id_t type;
1418
1419	char n1[DT_TYPE_NAMELEN];
1420	char n2[DT_TYPE_NAMELEN];
1421
1422	if (dt_decl_type(ddp, &dtt) != 0)
1423		longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
1424
1425	/*
1426	 * If we have no declaration identifier, then this is either a spurious
1427	 * declaration of an intrinsic type (e.g. "extern int;") or declaration
1428	 * or redeclaration of a struct, union, or enum type or tag.
1429	 */
1430	if (dsp->ds_ident == NULL) {
1431		if (ddp->dd_kind != CTF_K_STRUCT &&
1432		    ddp->dd_kind != CTF_K_UNION && ddp->dd_kind != CTF_K_ENUM)
1433			xyerror(D_DECL_USELESS, "useless declaration\n");
1434
1435		dt_dprintf("type %s added as id %ld\n", dt_type_name(
1436		    ddp->dd_ctfp, ddp->dd_type, n1, sizeof (n1)), ddp->dd_type);
1437
1438		return (NULL);
1439	}
1440
1441	if (strchr(dsp->ds_ident, '`') != NULL) {
1442		xyerror(D_DECL_SCOPE, "D scoping operator may not be used in "
1443		    "a declaration name (%s)\n", dsp->ds_ident);
1444	}
1445
1446	/*
1447	 * If we are nested inside of a C include file, add the declaration to
1448	 * the C definition module; otherwise use the D definition module.
1449	 */
1450	if (yypcb->pcb_idepth != 0)
1451		dmp = dtp->dt_cdefs;
1452	else
1453		dmp = dtp->dt_ddefs;
1454
1455	/*
1456	 * If we see a global or static declaration of a function prototype,
1457	 * treat this as equivalent to a D extern declaration.
1458	 */
1459	if (ctf_type_kind(dtt.dtt_ctfp, dtt.dtt_type) == CTF_K_FUNCTION &&
1460	    (class == DT_DC_DEFAULT || class == DT_DC_STATIC))
1461		class = DT_DC_EXTERN;
1462
1463	switch (class) {
1464	case DT_DC_AUTO:
1465	case DT_DC_REGISTER:
1466	case DT_DC_STATIC:
1467		xyerror(D_DECL_BADCLASS, "specified storage class not "
1468		    "appropriate in D\n");
1469		/*NOTREACHED*/
1470
1471	case DT_DC_EXTERN: {
1472		dtrace_typeinfo_t ott;
1473		dtrace_syminfo_t dts;
1474		GElf_Sym sym;
1475
1476		int exists = dtrace_lookup_by_name(dtp,
1477		    dmp->dm_name, dsp->ds_ident, &sym, &dts) == 0;
1478
1479		if (exists && (dtrace_symbol_type(dtp, &sym, &dts, &ott) != 0 ||
1480		    ctf_type_cmp(dtt.dtt_ctfp, dtt.dtt_type,
1481		    ott.dtt_ctfp, ott.dtt_type) != 0)) {
1482			xyerror(D_DECL_IDRED, "identifier redeclared: %s`%s\n"
1483			    "\t current: %s\n\tprevious: %s\n",
1484			    dmp->dm_name, dsp->ds_ident,
1485			    dt_type_name(dtt.dtt_ctfp, dtt.dtt_type,
1486			    n1, sizeof (n1)),
1487			    dt_type_name(ott.dtt_ctfp, ott.dtt_type,
1488			    n2, sizeof (n2)));
1489		} else if (!exists && dt_module_extern(dtp, dmp,
1490		    dsp->ds_ident, &dtt) == NULL) {
1491			xyerror(D_UNKNOWN,
1492			    "failed to extern %s: %s\n", dsp->ds_ident,
1493			    dtrace_errmsg(dtp, dtrace_errno(dtp)));
1494		} else {
1495			dt_dprintf("extern %s`%s type=<%s>\n",
1496			    dmp->dm_name, dsp->ds_ident,
1497			    dt_type_name(dtt.dtt_ctfp, dtt.dtt_type,
1498			    n1, sizeof (n1)));
1499		}
1500		break;
1501	}
1502
1503	case DT_DC_TYPEDEF:
1504		if (dt_idstack_lookup(&yypcb->pcb_globals, dsp->ds_ident)) {
1505			xyerror(D_DECL_IDRED, "global variable identifier "
1506			    "redeclared: %s\n", dsp->ds_ident);
1507		}
1508
1509		if (ctf_lookup_by_name(dmp->dm_ctfp,
1510		    dsp->ds_ident) != CTF_ERR) {
1511			xyerror(D_DECL_IDRED,
1512			    "typedef redeclared: %s\n", dsp->ds_ident);
1513		}
1514
1515		/*
1516		 * If the source type for the typedef is not defined in the
1517		 * target container or its parent, copy the type to the target
1518		 * container and reset dtt_ctfp and dtt_type to the copy.
1519		 */
1520		if (dtt.dtt_ctfp != dmp->dm_ctfp &&
1521		    dtt.dtt_ctfp != ctf_parent_file(dmp->dm_ctfp)) {
1522
1523			dtt.dtt_type = ctf_add_type(dmp->dm_ctfp,
1524			    dtt.dtt_ctfp, dtt.dtt_type);
1525			dtt.dtt_ctfp = dmp->dm_ctfp;
1526
1527			if (dtt.dtt_type == CTF_ERR ||
1528			    ctf_update(dtt.dtt_ctfp) == CTF_ERR) {
1529				xyerror(D_UNKNOWN, "failed to copy typedef %s "
1530				    "source type: %s\n", dsp->ds_ident,
1531				    ctf_errmsg(ctf_errno(dtt.dtt_ctfp)));
1532			}
1533		}
1534
1535		type = ctf_add_typedef(dmp->dm_ctfp,
1536		    CTF_ADD_ROOT, dsp->ds_ident, dtt.dtt_type);
1537
1538		if (type == CTF_ERR || ctf_update(dmp->dm_ctfp) == CTF_ERR) {
1539			xyerror(D_UNKNOWN, "failed to typedef %s: %s\n",
1540			    dsp->ds_ident, ctf_errmsg(ctf_errno(dmp->dm_ctfp)));
1541		}
1542
1543		dt_dprintf("typedef %s added as id %ld\n", dsp->ds_ident, type);
1544		break;
1545
1546	default: {
1547		ctf_encoding_t cte;
1548		dt_idhash_t *dhp;
1549		dt_ident_t *idp;
1550		dt_node_t idn;
1551		int assc, idkind;
1552		uint_t id, kind;
1553		ushort_t idflags;
1554
1555		switch (class) {
1556		case DT_DC_THIS:
1557			dhp = yypcb->pcb_locals;
1558			idflags = DT_IDFLG_LOCAL;
1559			idp = dt_idhash_lookup(dhp, dsp->ds_ident);
1560			break;
1561		case DT_DC_SELF:
1562			dhp = dtp->dt_tls;
1563			idflags = DT_IDFLG_TLS;
1564			idp = dt_idhash_lookup(dhp, dsp->ds_ident);
1565			break;
1566		default:
1567			dhp = dtp->dt_globals;
1568			idflags = 0;
1569			idp = dt_idstack_lookup(
1570			    &yypcb->pcb_globals, dsp->ds_ident);
1571			break;
1572		}
1573
1574		if (ddp->dd_kind == CTF_K_ARRAY && ddp->dd_node == NULL) {
1575			xyerror(D_DECL_ARRNULL,
1576			    "array declaration requires array dimension or "
1577			    "tuple signature: %s\n", dsp->ds_ident);
1578		}
1579
1580		if (idp != NULL && idp->di_gen == 0) {
1581			xyerror(D_DECL_IDRED, "built-in identifier "
1582			    "redeclared: %s\n", idp->di_name);
1583		}
1584
1585		if (dtrace_lookup_by_type(dtp, DTRACE_OBJ_CDEFS,
1586		    dsp->ds_ident, NULL) == 0 ||
1587		    dtrace_lookup_by_type(dtp, DTRACE_OBJ_DDEFS,
1588		    dsp->ds_ident, NULL) == 0) {
1589			xyerror(D_DECL_IDRED, "typedef identifier "
1590			    "redeclared: %s\n", dsp->ds_ident);
1591		}
1592
1593		/*
1594		 * Cache some attributes of the decl to make the rest of this
1595		 * code simpler: if the decl is an array which is subscripted
1596		 * by a type rather than an integer, then it's an associative
1597		 * array (assc).  We then expect to match either DT_IDENT_ARRAY
1598		 * for associative arrays or DT_IDENT_SCALAR for anything else.
1599		 */
1600		assc = ddp->dd_kind == CTF_K_ARRAY &&
1601		    ddp->dd_node->dn_kind == DT_NODE_TYPE;
1602
1603		idkind = assc ? DT_IDENT_ARRAY : DT_IDENT_SCALAR;
1604
1605		/*
1606		 * Create a fake dt_node_t on the stack so we can determine the
1607		 * type of any matching identifier by assigning to this node.
1608		 * If the pre-existing ident has its di_type set, propagate
1609		 * the type by hand so as not to trigger a prototype check for
1610		 * arrays (yet); otherwise we use dt_ident_cook() on the ident
1611		 * to ensure it is fully initialized before looking at it.
1612		 */
1613		bzero(&idn, sizeof (dt_node_t));
1614
1615		if (idp != NULL && idp->di_type != CTF_ERR)
1616			dt_node_type_assign(&idn, idp->di_ctfp, idp->di_type,
1617			    B_FALSE);
1618		else if (idp != NULL)
1619			(void) dt_ident_cook(&idn, idp, NULL);
1620
1621		if (assc) {
1622			if (class == DT_DC_THIS) {
1623				xyerror(D_DECL_LOCASSC, "associative arrays "
1624				    "may not be declared as local variables:"
1625				    " %s\n", dsp->ds_ident);
1626			}
1627
1628			if (dt_decl_type(ddp->dd_next, &dtt) != 0)
1629				longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
1630		}
1631
1632		if (idp != NULL && (idp->di_kind != idkind ||
1633		    ctf_type_cmp(dtt.dtt_ctfp, dtt.dtt_type,
1634		    idn.dn_ctfp, idn.dn_type) != 0)) {
1635			xyerror(D_DECL_IDRED, "identifier redeclared: %s\n"
1636			    "\t current: %s %s\n\tprevious: %s %s\n",
1637			    dsp->ds_ident, dt_idkind_name(idkind),
1638			    dt_type_name(dtt.dtt_ctfp,
1639			    dtt.dtt_type, n1, sizeof (n1)),
1640			    dt_idkind_name(idp->di_kind),
1641			    dt_node_type_name(&idn, n2, sizeof (n2)));
1642
1643		} else if (idp != NULL && assc) {
1644			const dt_idsig_t *isp = idp->di_data;
1645			dt_node_t *dnp = ddp->dd_node;
1646			int argc = 0;
1647
1648			for (; dnp != NULL; dnp = dnp->dn_list, argc++) {
1649				const dt_node_t *pnp = &isp->dis_args[argc];
1650
1651				if (argc >= isp->dis_argc)
1652					continue; /* tuple length mismatch */
1653
1654				if (ctf_type_cmp(dnp->dn_ctfp, dnp->dn_type,
1655				    pnp->dn_ctfp, pnp->dn_type) == 0)
1656					continue;
1657
1658				xyerror(D_DECL_IDRED,
1659				    "identifier redeclared: %s\n"
1660				    "\t current: %s, key #%d of type %s\n"
1661				    "\tprevious: %s, key #%d of type %s\n",
1662				    dsp->ds_ident,
1663				    dt_idkind_name(idkind), argc + 1,
1664				    dt_node_type_name(dnp, n1, sizeof (n1)),
1665				    dt_idkind_name(idp->di_kind), argc + 1,
1666				    dt_node_type_name(pnp, n2, sizeof (n2)));
1667			}
1668
1669			if (isp->dis_argc != argc) {
1670				xyerror(D_DECL_IDRED,
1671				    "identifier redeclared: %s\n"
1672				    "\t current: %s of %s, tuple length %d\n"
1673				    "\tprevious: %s of %s, tuple length %d\n",
1674				    dsp->ds_ident, dt_idkind_name(idkind),
1675				    dt_type_name(dtt.dtt_ctfp, dtt.dtt_type,
1676				    n1, sizeof (n1)), argc,
1677				    dt_idkind_name(idp->di_kind),
1678				    dt_node_type_name(&idn, n2, sizeof (n2)),
1679				    isp->dis_argc);
1680			}
1681
1682		} else if (idp == NULL) {
1683			type = ctf_type_resolve(dtt.dtt_ctfp, dtt.dtt_type);
1684			kind = ctf_type_kind(dtt.dtt_ctfp, type);
1685
1686			switch (kind) {
1687			case CTF_K_INTEGER:
1688				if (ctf_type_encoding(dtt.dtt_ctfp, type,
1689				    &cte) == 0 && IS_VOID(cte)) {
1690					xyerror(D_DECL_VOIDOBJ, "cannot have "
1691					    "void object: %s\n", dsp->ds_ident);
1692				}
1693				break;
1694			case CTF_K_STRUCT:
1695			case CTF_K_UNION:
1696				if (ctf_type_size(dtt.dtt_ctfp, type) != 0)
1697					break; /* proceed to declaring */
1698				/*FALLTHRU*/
1699			case CTF_K_FORWARD:
1700				xyerror(D_DECL_INCOMPLETE,
1701				    "incomplete struct/union/enum %s: %s\n",
1702				    dt_type_name(dtt.dtt_ctfp, dtt.dtt_type,
1703				    n1, sizeof (n1)), dsp->ds_ident);
1704				/*NOTREACHED*/
1705			}
1706
1707			if (dt_idhash_nextid(dhp, &id) == -1) {
1708				xyerror(D_ID_OFLOW, "cannot create %s: limit "
1709				    "on number of %s variables exceeded\n",
1710				    dsp->ds_ident, dt_idhash_name(dhp));
1711			}
1712
1713			dt_dprintf("declare %s %s variable %s, id=%u\n",
1714			    dt_idhash_name(dhp), dt_idkind_name(idkind),
1715			    dsp->ds_ident, id);
1716
1717			idp = dt_idhash_insert(dhp, dsp->ds_ident, idkind,
1718			    idflags | DT_IDFLG_WRITE | DT_IDFLG_DECL, id,
1719			    _dtrace_defattr, 0, assc ? &dt_idops_assc :
1720			    &dt_idops_thaw, NULL, dtp->dt_gen);
1721
1722			if (idp == NULL)
1723				longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
1724
1725			dt_ident_type_assign(idp, dtt.dtt_ctfp, dtt.dtt_type);
1726
1727			/*
1728			 * If we are declaring an associative array, use our
1729			 * fake parse node to cook the new assoc identifier.
1730			 * This will force the ident code to instantiate the
1731			 * array type signature corresponding to the list of
1732			 * types pointed to by ddp->dd_node.  We also reset
1733			 * the identifier's attributes based upon the result.
1734			 */
1735			if (assc) {
1736				idp->di_attr =
1737				    dt_ident_cook(&idn, idp, &ddp->dd_node);
1738			}
1739		}
1740	}
1741
1742	} /* end of switch */
1743
1744	free(dsp->ds_ident);
1745	dsp->ds_ident = NULL;
1746
1747	return (NULL);
1748}
1749
1750dt_node_t *
1751dt_node_func(dt_node_t *dnp, dt_node_t *args)
1752{
1753	dt_ident_t *idp;
1754
1755	if (dnp->dn_kind != DT_NODE_IDENT) {
1756		xyerror(D_FUNC_IDENT,
1757		    "function designator is not of function type\n");
1758	}
1759
1760	idp = dt_idstack_lookup(&yypcb->pcb_globals, dnp->dn_string);
1761
1762	if (idp == NULL) {
1763		xyerror(D_FUNC_UNDEF,
1764		    "undefined function name: %s\n", dnp->dn_string);
1765	}
1766
1767	if (idp->di_kind != DT_IDENT_FUNC &&
1768	    idp->di_kind != DT_IDENT_AGGFUNC &&
1769	    idp->di_kind != DT_IDENT_ACTFUNC) {
1770		xyerror(D_FUNC_IDKIND, "%s '%s' may not be referenced as a "
1771		    "function\n", dt_idkind_name(idp->di_kind), idp->di_name);
1772	}
1773
1774	free(dnp->dn_string);
1775	dnp->dn_string = NULL;
1776
1777	dnp->dn_kind = DT_NODE_FUNC;
1778	dnp->dn_flags &= ~DT_NF_COOKED;
1779	dnp->dn_ident = idp;
1780	dnp->dn_args = args;
1781	dnp->dn_list = NULL;
1782
1783	return (dnp);
1784}
1785
1786/*
1787 * The offsetof() function is special because it takes a type name as an
1788 * argument.  It does not actually construct its own node; after looking up the
1789 * structure or union offset, we just return an integer node with the offset.
1790 */
1791dt_node_t *
1792dt_node_offsetof(dt_decl_t *ddp, char *s)
1793{
1794	dtrace_typeinfo_t dtt;
1795	dt_node_t dn;
1796	char *name;
1797	int err;
1798
1799	ctf_membinfo_t ctm;
1800	ctf_id_t type;
1801	uint_t kind;
1802
1803	name = strdupa(s);
1804	free(s);
1805
1806	err = dt_decl_type(ddp, &dtt);
1807	dt_decl_free(ddp);
1808
1809	if (err != 0)
1810		longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
1811
1812	type = ctf_type_resolve(dtt.dtt_ctfp, dtt.dtt_type);
1813	kind = ctf_type_kind(dtt.dtt_ctfp, type);
1814
1815	if (kind != CTF_K_STRUCT && kind != CTF_K_UNION) {
1816		xyerror(D_OFFSETOF_TYPE,
1817		    "offsetof operand must be a struct or union type\n");
1818	}
1819
1820	if (ctf_member_info(dtt.dtt_ctfp, type, name, &ctm) == CTF_ERR) {
1821		xyerror(D_UNKNOWN, "failed to determine offset of %s: %s\n",
1822		    name, ctf_errmsg(ctf_errno(dtt.dtt_ctfp)));
1823	}
1824
1825	bzero(&dn, sizeof (dn));
1826	dt_node_type_assign(&dn, dtt.dtt_ctfp, ctm.ctm_type, B_FALSE);
1827
1828	if (dn.dn_flags & DT_NF_BITFIELD) {
1829		xyerror(D_OFFSETOF_BITFIELD,
1830		    "cannot take offset of a bit-field: %s\n", name);
1831	}
1832
1833	return (dt_node_int(ctm.ctm_offset / NBBY));
1834}
1835
1836dt_node_t *
1837dt_node_op1(int op, dt_node_t *cp)
1838{
1839	dt_node_t *dnp;
1840
1841	if (cp->dn_kind == DT_NODE_INT) {
1842		switch (op) {
1843		case DT_TOK_INEG:
1844			/*
1845			 * If we're negating an unsigned integer, zero out any
1846			 * extra top bits to truncate the value to the size of
1847			 * the effective type determined by dt_node_int().
1848			 */
1849			cp->dn_value = -cp->dn_value;
1850			if (!(cp->dn_flags & DT_NF_SIGNED)) {
1851				cp->dn_value &= ~0ULL >>
1852				    (64 - dt_node_type_size(cp) * NBBY);
1853			}
1854			/*FALLTHRU*/
1855		case DT_TOK_IPOS:
1856			return (cp);
1857		case DT_TOK_BNEG:
1858			cp->dn_value = ~cp->dn_value;
1859			return (cp);
1860		case DT_TOK_LNEG:
1861			cp->dn_value = !cp->dn_value;
1862			return (cp);
1863		}
1864	}
1865
1866	/*
1867	 * If sizeof is applied to a type_name or string constant, we can
1868	 * transform 'cp' into an integer constant in the node construction
1869	 * pass so that it can then be used for arithmetic in this pass.
1870	 */
1871	if (op == DT_TOK_SIZEOF &&
1872	    (cp->dn_kind == DT_NODE_STRING || cp->dn_kind == DT_NODE_TYPE)) {
1873		dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1874		size_t size = dt_node_type_size(cp);
1875
1876		if (size == 0) {
1877			xyerror(D_SIZEOF_TYPE, "cannot apply sizeof to an "
1878			    "operand of unknown size\n");
1879		}
1880
1881		dt_node_type_assign(cp, dtp->dt_ddefs->dm_ctfp,
1882		    ctf_lookup_by_name(dtp->dt_ddefs->dm_ctfp, "size_t"),
1883		    B_FALSE);
1884
1885		cp->dn_kind = DT_NODE_INT;
1886		cp->dn_op = DT_TOK_INT;
1887		cp->dn_value = size;
1888
1889		return (cp);
1890	}
1891
1892	dnp = dt_node_alloc(DT_NODE_OP1);
1893	assert(op <= USHRT_MAX);
1894	dnp->dn_op = (ushort_t)op;
1895	dnp->dn_child = cp;
1896
1897	return (dnp);
1898}
1899
1900/*
1901 * If an integer constant is being cast to another integer type, we can
1902 * perform the cast as part of integer constant folding in this pass. We must
1903 * take action when the integer is being cast to a smaller type or if it is
1904 * changing signed-ness. If so, we first shift rp's bits bits high (losing
1905 * excess bits if narrowing) and then shift them down with either a logical
1906 * shift (unsigned) or arithmetic shift (signed).
1907 */
1908static void
1909dt_cast(dt_node_t *lp, dt_node_t *rp)
1910{
1911	size_t srcsize = dt_node_type_size(rp);
1912	size_t dstsize = dt_node_type_size(lp);
1913
1914	if (dstsize < srcsize) {
1915		int n = (sizeof (uint64_t) - dstsize) * NBBY;
1916		rp->dn_value <<= n;
1917		rp->dn_value >>= n;
1918	} else if (dstsize > srcsize) {
1919		int n = (sizeof (uint64_t) - srcsize) * NBBY;
1920		int s = (dstsize - srcsize) * NBBY;
1921
1922		rp->dn_value <<= n;
1923		if (rp->dn_flags & DT_NF_SIGNED) {
1924			rp->dn_value = (intmax_t)rp->dn_value >> s;
1925			rp->dn_value >>= n - s;
1926		} else {
1927			rp->dn_value >>= n;
1928		}
1929	}
1930}
1931
1932dt_node_t *
1933dt_node_op2(int op, dt_node_t *lp, dt_node_t *rp)
1934{
1935	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
1936	dt_node_t *dnp;
1937
1938	/*
1939	 * First we check for operations that are illegal -- namely those that
1940	 * might result in integer division by zero, and abort if one is found.
1941	 */
1942	if (rp->dn_kind == DT_NODE_INT && rp->dn_value == 0 &&
1943	    (op == DT_TOK_MOD || op == DT_TOK_DIV ||
1944	    op == DT_TOK_MOD_EQ || op == DT_TOK_DIV_EQ))
1945		xyerror(D_DIV_ZERO, "expression contains division by zero\n");
1946
1947	/*
1948	 * If both children are immediate values, we can just perform inline
1949	 * calculation and return a new immediate node with the result.
1950	 */
1951	if (lp->dn_kind == DT_NODE_INT && rp->dn_kind == DT_NODE_INT) {
1952		uintmax_t l = lp->dn_value;
1953		uintmax_t r = rp->dn_value;
1954
1955		dnp = dt_node_int(0); /* allocate new integer node for result */
1956
1957		switch (op) {
1958		case DT_TOK_LOR:
1959			dnp->dn_value = l || r;
1960			dt_node_type_assign(dnp,
1961			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
1962			break;
1963		case DT_TOK_LXOR:
1964			dnp->dn_value = (l != 0) ^ (r != 0);
1965			dt_node_type_assign(dnp,
1966			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
1967			break;
1968		case DT_TOK_LAND:
1969			dnp->dn_value = l && r;
1970			dt_node_type_assign(dnp,
1971			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
1972			break;
1973		case DT_TOK_BOR:
1974			dnp->dn_value = l | r;
1975			dt_node_promote(lp, rp, dnp);
1976			break;
1977		case DT_TOK_XOR:
1978			dnp->dn_value = l ^ r;
1979			dt_node_promote(lp, rp, dnp);
1980			break;
1981		case DT_TOK_BAND:
1982			dnp->dn_value = l & r;
1983			dt_node_promote(lp, rp, dnp);
1984			break;
1985		case DT_TOK_EQU:
1986			dnp->dn_value = l == r;
1987			dt_node_type_assign(dnp,
1988			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
1989			break;
1990		case DT_TOK_NEQ:
1991			dnp->dn_value = l != r;
1992			dt_node_type_assign(dnp,
1993			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
1994			break;
1995		case DT_TOK_LT:
1996			dt_node_promote(lp, rp, dnp);
1997			if (dnp->dn_flags & DT_NF_SIGNED)
1998				dnp->dn_value = (intmax_t)l < (intmax_t)r;
1999			else
2000				dnp->dn_value = l < r;
2001			dt_node_type_assign(dnp,
2002			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
2003			break;
2004		case DT_TOK_LE:
2005			dt_node_promote(lp, rp, dnp);
2006			if (dnp->dn_flags & DT_NF_SIGNED)
2007				dnp->dn_value = (intmax_t)l <= (intmax_t)r;
2008			else
2009				dnp->dn_value = l <= r;
2010			dt_node_type_assign(dnp,
2011			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
2012			break;
2013		case DT_TOK_GT:
2014			dt_node_promote(lp, rp, dnp);
2015			if (dnp->dn_flags & DT_NF_SIGNED)
2016				dnp->dn_value = (intmax_t)l > (intmax_t)r;
2017			else
2018				dnp->dn_value = l > r;
2019			dt_node_type_assign(dnp,
2020			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
2021			break;
2022		case DT_TOK_GE:
2023			dt_node_promote(lp, rp, dnp);
2024			if (dnp->dn_flags & DT_NF_SIGNED)
2025				dnp->dn_value = (intmax_t)l >= (intmax_t)r;
2026			else
2027				dnp->dn_value = l >= r;
2028			dt_node_type_assign(dnp,
2029			    DT_INT_CTFP(dtp), DT_INT_TYPE(dtp), B_FALSE);
2030			break;
2031		case DT_TOK_LSH:
2032			dnp->dn_value = l << r;
2033			dt_node_type_propagate(lp, dnp);
2034			dt_node_attr_assign(rp,
2035			    dt_attr_min(lp->dn_attr, rp->dn_attr));
2036			break;
2037		case DT_TOK_RSH:
2038			dnp->dn_value = l >> r;
2039			dt_node_type_propagate(lp, dnp);
2040			dt_node_attr_assign(rp,
2041			    dt_attr_min(lp->dn_attr, rp->dn_attr));
2042			break;
2043		case DT_TOK_ADD:
2044			dnp->dn_value = l + r;
2045			dt_node_promote(lp, rp, dnp);
2046			break;
2047		case DT_TOK_SUB:
2048			dnp->dn_value = l - r;
2049			dt_node_promote(lp, rp, dnp);
2050			break;
2051		case DT_TOK_MUL:
2052			dnp->dn_value = l * r;
2053			dt_node_promote(lp, rp, dnp);
2054			break;
2055		case DT_TOK_DIV:
2056			dt_node_promote(lp, rp, dnp);
2057			if (dnp->dn_flags & DT_NF_SIGNED)
2058				dnp->dn_value = (intmax_t)l / (intmax_t)r;
2059			else
2060				dnp->dn_value = l / r;
2061			break;
2062		case DT_TOK_MOD:
2063			dt_node_promote(lp, rp, dnp);
2064			if (dnp->dn_flags & DT_NF_SIGNED)
2065				dnp->dn_value = (intmax_t)l % (intmax_t)r;
2066			else
2067				dnp->dn_value = l % r;
2068			break;
2069		default:
2070			dt_node_free(dnp);
2071			dnp = NULL;
2072		}
2073
2074		if (dnp != NULL) {
2075			dt_node_free(lp);
2076			dt_node_free(rp);
2077			return (dnp);
2078		}
2079	}
2080
2081	if (op == DT_TOK_LPAR && rp->dn_kind == DT_NODE_INT &&
2082	    dt_node_is_integer(lp)) {
2083		dt_cast(lp, rp);
2084		dt_node_type_propagate(lp, rp);
2085		dt_node_attr_assign(rp, dt_attr_min(lp->dn_attr, rp->dn_attr));
2086		dt_node_free(lp);
2087
2088		return (rp);
2089	}
2090
2091	/*
2092	 * If no immediate optimizations are available, create an new OP2 node
2093	 * and glue the left and right children into place and return.
2094	 */
2095	dnp = dt_node_alloc(DT_NODE_OP2);
2096	assert(op <= USHRT_MAX);
2097	dnp->dn_op = (ushort_t)op;
2098	dnp->dn_left = lp;
2099	dnp->dn_right = rp;
2100
2101	return (dnp);
2102}
2103
2104dt_node_t *
2105dt_node_op3(dt_node_t *expr, dt_node_t *lp, dt_node_t *rp)
2106{
2107	dt_node_t *dnp;
2108
2109	if (expr->dn_kind == DT_NODE_INT)
2110		return (expr->dn_value != 0 ? lp : rp);
2111
2112	dnp = dt_node_alloc(DT_NODE_OP3);
2113	dnp->dn_op = DT_TOK_QUESTION;
2114	dnp->dn_expr = expr;
2115	dnp->dn_left = lp;
2116	dnp->dn_right = rp;
2117
2118	return (dnp);
2119}
2120
2121dt_node_t *
2122dt_node_statement(dt_node_t *expr)
2123{
2124	dt_node_t *dnp;
2125
2126	if (expr->dn_kind == DT_NODE_AGG)
2127		return (expr);
2128
2129	if (expr->dn_kind == DT_NODE_FUNC &&
2130	    expr->dn_ident->di_kind == DT_IDENT_ACTFUNC)
2131		dnp = dt_node_alloc(DT_NODE_DFUNC);
2132	else
2133		dnp = dt_node_alloc(DT_NODE_DEXPR);
2134
2135	dnp->dn_expr = expr;
2136	return (dnp);
2137}
2138
2139dt_node_t *
2140dt_node_if(dt_node_t *pred, dt_node_t *acts, dt_node_t *else_acts)
2141{
2142	dt_node_t *dnp = dt_node_alloc(DT_NODE_IF);
2143	dnp->dn_conditional = pred;
2144	dnp->dn_body = acts;
2145	dnp->dn_alternate_body = else_acts;
2146
2147	return (dnp);
2148}
2149
2150dt_node_t *
2151dt_node_pdesc_by_name(char *spec)
2152{
2153	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2154	dt_node_t *dnp;
2155
2156	if (spec == NULL)
2157		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2158
2159	dnp = dt_node_alloc(DT_NODE_PDESC);
2160	dnp->dn_spec = spec;
2161	dnp->dn_desc = malloc(sizeof (dtrace_probedesc_t));
2162
2163	if (dnp->dn_desc == NULL)
2164		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2165
2166	if (dtrace_xstr2desc(dtp, yypcb->pcb_pspec, dnp->dn_spec,
2167	    yypcb->pcb_sargc, yypcb->pcb_sargv, dnp->dn_desc) != 0) {
2168		xyerror(D_PDESC_INVAL, "invalid probe description \"%s\": %s\n",
2169		    dnp->dn_spec, dtrace_errmsg(dtp, dtrace_errno(dtp)));
2170	}
2171
2172	free(dnp->dn_spec);
2173	dnp->dn_spec = NULL;
2174
2175	return (dnp);
2176}
2177
2178dt_node_t *
2179dt_node_pdesc_by_id(uintmax_t id)
2180{
2181	static const char *const names[] = {
2182		"providers", "modules", "functions"
2183	};
2184
2185	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2186	dt_node_t *dnp = dt_node_alloc(DT_NODE_PDESC);
2187
2188	if ((dnp->dn_desc = malloc(sizeof (dtrace_probedesc_t))) == NULL)
2189		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2190
2191	if (id > UINT_MAX) {
2192		xyerror(D_PDESC_INVAL, "identifier %llu exceeds maximum "
2193		    "probe id\n", (u_longlong_t)id);
2194	}
2195
2196	if (yypcb->pcb_pspec != DTRACE_PROBESPEC_NAME) {
2197		xyerror(D_PDESC_INVAL, "probe identifier %llu not permitted "
2198		    "when specifying %s\n", (u_longlong_t)id,
2199		    names[yypcb->pcb_pspec]);
2200	}
2201
2202	if (dtrace_id2desc(dtp, (dtrace_id_t)id, dnp->dn_desc) != 0) {
2203		xyerror(D_PDESC_INVAL, "invalid probe identifier %llu: %s\n",
2204		    (u_longlong_t)id, dtrace_errmsg(dtp, dtrace_errno(dtp)));
2205	}
2206
2207	return (dnp);
2208}
2209
2210dt_node_t *
2211dt_node_clause(dt_node_t *pdescs, dt_node_t *pred, dt_node_t *acts)
2212{
2213	dt_node_t *dnp = dt_node_alloc(DT_NODE_CLAUSE);
2214
2215	dnp->dn_pdescs = pdescs;
2216	dnp->dn_pred = pred;
2217	dnp->dn_acts = acts;
2218
2219	return (dnp);
2220}
2221
2222dt_node_t *
2223dt_node_inline(dt_node_t *expr)
2224{
2225	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2226	dt_scope_t *dsp = &yypcb->pcb_dstack;
2227	dt_decl_t *ddp = dt_decl_top();
2228
2229	char n[DT_TYPE_NAMELEN];
2230	dtrace_typeinfo_t dtt;
2231
2232	dt_ident_t *idp, *rdp;
2233	dt_idnode_t *inp;
2234	dt_node_t *dnp;
2235
2236	if (dt_decl_type(ddp, &dtt) != 0)
2237		longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
2238
2239	if (dsp->ds_class != DT_DC_DEFAULT) {
2240		xyerror(D_DECL_BADCLASS, "specified storage class not "
2241		    "appropriate for inline declaration\n");
2242	}
2243
2244	if (dsp->ds_ident == NULL)
2245		xyerror(D_DECL_USELESS, "inline declaration requires a name\n");
2246
2247	if ((idp = dt_idstack_lookup(
2248	    &yypcb->pcb_globals, dsp->ds_ident)) != NULL) {
2249		xyerror(D_DECL_IDRED, "identifier redefined: %s\n\t current: "
2250		    "inline definition\n\tprevious: %s %s\n",
2251		    idp->di_name, dt_idkind_name(idp->di_kind),
2252		    (idp->di_flags & DT_IDFLG_INLINE) ? "inline" : "");
2253	}
2254
2255	/*
2256	 * If we are declaring an inlined array, verify that we have a tuple
2257	 * signature, and then recompute 'dtt' as the array's value type.
2258	 */
2259	if (ddp->dd_kind == CTF_K_ARRAY) {
2260		if (ddp->dd_node == NULL) {
2261			xyerror(D_DECL_ARRNULL, "inline declaration requires "
2262			    "array tuple signature: %s\n", dsp->ds_ident);
2263		}
2264
2265		if (ddp->dd_node->dn_kind != DT_NODE_TYPE) {
2266			xyerror(D_DECL_ARRNULL, "inline declaration cannot be "
2267			    "of scalar array type: %s\n", dsp->ds_ident);
2268		}
2269
2270		if (dt_decl_type(ddp->dd_next, &dtt) != 0)
2271			longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
2272	}
2273
2274	/*
2275	 * If the inline identifier is not defined, then create it with the
2276	 * orphan flag set.  We do not insert the identifier into dt_globals
2277	 * until we have successfully cooked the right-hand expression, below.
2278	 */
2279	dnp = dt_node_alloc(DT_NODE_INLINE);
2280	dt_node_type_assign(dnp, dtt.dtt_ctfp, dtt.dtt_type, B_FALSE);
2281	dt_node_attr_assign(dnp, _dtrace_defattr);
2282
2283	if (dt_node_is_void(dnp)) {
2284		xyerror(D_DECL_VOIDOBJ,
2285		    "cannot declare void inline: %s\n", dsp->ds_ident);
2286	}
2287
2288	if (ctf_type_kind(dnp->dn_ctfp, ctf_type_resolve(
2289	    dnp->dn_ctfp, dnp->dn_type)) == CTF_K_FORWARD) {
2290		xyerror(D_DECL_INCOMPLETE,
2291		    "incomplete struct/union/enum %s: %s\n",
2292		    dt_node_type_name(dnp, n, sizeof (n)), dsp->ds_ident);
2293	}
2294
2295	if ((inp = malloc(sizeof (dt_idnode_t))) == NULL)
2296		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2297
2298	bzero(inp, sizeof (dt_idnode_t));
2299
2300	idp = dnp->dn_ident = dt_ident_create(dsp->ds_ident,
2301	    ddp->dd_kind == CTF_K_ARRAY ? DT_IDENT_ARRAY : DT_IDENT_SCALAR,
2302	    DT_IDFLG_INLINE | DT_IDFLG_REF | DT_IDFLG_DECL | DT_IDFLG_ORPHAN, 0,
2303	    _dtrace_defattr, 0, &dt_idops_inline, inp, dtp->dt_gen);
2304
2305	if (idp == NULL) {
2306		free(inp);
2307		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2308	}
2309
2310	/*
2311	 * If we're inlining an associative array, create a private identifier
2312	 * hash containing the named parameters and store it in inp->din_hash.
2313	 * We then push this hash on to the top of the pcb_globals stack.
2314	 */
2315	if (ddp->dd_kind == CTF_K_ARRAY) {
2316		dt_idnode_t *pinp;
2317		dt_ident_t *pidp;
2318		dt_node_t *pnp;
2319		uint_t i = 0;
2320
2321		for (pnp = ddp->dd_node; pnp != NULL; pnp = pnp->dn_list)
2322			i++; /* count up parameters for din_argv[] */
2323
2324		inp->din_hash = dt_idhash_create("inline args", NULL, 0, 0);
2325		inp->din_argv = calloc(i, sizeof (dt_ident_t *));
2326
2327		if (inp->din_hash == NULL || inp->din_argv == NULL)
2328			longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2329
2330		/*
2331		 * Create an identifier for each parameter as a scalar inline,
2332		 * and store it in din_hash and in position in din_argv[].  The
2333		 * parameter identifiers also use dt_idops_inline, but we leave
2334		 * the dt_idnode_t argument 'pinp' zeroed.  This will be filled
2335		 * in by the code generation pass with references to the args.
2336		 */
2337		for (i = 0, pnp = ddp->dd_node;
2338		    pnp != NULL; pnp = pnp->dn_list, i++) {
2339
2340			if (pnp->dn_string == NULL)
2341				continue; /* ignore anonymous parameters */
2342
2343			if ((pinp = malloc(sizeof (dt_idnode_t))) == NULL)
2344				longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2345
2346			pidp = dt_idhash_insert(inp->din_hash, pnp->dn_string,
2347			    DT_IDENT_SCALAR, DT_IDFLG_DECL | DT_IDFLG_INLINE, 0,
2348			    _dtrace_defattr, 0, &dt_idops_inline,
2349			    pinp, dtp->dt_gen);
2350
2351			if (pidp == NULL) {
2352				free(pinp);
2353				longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2354			}
2355
2356			inp->din_argv[i] = pidp;
2357			bzero(pinp, sizeof (dt_idnode_t));
2358			dt_ident_type_assign(pidp, pnp->dn_ctfp, pnp->dn_type);
2359		}
2360
2361		dt_idstack_push(&yypcb->pcb_globals, inp->din_hash);
2362	}
2363
2364	/*
2365	 * Unlike most constructors, we need to explicitly cook the right-hand
2366	 * side of the inline definition immediately to prevent recursion.  If
2367	 * the right-hand side uses the inline itself, the cook will fail.
2368	 */
2369	expr = dt_node_cook(expr, DT_IDFLG_REF);
2370
2371	if (ddp->dd_kind == CTF_K_ARRAY)
2372		dt_idstack_pop(&yypcb->pcb_globals, inp->din_hash);
2373
2374	/*
2375	 * Set the type, attributes, and flags for the inline.  If the right-
2376	 * hand expression has an identifier, propagate its flags.  Then cook
2377	 * the identifier to fully initialize it: if we're declaring an inline
2378	 * associative array this will construct a type signature from 'ddp'.
2379	 */
2380	if (dt_node_is_dynamic(expr))
2381		rdp = dt_ident_resolve(expr->dn_ident);
2382	else if (expr->dn_kind == DT_NODE_VAR || expr->dn_kind == DT_NODE_SYM)
2383		rdp = expr->dn_ident;
2384	else
2385		rdp = NULL;
2386
2387	if (rdp != NULL) {
2388		idp->di_flags |= (rdp->di_flags &
2389		    (DT_IDFLG_WRITE | DT_IDFLG_USER | DT_IDFLG_PRIM));
2390	}
2391
2392	idp->di_attr = dt_attr_min(_dtrace_defattr, expr->dn_attr);
2393	dt_ident_type_assign(idp, dtt.dtt_ctfp, dtt.dtt_type);
2394	(void) dt_ident_cook(dnp, idp, &ddp->dd_node);
2395
2396	/*
2397	 * Store the parse tree nodes for 'expr' inside of idp->di_data ('inp')
2398	 * so that they will be preserved with this identifier.  Then pop the
2399	 * inline declaration from the declaration stack and restore the lexer.
2400	 */
2401	inp->din_list = yypcb->pcb_list;
2402	inp->din_root = expr;
2403
2404	dt_decl_free(dt_decl_pop());
2405	yybegin(YYS_CLAUSE);
2406
2407	/*
2408	 * Finally, insert the inline identifier into dt_globals to make it
2409	 * visible, and then cook 'dnp' to check its type against 'expr'.
2410	 */
2411	dt_idhash_xinsert(dtp->dt_globals, idp);
2412	return (dt_node_cook(dnp, DT_IDFLG_REF));
2413}
2414
2415dt_node_t *
2416dt_node_member(dt_decl_t *ddp, char *name, dt_node_t *expr)
2417{
2418	dtrace_typeinfo_t dtt;
2419	dt_node_t *dnp;
2420	int err;
2421
2422	if (ddp != NULL) {
2423		err = dt_decl_type(ddp, &dtt);
2424		dt_decl_free(ddp);
2425
2426		if (err != 0)
2427			longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
2428	}
2429
2430	dnp = dt_node_alloc(DT_NODE_MEMBER);
2431	dnp->dn_membname = name;
2432	dnp->dn_membexpr = expr;
2433
2434	if (ddp != NULL)
2435		dt_node_type_assign(dnp, dtt.dtt_ctfp, dtt.dtt_type,
2436		    dtt.dtt_flags);
2437
2438	return (dnp);
2439}
2440
2441dt_node_t *
2442dt_node_xlator(dt_decl_t *ddp, dt_decl_t *sdp, char *name, dt_node_t *members)
2443{
2444	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2445	dtrace_typeinfo_t src, dst;
2446	dt_node_t sn, dn;
2447	dt_xlator_t *dxp;
2448	dt_node_t *dnp;
2449	int edst, esrc;
2450	uint_t kind;
2451
2452	char n1[DT_TYPE_NAMELEN];
2453	char n2[DT_TYPE_NAMELEN];
2454
2455	edst = dt_decl_type(ddp, &dst);
2456	dt_decl_free(ddp);
2457
2458	esrc = dt_decl_type(sdp, &src);
2459	dt_decl_free(sdp);
2460
2461	if (edst != 0 || esrc != 0) {
2462		free(name);
2463		longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
2464	}
2465
2466	bzero(&sn, sizeof (sn));
2467	dt_node_type_assign(&sn, src.dtt_ctfp, src.dtt_type, B_FALSE);
2468
2469	bzero(&dn, sizeof (dn));
2470	dt_node_type_assign(&dn, dst.dtt_ctfp, dst.dtt_type, B_FALSE);
2471
2472	if (dt_xlator_lookup(dtp, &sn, &dn, DT_XLATE_EXACT) != NULL) {
2473		xyerror(D_XLATE_REDECL,
2474		    "translator from %s to %s has already been declared\n",
2475		    dt_node_type_name(&sn, n1, sizeof (n1)),
2476		    dt_node_type_name(&dn, n2, sizeof (n2)));
2477	}
2478
2479	kind = ctf_type_kind(dst.dtt_ctfp,
2480	    ctf_type_resolve(dst.dtt_ctfp, dst.dtt_type));
2481
2482	if (kind == CTF_K_FORWARD) {
2483		xyerror(D_XLATE_SOU, "incomplete struct/union/enum %s\n",
2484		    dt_type_name(dst.dtt_ctfp, dst.dtt_type, n1, sizeof (n1)));
2485	}
2486
2487	if (kind != CTF_K_STRUCT && kind != CTF_K_UNION) {
2488		xyerror(D_XLATE_SOU,
2489		    "translator output type must be a struct or union\n");
2490	}
2491
2492	dxp = dt_xlator_create(dtp, &src, &dst, name, members, yypcb->pcb_list);
2493	yybegin(YYS_CLAUSE);
2494	free(name);
2495
2496	if (dxp == NULL)
2497		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2498
2499	dnp = dt_node_alloc(DT_NODE_XLATOR);
2500	dnp->dn_xlator = dxp;
2501	dnp->dn_members = members;
2502
2503	return (dt_node_cook(dnp, DT_IDFLG_REF));
2504}
2505
2506dt_node_t *
2507dt_node_probe(char *s, int protoc, dt_node_t *nargs, dt_node_t *xargs)
2508{
2509	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2510	int nargc, xargc;
2511	dt_node_t *dnp;
2512
2513	size_t len = strlen(s) + 3; /* +3 for :: and \0 */
2514	char *name = alloca(len);
2515
2516	(void) snprintf(name, len, "::%s", s);
2517	(void) strhyphenate(name);
2518	free(s);
2519
2520	if (strchr(name, '`') != NULL) {
2521		xyerror(D_PROV_BADNAME, "probe name may not "
2522		    "contain scoping operator: %s\n", name);
2523	}
2524
2525	if (strlen(name) - 2 >= DTRACE_NAMELEN) {
2526		xyerror(D_PROV_BADNAME, "probe name may not exceed %d "
2527		    "characters: %s\n", DTRACE_NAMELEN - 1, name);
2528	}
2529
2530	dnp = dt_node_alloc(DT_NODE_PROBE);
2531
2532	dnp->dn_ident = dt_ident_create(name, DT_IDENT_PROBE,
2533	    DT_IDFLG_ORPHAN, DTRACE_IDNONE, _dtrace_defattr, 0,
2534	    &dt_idops_probe, NULL, dtp->dt_gen);
2535
2536	nargc = dt_decl_prototype(nargs, nargs,
2537	    "probe input", DT_DP_VOID | DT_DP_ANON);
2538
2539	xargc = dt_decl_prototype(xargs, nargs,
2540	    "probe output", DT_DP_VOID);
2541
2542	if (nargc > UINT8_MAX) {
2543		xyerror(D_PROV_PRARGLEN, "probe %s input prototype exceeds %u "
2544		    "parameters: %d params used\n", name, UINT8_MAX, nargc);
2545	}
2546
2547	if (xargc > UINT8_MAX) {
2548		xyerror(D_PROV_PRARGLEN, "probe %s output prototype exceeds %u "
2549		    "parameters: %d params used\n", name, UINT8_MAX, xargc);
2550	}
2551
2552	if (dnp->dn_ident == NULL || dt_probe_create(dtp,
2553	    dnp->dn_ident, protoc, nargs, nargc, xargs, xargc) == NULL)
2554		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2555
2556	return (dnp);
2557}
2558
2559dt_node_t *
2560dt_node_provider(char *name, dt_node_t *probes)
2561{
2562	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2563	dt_node_t *dnp = dt_node_alloc(DT_NODE_PROVIDER);
2564	dt_node_t *lnp;
2565	size_t len;
2566
2567	dnp->dn_provname = name;
2568	dnp->dn_probes = probes;
2569
2570	if (strchr(name, '`') != NULL) {
2571		dnerror(dnp, D_PROV_BADNAME, "provider name may not "
2572		    "contain scoping operator: %s\n", name);
2573	}
2574
2575	if ((len = strlen(name)) >= DTRACE_PROVNAMELEN) {
2576		dnerror(dnp, D_PROV_BADNAME, "provider name may not exceed %d "
2577		    "characters: %s\n", DTRACE_PROVNAMELEN - 1, name);
2578	}
2579
2580	if (isdigit(name[len - 1])) {
2581		dnerror(dnp, D_PROV_BADNAME, "provider name may not "
2582		    "end with a digit: %s\n", name);
2583	}
2584
2585	/*
2586	 * Check to see if the provider is already defined or visible through
2587	 * dtrace(7D).  If so, set dn_provred to treat it as a re-declaration.
2588	 * If not, create a new provider and set its interface-only flag.  This
2589	 * flag may be cleared later by calls made to dt_probe_declare().
2590	 */
2591	if ((dnp->dn_provider = dt_provider_lookup(dtp, name)) != NULL)
2592		dnp->dn_provred = B_TRUE;
2593	else if ((dnp->dn_provider = dt_provider_create(dtp, name)) == NULL)
2594		longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2595	else
2596		dnp->dn_provider->pv_flags |= DT_PROVIDER_INTF;
2597
2598	/*
2599	 * Store all parse nodes created since we consumed the DT_KEY_PROVIDER
2600	 * token with the provider and then restore our lexing state to CLAUSE.
2601	 * Note that if dnp->dn_provred is true, we may end up storing dups of
2602	 * a provider's interface and implementation: we eat this space because
2603	 * the implementation will likely need to redeclare probe members, and
2604	 * therefore may result in those member nodes becoming persistent.
2605	 */
2606	for (lnp = yypcb->pcb_list; lnp->dn_link != NULL; lnp = lnp->dn_link)
2607		continue; /* skip to end of allocation list */
2608
2609	lnp->dn_link = dnp->dn_provider->pv_nodes;
2610	dnp->dn_provider->pv_nodes = yypcb->pcb_list;
2611
2612	yybegin(YYS_CLAUSE);
2613	return (dnp);
2614}
2615
2616dt_node_t *
2617dt_node_program(dt_node_t *lnp)
2618{
2619	dt_node_t *dnp = dt_node_alloc(DT_NODE_PROG);
2620	dnp->dn_list = lnp;
2621	return (dnp);
2622}
2623
2624/*
2625 * This function provides the underlying implementation of cooking an
2626 * identifier given its node, a hash of dynamic identifiers, an identifier
2627 * kind, and a boolean flag indicating whether we are allowed to instantiate
2628 * a new identifier if the string is not found.  This function is either
2629 * called from dt_cook_ident(), below, or directly by the various cooking
2630 * routines that are allowed to instantiate identifiers (e.g. op2 TOK_ASGN).
2631 */
2632static void
2633dt_xcook_ident(dt_node_t *dnp, dt_idhash_t *dhp, uint_t idkind, int create)
2634{
2635	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2636	const char *sname = dt_idhash_name(dhp);
2637	int uref = 0;
2638
2639	dtrace_attribute_t attr = _dtrace_defattr;
2640	dt_ident_t *idp;
2641	dtrace_syminfo_t dts;
2642	GElf_Sym sym;
2643
2644	const char *scope, *mark;
2645	uchar_t dnkind;
2646	char *name;
2647
2648	/*
2649	 * Look for scoping marks in the identifier.  If one is found, set our
2650	 * scope to either DTRACE_OBJ_KMODS or UMODS or to the first part of
2651	 * the string that specifies the scope using an explicit module name.
2652	 * If two marks in a row are found, set 'uref' (user symbol reference).
2653	 * Otherwise we set scope to DTRACE_OBJ_EXEC, indicating that normal
2654	 * scope is desired and we should search the specified idhash.
2655	 */
2656	if ((name = strrchr(dnp->dn_string, '`')) != NULL) {
2657		if (name > dnp->dn_string && name[-1] == '`') {
2658			uref++;
2659			name[-1] = '\0';
2660		}
2661
2662		if (name == dnp->dn_string + uref)
2663			scope = uref ? DTRACE_OBJ_UMODS : DTRACE_OBJ_KMODS;
2664		else
2665			scope = dnp->dn_string;
2666
2667		*name++ = '\0'; /* leave name pointing after scoping mark */
2668		dnkind = DT_NODE_VAR;
2669
2670	} else if (idkind == DT_IDENT_AGG) {
2671		scope = DTRACE_OBJ_EXEC;
2672		name = dnp->dn_string + 1;
2673		dnkind = DT_NODE_AGG;
2674	} else {
2675		scope = DTRACE_OBJ_EXEC;
2676		name = dnp->dn_string;
2677		dnkind = DT_NODE_VAR;
2678	}
2679
2680	/*
2681	 * If create is set to false, and we fail our idhash lookup, preset
2682	 * the errno code to EDT_NOVAR for our final error message below.
2683	 * If we end up calling dtrace_lookup_by_name(), it will reset the
2684	 * errno appropriately and that error will be reported instead.
2685	 */
2686	(void) dt_set_errno(dtp, EDT_NOVAR);
2687	mark = uref ? "``" : "`";
2688
2689	if (scope == DTRACE_OBJ_EXEC && (
2690	    (dhp != dtp->dt_globals &&
2691	    (idp = dt_idhash_lookup(dhp, name)) != NULL) ||
2692	    (dhp == dtp->dt_globals &&
2693	    (idp = dt_idstack_lookup(&yypcb->pcb_globals, name)) != NULL))) {
2694		/*
2695		 * Check that we are referencing the ident in the manner that
2696		 * matches its type if this is a global lookup.  In the TLS or
2697		 * local case, we don't know how the ident will be used until
2698		 * the time operator -> is seen; more parsing is needed.
2699		 */
2700		if (idp->di_kind != idkind && dhp == dtp->dt_globals) {
2701			xyerror(D_IDENT_BADREF, "%s '%s' may not be referenced "
2702			    "as %s\n", dt_idkind_name(idp->di_kind),
2703			    idp->di_name, dt_idkind_name(idkind));
2704		}
2705
2706		/*
2707		 * Arrays and aggregations are not cooked individually. They
2708		 * have dynamic types and must be referenced using operator [].
2709		 * This is handled explicitly by the code for DT_TOK_LBRAC.
2710		 */
2711		if (idp->di_kind != DT_IDENT_ARRAY &&
2712		    idp->di_kind != DT_IDENT_AGG)
2713			attr = dt_ident_cook(dnp, idp, NULL);
2714		else {
2715			dt_node_type_assign(dnp,
2716			    DT_DYN_CTFP(dtp), DT_DYN_TYPE(dtp), B_FALSE);
2717			attr = idp->di_attr;
2718		}
2719
2720		free(dnp->dn_string);
2721		dnp->dn_string = NULL;
2722		dnp->dn_kind = dnkind;
2723		dnp->dn_ident = idp;
2724		dnp->dn_flags |= DT_NF_LVALUE;
2725
2726		if (idp->di_flags & DT_IDFLG_WRITE)
2727			dnp->dn_flags |= DT_NF_WRITABLE;
2728
2729		dt_node_attr_assign(dnp, attr);
2730
2731	} else if (dhp == dtp->dt_globals && scope != DTRACE_OBJ_EXEC &&
2732	    dtrace_lookup_by_name(dtp, scope, name, &sym, &dts) == 0) {
2733
2734		dt_module_t *mp = dt_module_lookup_by_name(dtp, dts.dts_object);
2735		int umod = (mp->dm_flags & DT_DM_KERNEL) == 0;
2736		static const char *const kunames[] = { "kernel", "user" };
2737
2738		dtrace_typeinfo_t dtt;
2739		dtrace_syminfo_t *sip;
2740
2741		if (uref ^ umod) {
2742			xyerror(D_SYM_BADREF, "%s module '%s' symbol '%s' may "
2743			    "not be referenced as a %s symbol\n", kunames[umod],
2744			    dts.dts_object, dts.dts_name, kunames[uref]);
2745		}
2746
2747		if (dtrace_symbol_type(dtp, &sym, &dts, &dtt) != 0) {
2748			/*
2749			 * For now, we special-case EDT_DATAMODEL to clarify
2750			 * that mixed data models are not currently supported.
2751			 */
2752			if (dtp->dt_errno == EDT_DATAMODEL) {
2753				xyerror(D_SYM_MODEL, "cannot use %s symbol "
2754				    "%s%s%s in a %s D program\n",
2755				    dt_module_modelname(mp),
2756				    dts.dts_object, mark, dts.dts_name,
2757				    dt_module_modelname(dtp->dt_ddefs));
2758			}
2759
2760			xyerror(D_SYM_NOTYPES,
2761			    "no symbolic type information is available for "
2762			    "%s%s%s: %s\n", dts.dts_object, mark, dts.dts_name,
2763			    dtrace_errmsg(dtp, dtrace_errno(dtp)));
2764		}
2765
2766		idp = dt_ident_create(name, DT_IDENT_SYMBOL, 0, 0,
2767		    _dtrace_symattr, 0, &dt_idops_thaw, NULL, dtp->dt_gen);
2768
2769		if (idp == NULL)
2770			longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2771
2772		if (mp->dm_flags & DT_DM_PRIMARY)
2773			idp->di_flags |= DT_IDFLG_PRIM;
2774
2775		idp->di_next = dtp->dt_externs;
2776		dtp->dt_externs = idp;
2777
2778		if ((sip = malloc(sizeof (dtrace_syminfo_t))) == NULL)
2779			longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2780
2781		bcopy(&dts, sip, sizeof (dtrace_syminfo_t));
2782		idp->di_data = sip;
2783		idp->di_ctfp = dtt.dtt_ctfp;
2784		idp->di_type = dtt.dtt_type;
2785
2786		free(dnp->dn_string);
2787		dnp->dn_string = NULL;
2788		dnp->dn_kind = DT_NODE_SYM;
2789		dnp->dn_ident = idp;
2790		dnp->dn_flags |= DT_NF_LVALUE;
2791
2792		dt_node_type_assign(dnp, dtt.dtt_ctfp, dtt.dtt_type,
2793		    dtt.dtt_flags);
2794		dt_node_attr_assign(dnp, _dtrace_symattr);
2795
2796		if (uref) {
2797			idp->di_flags |= DT_IDFLG_USER;
2798			dnp->dn_flags |= DT_NF_USERLAND;
2799		}
2800
2801	} else if (scope == DTRACE_OBJ_EXEC && create == B_TRUE) {
2802		uint_t flags = DT_IDFLG_WRITE;
2803		uint_t id;
2804
2805		if (dt_idhash_nextid(dhp, &id) == -1) {
2806			xyerror(D_ID_OFLOW, "cannot create %s: limit on number "
2807			    "of %s variables exceeded\n", name, sname);
2808		}
2809
2810		if (dhp == yypcb->pcb_locals)
2811			flags |= DT_IDFLG_LOCAL;
2812		else if (dhp == dtp->dt_tls)
2813			flags |= DT_IDFLG_TLS;
2814
2815		dt_dprintf("create %s %s variable %s, id=%u\n",
2816		    sname, dt_idkind_name(idkind), name, id);
2817
2818		if (idkind == DT_IDENT_ARRAY || idkind == DT_IDENT_AGG) {
2819			idp = dt_idhash_insert(dhp, name,
2820			    idkind, flags, id, _dtrace_defattr, 0,
2821			    &dt_idops_assc, NULL, dtp->dt_gen);
2822		} else {
2823			idp = dt_idhash_insert(dhp, name,
2824			    idkind, flags, id, _dtrace_defattr, 0,
2825			    &dt_idops_thaw, NULL, dtp->dt_gen);
2826		}
2827
2828		if (idp == NULL)
2829			longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
2830
2831		/*
2832		 * Arrays and aggregations are not cooked individually. They
2833		 * have dynamic types and must be referenced using operator [].
2834		 * This is handled explicitly by the code for DT_TOK_LBRAC.
2835		 */
2836		if (idp->di_kind != DT_IDENT_ARRAY &&
2837		    idp->di_kind != DT_IDENT_AGG)
2838			attr = dt_ident_cook(dnp, idp, NULL);
2839		else {
2840			dt_node_type_assign(dnp,
2841			    DT_DYN_CTFP(dtp), DT_DYN_TYPE(dtp), B_FALSE);
2842			attr = idp->di_attr;
2843		}
2844
2845		free(dnp->dn_string);
2846		dnp->dn_string = NULL;
2847		dnp->dn_kind = dnkind;
2848		dnp->dn_ident = idp;
2849		dnp->dn_flags |= DT_NF_LVALUE | DT_NF_WRITABLE;
2850
2851		dt_node_attr_assign(dnp, attr);
2852
2853	} else if (scope != DTRACE_OBJ_EXEC) {
2854		xyerror(D_IDENT_UNDEF, "failed to resolve %s%s%s: %s\n",
2855		    dnp->dn_string, mark, name,
2856		    dtrace_errmsg(dtp, dtrace_errno(dtp)));
2857	} else {
2858		xyerror(D_IDENT_UNDEF, "failed to resolve %s: %s\n",
2859		    dnp->dn_string, dtrace_errmsg(dtp, dtrace_errno(dtp)));
2860	}
2861}
2862
2863static dt_node_t *
2864dt_cook_ident(dt_node_t *dnp, uint_t idflags)
2865{
2866	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2867
2868	if (dnp->dn_op == DT_TOK_AGG)
2869		dt_xcook_ident(dnp, dtp->dt_aggs, DT_IDENT_AGG, B_FALSE);
2870	else
2871		dt_xcook_ident(dnp, dtp->dt_globals, DT_IDENT_SCALAR, B_FALSE);
2872
2873	return (dt_node_cook(dnp, idflags));
2874}
2875
2876/*
2877 * Since operators [ and -> can instantiate new variables before we know
2878 * whether the reference is for a read or a write, we need to check read
2879 * references to determine if the identifier is currently dt_ident_unref().
2880 * If so, we report that this first access was to an undefined variable.
2881 */
2882static dt_node_t *
2883dt_cook_var(dt_node_t *dnp, uint_t idflags)
2884{
2885	dt_ident_t *idp = dnp->dn_ident;
2886
2887	if ((idflags & DT_IDFLG_REF) && dt_ident_unref(idp)) {
2888		dnerror(dnp, D_VAR_UNDEF,
2889		    "%s%s has not yet been declared or assigned\n",
2890		    (idp->di_flags & DT_IDFLG_LOCAL) ? "this->" :
2891		    (idp->di_flags & DT_IDFLG_TLS) ? "self->" : "",
2892		    idp->di_name);
2893	}
2894
2895	dt_node_attr_assign(dnp, dt_ident_cook(dnp, idp, &dnp->dn_args));
2896	return (dnp);
2897}
2898
2899/*ARGSUSED*/
2900static dt_node_t *
2901dt_cook_func(dt_node_t *dnp, uint_t idflags)
2902{
2903	dt_node_attr_assign(dnp,
2904	    dt_ident_cook(dnp, dnp->dn_ident, &dnp->dn_args));
2905
2906	return (dnp);
2907}
2908
2909static dt_node_t *
2910dt_cook_op1(dt_node_t *dnp, uint_t idflags)
2911{
2912	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
2913	dt_node_t *cp = dnp->dn_child;
2914
2915	char n[DT_TYPE_NAMELEN];
2916	dtrace_typeinfo_t dtt;
2917	dt_ident_t *idp;
2918
2919	ctf_encoding_t e;
2920	ctf_arinfo_t r;
2921	ctf_id_t type, base;
2922	uint_t kind;
2923
2924	if (dnp->dn_op == DT_TOK_PREINC || dnp->dn_op == DT_TOK_POSTINC ||
2925	    dnp->dn_op == DT_TOK_PREDEC || dnp->dn_op == DT_TOK_POSTDEC)
2926		idflags = DT_IDFLG_REF | DT_IDFLG_MOD;
2927	else
2928		idflags = DT_IDFLG_REF;
2929
2930	/*
2931	 * We allow the unary ++ and -- operators to instantiate new scalar
2932	 * variables if applied to an identifier; otherwise just cook as usual.
2933	 */
2934	if (cp->dn_kind == DT_NODE_IDENT && (idflags & DT_IDFLG_MOD))
2935		dt_xcook_ident(cp, dtp->dt_globals, DT_IDENT_SCALAR, B_TRUE);
2936
2937	cp = dnp->dn_child = dt_node_cook(cp, 0); /* don't set idflags yet */
2938
2939	if (cp->dn_kind == DT_NODE_VAR && dt_ident_unref(cp->dn_ident)) {
2940		if (dt_type_lookup("int64_t", &dtt) != 0)
2941			xyerror(D_TYPE_ERR, "failed to lookup int64_t\n");
2942
2943		dt_ident_type_assign(cp->dn_ident, dtt.dtt_ctfp, dtt.dtt_type);
2944		dt_node_type_assign(cp, dtt.dtt_ctfp, dtt.dtt_type,
2945		    dtt.dtt_flags);
2946	}
2947
2948	if (cp->dn_kind == DT_NODE_VAR)
2949		cp->dn_ident->di_flags |= idflags;
2950
2951	switch (dnp->dn_op) {
2952	case DT_TOK_DEREF:
2953		/*
2954		 * If the deref operator is applied to a translated pointer,
2955		 * we set our output type to the output of the translation.
2956		 */
2957		if ((idp = dt_node_resolve(cp, DT_IDENT_XLPTR)) != NULL) {
2958			dt_xlator_t *dxp = idp->di_data;
2959
2960			dnp->dn_ident = &dxp->dx_souid;
2961			dt_node_type_assign(dnp,
2962			    dnp->dn_ident->di_ctfp, dnp->dn_ident->di_type,
2963			    cp->dn_flags & DT_NF_USERLAND);
2964			break;
2965		}
2966
2967		type = ctf_type_resolve(cp->dn_ctfp, cp->dn_type);
2968		kind = ctf_type_kind(cp->dn_ctfp, type);
2969
2970		if (kind == CTF_K_ARRAY) {
2971			if (ctf_array_info(cp->dn_ctfp, type, &r) != 0) {
2972				dtp->dt_ctferr = ctf_errno(cp->dn_ctfp);
2973				longjmp(yypcb->pcb_jmpbuf, EDT_CTF);
2974			} else
2975				type = r.ctr_contents;
2976		} else if (kind == CTF_K_POINTER) {
2977			type = ctf_type_reference(cp->dn_ctfp, type);
2978		} else {
2979			xyerror(D_DEREF_NONPTR,
2980			    "cannot dereference non-pointer type\n");
2981		}
2982
2983		dt_node_type_assign(dnp, cp->dn_ctfp, type,
2984		    cp->dn_flags & DT_NF_USERLAND);
2985		base = ctf_type_resolve(cp->dn_ctfp, type);
2986		kind = ctf_type_kind(cp->dn_ctfp, base);
2987
2988		if (kind == CTF_K_INTEGER && ctf_type_encoding(cp->dn_ctfp,
2989		    base, &e) == 0 && IS_VOID(e)) {
2990			xyerror(D_DEREF_VOID,
2991			    "cannot dereference pointer to void\n");
2992		}
2993
2994		if (kind == CTF_K_FUNCTION) {
2995			xyerror(D_DEREF_FUNC,
2996			    "cannot dereference pointer to function\n");
2997		}
2998
2999		if (kind != CTF_K_ARRAY || dt_node_is_string(dnp))
3000			dnp->dn_flags |= DT_NF_LVALUE; /* see K&R[A7.4.3] */
3001
3002		/*
3003		 * If we propagated the l-value bit and the child operand was
3004		 * a writable D variable or a binary operation of the form
3005		 * a + b where a is writable, then propagate the writable bit.
3006		 * This is necessary to permit assignments to scalar arrays,
3007		 * which are converted to expressions of the form *(a + i).
3008		 */
3009		if ((cp->dn_flags & DT_NF_WRITABLE) ||
3010		    (cp->dn_kind == DT_NODE_OP2 && cp->dn_op == DT_TOK_ADD &&
3011		    (cp->dn_left->dn_flags & DT_NF_WRITABLE)))
3012			dnp->dn_flags |= DT_NF_WRITABLE;
3013
3014		if ((cp->dn_flags & DT_NF_USERLAND) &&
3015		    (kind == CTF_K_POINTER || (dnp->dn_flags & DT_NF_REF)))
3016			dnp->dn_flags |= DT_NF_USERLAND;
3017		break;
3018
3019	case DT_TOK_IPOS:
3020	case DT_TOK_INEG:
3021		if (!dt_node_is_arith(cp)) {
3022			xyerror(D_OP_ARITH, "operator %s requires an operand "
3023			    "of arithmetic type\n", opstr(dnp->dn_op));
3024		}
3025		dt_node_type_propagate(cp, dnp); /* see K&R[A7.4.4-6] */
3026		break;
3027
3028	case DT_TOK_BNEG:
3029		if (!dt_node_is_integer(cp)) {
3030			xyerror(D_OP_INT, "operator %s requires an operand of "
3031			    "integral type\n", opstr(dnp->dn_op));
3032		}
3033		dt_node_type_propagate(cp, dnp); /* see K&R[A7.4.4-6] */
3034		break;
3035
3036	case DT_TOK_LNEG:
3037		if (!dt_node_is_scalar(cp)) {
3038			xyerror(D_OP_SCALAR, "operator %s requires an operand "
3039			    "of scalar type\n", opstr(dnp->dn_op));
3040		}
3041		dt_node_type_assign(dnp, DT_INT_CTFP(dtp), DT_INT_TYPE(dtp),
3042		    B_FALSE);
3043		break;
3044
3045	case DT_TOK_ADDROF:
3046		if (cp->dn_kind == DT_NODE_VAR || cp->dn_kind == DT_NODE_AGG) {
3047			xyerror(D_ADDROF_VAR,
3048			    "cannot take address of dynamic variable\n");
3049		}
3050
3051		if (dt_node_is_dynamic(cp)) {
3052			xyerror(D_ADDROF_VAR,
3053			    "cannot take address of dynamic object\n");
3054		}
3055
3056		if (!(cp->dn_flags & DT_NF_LVALUE)) {
3057			xyerror(D_ADDROF_LVAL, /* see K&R[A7.4.2] */
3058			    "unacceptable operand for unary & operator\n");
3059		}
3060
3061		if (cp->dn_flags & DT_NF_BITFIELD) {
3062			xyerror(D_ADDROF_BITFIELD,
3063			    "cannot take address of bit-field\n");
3064		}
3065
3066		dtt.dtt_object = NULL;
3067		dtt.dtt_ctfp = cp->dn_ctfp;
3068		dtt.dtt_type = cp->dn_type;
3069
3070		if (dt_type_pointer(&dtt) == -1) {
3071			xyerror(D_TYPE_ERR, "cannot find type for \"&\": %s*\n",
3072			    dt_node_type_name(cp, n, sizeof (n)));
3073		}
3074
3075		dt_node_type_assign(dnp, dtt.dtt_ctfp, dtt.dtt_type,
3076		    cp->dn_flags & DT_NF_USERLAND);
3077		break;
3078
3079	case DT_TOK_SIZEOF:
3080		if (cp->dn_flags & DT_NF_BITFIELD) {
3081			xyerror(D_SIZEOF_BITFIELD,
3082			    "cannot apply sizeof to a bit-field\n");
3083		}
3084
3085		if (dt_node_sizeof(cp) == 0) {
3086			xyerror(D_SIZEOF_TYPE, "cannot apply sizeof to an "
3087			    "operand of unknown size\n");
3088		}
3089
3090		dt_node_type_assign(dnp, dtp->dt_ddefs->dm_ctfp,
3091		    ctf_lookup_by_name(dtp->dt_ddefs->dm_ctfp, "size_t"),
3092		    B_FALSE);
3093		break;
3094
3095	case DT_TOK_STRINGOF:
3096		if (!dt_node_is_scalar(cp) && !dt_node_is_pointer(cp) &&
3097		    !dt_node_is_strcompat(cp)) {
3098			xyerror(D_STRINGOF_TYPE,
3099			    "cannot apply stringof to a value of type %s\n",
3100			    dt_node_type_name(cp, n, sizeof (n)));
3101		}
3102		dt_node_type_assign(dnp, DT_STR_CTFP(dtp), DT_STR_TYPE(dtp),
3103		    cp->dn_flags & DT_NF_USERLAND);
3104		break;
3105
3106	case DT_TOK_PREINC:
3107	case DT_TOK_POSTINC:
3108	case DT_TOK_PREDEC:
3109	case DT_TOK_POSTDEC:
3110		if (dt_node_is_scalar(cp) == 0) {
3111			xyerror(D_OP_SCALAR, "operator %s requires operand of "
3112			    "scalar type\n", opstr(dnp->dn_op));
3113		}
3114
3115		if (dt_node_is_vfptr(cp)) {
3116			xyerror(D_OP_VFPTR, "operator %s requires an operand "
3117			    "of known size\n", opstr(dnp->dn_op));
3118		}
3119
3120		if (!(cp->dn_flags & DT_NF_LVALUE)) {
3121			xyerror(D_OP_LVAL, "operator %s requires modifiable "
3122			    "lvalue as an operand\n", opstr(dnp->dn_op));
3123		}
3124
3125		if (!(cp->dn_flags & DT_NF_WRITABLE)) {
3126			xyerror(D_OP_WRITE, "operator %s can only be applied "
3127			    "to a writable variable\n", opstr(dnp->dn_op));
3128		}
3129
3130		dt_node_type_propagate(cp, dnp); /* see K&R[A7.4.1] */
3131		break;
3132
3133	default:
3134		xyerror(D_UNKNOWN, "invalid unary op %s\n", opstr(dnp->dn_op));
3135	}
3136
3137	dt_node_attr_assign(dnp, cp->dn_attr);
3138	return (dnp);
3139}
3140
3141static void
3142dt_assign_common(dt_node_t *dnp)
3143{
3144	dt_node_t *lp = dnp->dn_left;
3145	dt_node_t *rp = dnp->dn_right;
3146	int op = dnp->dn_op;
3147
3148	if (rp->dn_kind == DT_NODE_INT)
3149		dt_cast(lp, rp);
3150
3151	if (!(lp->dn_flags & DT_NF_LVALUE)) {
3152		xyerror(D_OP_LVAL, "operator %s requires modifiable "
3153		    "lvalue as an operand\n", opstr(op));
3154		/* see K&R[A7.17] */
3155	}
3156
3157	if (!(lp->dn_flags & DT_NF_WRITABLE)) {
3158		xyerror(D_OP_WRITE, "operator %s can only be applied "
3159		    "to a writable variable\n", opstr(op));
3160	}
3161
3162	dt_node_type_propagate(lp, dnp); /* see K&R[A7.17] */
3163	dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3164}
3165
3166static dt_node_t *
3167dt_cook_op2(dt_node_t *dnp, uint_t idflags)
3168{
3169	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
3170	dt_node_t *lp = dnp->dn_left;
3171	dt_node_t *rp = dnp->dn_right;
3172	int op = dnp->dn_op;
3173
3174	ctf_membinfo_t m;
3175	ctf_file_t *ctfp;
3176	ctf_id_t type;
3177	int kind, val, uref;
3178	dt_ident_t *idp;
3179
3180	char n1[DT_TYPE_NAMELEN];
3181	char n2[DT_TYPE_NAMELEN];
3182
3183	/*
3184	 * The expression E1[E2] is identical by definition to *((E1)+(E2)) so
3185	 * we convert "[" to "+" and glue on "*" at the end (see K&R[A7.3.1])
3186	 * unless the left-hand side is an untyped D scalar, associative array,
3187	 * or aggregation.  In these cases, we proceed to case DT_TOK_LBRAC and
3188	 * handle associative array and aggregation references there.
3189	 */
3190	if (op == DT_TOK_LBRAC) {
3191		if (lp->dn_kind == DT_NODE_IDENT) {
3192			dt_idhash_t *dhp;
3193			uint_t idkind;
3194
3195			if (lp->dn_op == DT_TOK_AGG) {
3196				dhp = dtp->dt_aggs;
3197				idp = dt_idhash_lookup(dhp, lp->dn_string + 1);
3198				idkind = DT_IDENT_AGG;
3199			} else {
3200				dhp = dtp->dt_globals;
3201				idp = dt_idstack_lookup(
3202				    &yypcb->pcb_globals, lp->dn_string);
3203				idkind = DT_IDENT_ARRAY;
3204			}
3205
3206			if (idp == NULL || dt_ident_unref(idp))
3207				dt_xcook_ident(lp, dhp, idkind, B_TRUE);
3208			else
3209				dt_xcook_ident(lp, dhp, idp->di_kind, B_FALSE);
3210		} else {
3211			lp = dnp->dn_left = dt_node_cook(lp, 0);
3212		}
3213
3214		/*
3215		 * Switch op to '+' for *(E1 + E2) array mode in these cases:
3216		 * (a) lp is a DT_IDENT_ARRAY variable that has already been
3217		 *	referenced using [] notation (dn_args != NULL).
3218		 * (b) lp is a non-ARRAY variable that has already been given
3219		 *	a type by assignment or declaration (!dt_ident_unref())
3220		 * (c) lp is neither a variable nor an aggregation
3221		 */
3222		if (lp->dn_kind == DT_NODE_VAR) {
3223			if (lp->dn_ident->di_kind == DT_IDENT_ARRAY) {
3224				if (lp->dn_args != NULL)
3225					op = DT_TOK_ADD;
3226			} else if (!dt_ident_unref(lp->dn_ident)) {
3227				op = DT_TOK_ADD;
3228			}
3229		} else if (lp->dn_kind != DT_NODE_AGG) {
3230			op = DT_TOK_ADD;
3231		}
3232	}
3233
3234	switch (op) {
3235	case DT_TOK_BAND:
3236	case DT_TOK_XOR:
3237	case DT_TOK_BOR:
3238		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3239		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3240
3241		if (!dt_node_is_integer(lp) || !dt_node_is_integer(rp)) {
3242			xyerror(D_OP_INT, "operator %s requires operands of "
3243			    "integral type\n", opstr(op));
3244		}
3245
3246		dt_node_promote(lp, rp, dnp); /* see K&R[A7.11-13] */
3247		break;
3248
3249	case DT_TOK_LSH:
3250	case DT_TOK_RSH:
3251		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3252		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3253
3254		if (!dt_node_is_integer(lp) || !dt_node_is_integer(rp)) {
3255			xyerror(D_OP_INT, "operator %s requires operands of "
3256			    "integral type\n", opstr(op));
3257		}
3258
3259		dt_node_type_propagate(lp, dnp); /* see K&R[A7.8] */
3260		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3261		break;
3262
3263	case DT_TOK_MOD:
3264		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3265		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3266
3267		if (!dt_node_is_integer(lp) || !dt_node_is_integer(rp)) {
3268			xyerror(D_OP_INT, "operator %s requires operands of "
3269			    "integral type\n", opstr(op));
3270		}
3271
3272		dt_node_promote(lp, rp, dnp); /* see K&R[A7.6] */
3273		break;
3274
3275	case DT_TOK_MUL:
3276	case DT_TOK_DIV:
3277		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3278		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3279
3280		if (!dt_node_is_arith(lp) || !dt_node_is_arith(rp)) {
3281			xyerror(D_OP_ARITH, "operator %s requires operands of "
3282			    "arithmetic type\n", opstr(op));
3283		}
3284
3285		dt_node_promote(lp, rp, dnp); /* see K&R[A7.6] */
3286		break;
3287
3288	case DT_TOK_LAND:
3289	case DT_TOK_LXOR:
3290	case DT_TOK_LOR:
3291		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3292		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3293
3294		if (!dt_node_is_scalar(lp) || !dt_node_is_scalar(rp)) {
3295			xyerror(D_OP_SCALAR, "operator %s requires operands "
3296			    "of scalar type\n", opstr(op));
3297		}
3298
3299		dt_node_type_assign(dnp, DT_INT_CTFP(dtp), DT_INT_TYPE(dtp),
3300		    B_FALSE);
3301		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3302		break;
3303
3304	case DT_TOK_LT:
3305	case DT_TOK_LE:
3306	case DT_TOK_GT:
3307	case DT_TOK_GE:
3308	case DT_TOK_EQU:
3309	case DT_TOK_NEQ:
3310		/*
3311		 * The D comparison operators provide the ability to transform
3312		 * a right-hand identifier into a corresponding enum tag value
3313		 * if the left-hand side is an enum type.  To do this, we cook
3314		 * the left-hand side, and then see if the right-hand side is
3315		 * an unscoped identifier defined in the enum.  If so, we
3316		 * convert into an integer constant node with the tag's value.
3317		 */
3318		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3319
3320		kind = ctf_type_kind(lp->dn_ctfp,
3321		    ctf_type_resolve(lp->dn_ctfp, lp->dn_type));
3322
3323		if (kind == CTF_K_ENUM && rp->dn_kind == DT_NODE_IDENT &&
3324		    strchr(rp->dn_string, '`') == NULL && ctf_enum_value(
3325		    lp->dn_ctfp, lp->dn_type, rp->dn_string, &val) == 0) {
3326
3327			if ((idp = dt_idstack_lookup(&yypcb->pcb_globals,
3328			    rp->dn_string)) != NULL) {
3329				xyerror(D_IDENT_AMBIG,
3330				    "ambiguous use of operator %s: %s is "
3331				    "both a %s enum tag and a global %s\n",
3332				    opstr(op), rp->dn_string,
3333				    dt_node_type_name(lp, n1, sizeof (n1)),
3334				    dt_idkind_name(idp->di_kind));
3335			}
3336
3337			free(rp->dn_string);
3338			rp->dn_string = NULL;
3339			rp->dn_kind = DT_NODE_INT;
3340			rp->dn_flags |= DT_NF_COOKED;
3341			rp->dn_op = DT_TOK_INT;
3342			rp->dn_value = (intmax_t)val;
3343
3344			dt_node_type_assign(rp, lp->dn_ctfp, lp->dn_type,
3345			    B_FALSE);
3346			dt_node_attr_assign(rp, _dtrace_symattr);
3347		}
3348
3349		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3350
3351		/*
3352		 * The rules for type checking for the relational operators are
3353		 * described in the ANSI-C spec (see K&R[A7.9-10]).  We perform
3354		 * the various tests in order from least to most expensive.  We
3355		 * also allow derived strings to be compared as a first-class
3356		 * type (resulting in a strcmp(3C)-style comparison), and we
3357		 * slightly relax the A7.9 rules to permit void pointer
3358		 * comparisons as in A7.10.  Our users won't be confused by
3359		 * this since they understand pointers are just numbers, and
3360		 * relaxing this constraint simplifies the implementation.
3361		 */
3362		if (ctf_type_compat(lp->dn_ctfp, lp->dn_type,
3363		    rp->dn_ctfp, rp->dn_type))
3364			/*EMPTY*/;
3365		else if (dt_node_is_integer(lp) && dt_node_is_integer(rp))
3366			/*EMPTY*/;
3367		else if (dt_node_is_strcompat(lp) && dt_node_is_strcompat(rp) &&
3368		    (dt_node_is_string(lp) || dt_node_is_string(rp)))
3369			/*EMPTY*/;
3370		else if (dt_node_is_ptrcompat(lp, rp, NULL, NULL) == 0) {
3371			xyerror(D_OP_INCOMPAT, "operands have "
3372			    "incompatible types: \"%s\" %s \"%s\"\n",
3373			    dt_node_type_name(lp, n1, sizeof (n1)), opstr(op),
3374			    dt_node_type_name(rp, n2, sizeof (n2)));
3375		}
3376
3377		dt_node_type_assign(dnp, DT_INT_CTFP(dtp), DT_INT_TYPE(dtp),
3378		    B_FALSE);
3379		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3380		break;
3381
3382	case DT_TOK_ADD:
3383	case DT_TOK_SUB: {
3384		/*
3385		 * The rules for type checking for the additive operators are
3386		 * described in the ANSI-C spec (see K&R[A7.7]).  Pointers and
3387		 * integers may be manipulated according to specific rules.  In
3388		 * these cases D permits strings to be treated as pointers.
3389		 */
3390		int lp_is_ptr, lp_is_int, rp_is_ptr, rp_is_int;
3391
3392		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3393		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3394
3395		lp_is_ptr = dt_node_is_string(lp) ||
3396		    (dt_node_is_pointer(lp) && !dt_node_is_vfptr(lp));
3397		lp_is_int = dt_node_is_integer(lp);
3398
3399		rp_is_ptr = dt_node_is_string(rp) ||
3400		    (dt_node_is_pointer(rp) && !dt_node_is_vfptr(rp));
3401		rp_is_int = dt_node_is_integer(rp);
3402
3403		if (lp_is_int && rp_is_int) {
3404			dt_type_promote(lp, rp, &ctfp, &type);
3405			uref = 0;
3406		} else if (lp_is_ptr && rp_is_int) {
3407			ctfp = lp->dn_ctfp;
3408			type = lp->dn_type;
3409			uref = lp->dn_flags & DT_NF_USERLAND;
3410		} else if (lp_is_int && rp_is_ptr && op == DT_TOK_ADD) {
3411			ctfp = rp->dn_ctfp;
3412			type = rp->dn_type;
3413			uref = rp->dn_flags & DT_NF_USERLAND;
3414		} else if (lp_is_ptr && rp_is_ptr && op == DT_TOK_SUB &&
3415		    dt_node_is_ptrcompat(lp, rp, NULL, NULL)) {
3416			ctfp = dtp->dt_ddefs->dm_ctfp;
3417			type = ctf_lookup_by_name(ctfp, "ptrdiff_t");
3418			uref = 0;
3419		} else {
3420			xyerror(D_OP_INCOMPAT, "operands have incompatible "
3421			    "types: \"%s\" %s \"%s\"\n",
3422			    dt_node_type_name(lp, n1, sizeof (n1)), opstr(op),
3423			    dt_node_type_name(rp, n2, sizeof (n2)));
3424		}
3425
3426		dt_node_type_assign(dnp, ctfp, type, B_FALSE);
3427		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3428
3429		if (uref)
3430			dnp->dn_flags |= DT_NF_USERLAND;
3431		break;
3432	}
3433
3434	case DT_TOK_OR_EQ:
3435	case DT_TOK_XOR_EQ:
3436	case DT_TOK_AND_EQ:
3437	case DT_TOK_LSH_EQ:
3438	case DT_TOK_RSH_EQ:
3439	case DT_TOK_MOD_EQ:
3440		if (lp->dn_kind == DT_NODE_IDENT) {
3441			dt_xcook_ident(lp, dtp->dt_globals,
3442			    DT_IDENT_SCALAR, B_TRUE);
3443		}
3444
3445		lp = dnp->dn_left =
3446		    dt_node_cook(lp, DT_IDFLG_REF | DT_IDFLG_MOD);
3447
3448		rp = dnp->dn_right =
3449		    dt_node_cook(rp, DT_IDFLG_REF | DT_IDFLG_MOD);
3450
3451		if (!dt_node_is_integer(lp) || !dt_node_is_integer(rp)) {
3452			xyerror(D_OP_INT, "operator %s requires operands of "
3453			    "integral type\n", opstr(op));
3454		}
3455		goto asgn_common;
3456
3457	case DT_TOK_MUL_EQ:
3458	case DT_TOK_DIV_EQ:
3459		if (lp->dn_kind == DT_NODE_IDENT) {
3460			dt_xcook_ident(lp, dtp->dt_globals,
3461			    DT_IDENT_SCALAR, B_TRUE);
3462		}
3463
3464		lp = dnp->dn_left =
3465		    dt_node_cook(lp, DT_IDFLG_REF | DT_IDFLG_MOD);
3466
3467		rp = dnp->dn_right =
3468		    dt_node_cook(rp, DT_IDFLG_REF | DT_IDFLG_MOD);
3469
3470		if (!dt_node_is_arith(lp) || !dt_node_is_arith(rp)) {
3471			xyerror(D_OP_ARITH, "operator %s requires operands of "
3472			    "arithmetic type\n", opstr(op));
3473		}
3474		goto asgn_common;
3475
3476	case DT_TOK_ASGN:
3477		/*
3478		 * If the left-hand side is an identifier, attempt to resolve
3479		 * it as either an aggregation or scalar variable.  We pass
3480		 * B_TRUE to dt_xcook_ident to indicate that a new variable can
3481		 * be created if no matching variable exists in the namespace.
3482		 */
3483		if (lp->dn_kind == DT_NODE_IDENT) {
3484			if (lp->dn_op == DT_TOK_AGG) {
3485				dt_xcook_ident(lp, dtp->dt_aggs,
3486				    DT_IDENT_AGG, B_TRUE);
3487			} else {
3488				dt_xcook_ident(lp, dtp->dt_globals,
3489				    DT_IDENT_SCALAR, B_TRUE);
3490			}
3491		}
3492
3493		lp = dnp->dn_left = dt_node_cook(lp, 0); /* don't set mod yet */
3494		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3495
3496		/*
3497		 * If the left-hand side is an aggregation, verify that we are
3498		 * assigning it the result of an aggregating function.  Once
3499		 * we've done so, hide the func node in the aggregation and
3500		 * return the aggregation itself up to the parse tree parent.
3501		 * This transformation is legal since the assigned function
3502		 * cannot change identity across disjoint cooking passes and
3503		 * the argument list subtree is retained for later cooking.
3504		 */
3505		if (lp->dn_kind == DT_NODE_AGG) {
3506			const char *aname = lp->dn_ident->di_name;
3507			dt_ident_t *oid = lp->dn_ident->di_iarg;
3508
3509			if (rp->dn_kind != DT_NODE_FUNC ||
3510			    rp->dn_ident->di_kind != DT_IDENT_AGGFUNC) {
3511				xyerror(D_AGG_FUNC,
3512				    "@%s must be assigned the result of "
3513				    "an aggregating function\n", aname);
3514			}
3515
3516			if (oid != NULL && oid != rp->dn_ident) {
3517				xyerror(D_AGG_REDEF,
3518				    "aggregation redefined: @%s\n\t "
3519				    "current: @%s = %s( )\n\tprevious: @%s = "
3520				    "%s( ) : line %d\n", aname, aname,
3521				    rp->dn_ident->di_name, aname, oid->di_name,
3522				    lp->dn_ident->di_lineno);
3523			} else if (oid == NULL)
3524				lp->dn_ident->di_iarg = rp->dn_ident;
3525
3526			/*
3527			 * Do not allow multiple aggregation assignments in a
3528			 * single statement, e.g. (@a = count()) = count();
3529			 * We produce a message as if the result of aggregating
3530			 * function does not propagate DT_NF_LVALUE.
3531			 */
3532			if (lp->dn_aggfun != NULL) {
3533				xyerror(D_OP_LVAL, "operator = requires "
3534				    "modifiable lvalue as an operand\n");
3535			}
3536
3537			lp->dn_aggfun = rp;
3538			lp = dt_node_cook(lp, DT_IDFLG_MOD);
3539
3540			dnp->dn_left = dnp->dn_right = NULL;
3541			dt_node_free(dnp);
3542
3543			return (lp);
3544		}
3545
3546		/*
3547		 * If the right-hand side is a dynamic variable that is the
3548		 * output of a translator, our result is the translated type.
3549		 */
3550		if ((idp = dt_node_resolve(rp, DT_IDENT_XLSOU)) != NULL) {
3551			ctfp = idp->di_ctfp;
3552			type = idp->di_type;
3553			uref = idp->di_flags & DT_IDFLG_USER;
3554		} else {
3555			ctfp = rp->dn_ctfp;
3556			type = rp->dn_type;
3557			uref = rp->dn_flags & DT_NF_USERLAND;
3558		}
3559
3560		/*
3561		 * If the left-hand side of an assignment statement is a virgin
3562		 * variable created by this compilation pass, reset the type of
3563		 * this variable to the type of the right-hand side.
3564		 */
3565		if (lp->dn_kind == DT_NODE_VAR &&
3566		    dt_ident_unref(lp->dn_ident)) {
3567			dt_node_type_assign(lp, ctfp, type, B_FALSE);
3568			dt_ident_type_assign(lp->dn_ident, ctfp, type);
3569
3570			if (uref) {
3571				lp->dn_flags |= DT_NF_USERLAND;
3572				lp->dn_ident->di_flags |= DT_IDFLG_USER;
3573			}
3574		}
3575
3576		if (lp->dn_kind == DT_NODE_VAR)
3577			lp->dn_ident->di_flags |= DT_IDFLG_MOD;
3578
3579		/*
3580		 * The rules for type checking for the assignment operators are
3581		 * described in the ANSI-C spec (see K&R[A7.17]).  We share
3582		 * most of this code with the argument list checking code.
3583		 */
3584		if (!dt_node_is_string(lp)) {
3585			kind = ctf_type_kind(lp->dn_ctfp,
3586			    ctf_type_resolve(lp->dn_ctfp, lp->dn_type));
3587
3588			if (kind == CTF_K_ARRAY || kind == CTF_K_FUNCTION) {
3589				xyerror(D_OP_ARRFUN, "operator %s may not be "
3590				    "applied to operand of type \"%s\"\n",
3591				    opstr(op),
3592				    dt_node_type_name(lp, n1, sizeof (n1)));
3593			}
3594		}
3595
3596		if (idp != NULL && idp->di_kind == DT_IDENT_XLSOU &&
3597		    ctf_type_compat(lp->dn_ctfp, lp->dn_type, ctfp, type))
3598			goto asgn_common;
3599
3600		if (dt_node_is_argcompat(lp, rp))
3601			goto asgn_common;
3602
3603		xyerror(D_OP_INCOMPAT,
3604		    "operands have incompatible types: \"%s\" %s \"%s\"\n",
3605		    dt_node_type_name(lp, n1, sizeof (n1)), opstr(op),
3606		    dt_node_type_name(rp, n2, sizeof (n2)));
3607		/*NOTREACHED*/
3608
3609	case DT_TOK_ADD_EQ:
3610	case DT_TOK_SUB_EQ:
3611		if (lp->dn_kind == DT_NODE_IDENT) {
3612			dt_xcook_ident(lp, dtp->dt_globals,
3613			    DT_IDENT_SCALAR, B_TRUE);
3614		}
3615
3616		lp = dnp->dn_left =
3617		    dt_node_cook(lp, DT_IDFLG_REF | DT_IDFLG_MOD);
3618
3619		rp = dnp->dn_right =
3620		    dt_node_cook(rp, DT_IDFLG_REF | DT_IDFLG_MOD);
3621
3622		if (dt_node_is_string(lp) || dt_node_is_string(rp)) {
3623			xyerror(D_OP_INCOMPAT, "operands have "
3624			    "incompatible types: \"%s\" %s \"%s\"\n",
3625			    dt_node_type_name(lp, n1, sizeof (n1)), opstr(op),
3626			    dt_node_type_name(rp, n2, sizeof (n2)));
3627		}
3628
3629		/*
3630		 * The rules for type checking for the assignment operators are
3631		 * described in the ANSI-C spec (see K&R[A7.17]).  To these
3632		 * rules we add that only writable D nodes can be modified.
3633		 */
3634		if (dt_node_is_integer(lp) == 0 ||
3635		    dt_node_is_integer(rp) == 0) {
3636			if (!dt_node_is_pointer(lp) || dt_node_is_vfptr(lp)) {
3637				xyerror(D_OP_VFPTR,
3638				    "operator %s requires left-hand scalar "
3639				    "operand of known size\n", opstr(op));
3640			} else if (dt_node_is_integer(rp) == 0 &&
3641			    dt_node_is_ptrcompat(lp, rp, NULL, NULL) == 0) {
3642				xyerror(D_OP_INCOMPAT, "operands have "
3643				    "incompatible types: \"%s\" %s \"%s\"\n",
3644				    dt_node_type_name(lp, n1, sizeof (n1)),
3645				    opstr(op),
3646				    dt_node_type_name(rp, n2, sizeof (n2)));
3647			}
3648		}
3649asgn_common:
3650		dt_assign_common(dnp);
3651		break;
3652
3653	case DT_TOK_PTR:
3654		/*
3655		 * If the left-hand side of operator -> is one of the scoping
3656		 * keywords, permit a local or thread variable to be created or
3657		 * referenced.
3658		 */
3659		if (lp->dn_kind == DT_NODE_IDENT) {
3660			dt_idhash_t *dhp = NULL;
3661
3662			if (strcmp(lp->dn_string, "self") == 0) {
3663				dhp = dtp->dt_tls;
3664			} else if (strcmp(lp->dn_string, "this") == 0) {
3665				dhp = yypcb->pcb_locals;
3666			}
3667			if (dhp != NULL) {
3668				if (rp->dn_kind != DT_NODE_VAR) {
3669					dt_xcook_ident(rp, dhp,
3670					    DT_IDENT_SCALAR, B_TRUE);
3671				}
3672
3673				if (idflags != 0)
3674					rp = dt_node_cook(rp, idflags);
3675
3676				/* avoid freeing rp */
3677				dnp->dn_right = dnp->dn_left;
3678				dt_node_free(dnp);
3679				return (rp);
3680			}
3681		}
3682		/*FALLTHRU*/
3683	case DT_TOK_DOT:
3684		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3685
3686		if (rp->dn_kind != DT_NODE_IDENT) {
3687			xyerror(D_OP_IDENT, "operator %s must be followed by "
3688			    "an identifier\n", opstr(op));
3689		}
3690
3691		if ((idp = dt_node_resolve(lp, DT_IDENT_XLSOU)) != NULL ||
3692		    (idp = dt_node_resolve(lp, DT_IDENT_XLPTR)) != NULL) {
3693			/*
3694			 * If the left-hand side is a translated struct or ptr,
3695			 * the type of the left is the translation output type.
3696			 */
3697			dt_xlator_t *dxp = idp->di_data;
3698
3699			if (dt_xlator_member(dxp, rp->dn_string) == NULL) {
3700				xyerror(D_XLATE_NOCONV,
3701				    "translator does not define conversion "
3702				    "for member: %s\n", rp->dn_string);
3703			}
3704
3705			ctfp = idp->di_ctfp;
3706			type = ctf_type_resolve(ctfp, idp->di_type);
3707			uref = idp->di_flags & DT_IDFLG_USER;
3708		} else {
3709			ctfp = lp->dn_ctfp;
3710			type = ctf_type_resolve(ctfp, lp->dn_type);
3711			uref = lp->dn_flags & DT_NF_USERLAND;
3712		}
3713
3714		kind = ctf_type_kind(ctfp, type);
3715
3716		if (op == DT_TOK_PTR) {
3717			if (kind != CTF_K_POINTER) {
3718				xyerror(D_OP_PTR, "operator %s must be "
3719				    "applied to a pointer\n", opstr(op));
3720			}
3721			type = ctf_type_reference(ctfp, type);
3722			type = ctf_type_resolve(ctfp, type);
3723			kind = ctf_type_kind(ctfp, type);
3724		}
3725
3726		/*
3727		 * If we follow a reference to a forward declaration tag,
3728		 * search the entire type space for the actual definition.
3729		 */
3730		while (kind == CTF_K_FORWARD) {
3731			char *tag = ctf_type_name(ctfp, type, n1, sizeof (n1));
3732			dtrace_typeinfo_t dtt;
3733
3734			if (tag != NULL && dt_type_lookup(tag, &dtt) == 0 &&
3735			    (dtt.dtt_ctfp != ctfp || dtt.dtt_type != type)) {
3736				ctfp = dtt.dtt_ctfp;
3737				type = ctf_type_resolve(ctfp, dtt.dtt_type);
3738				kind = ctf_type_kind(ctfp, type);
3739			} else {
3740				xyerror(D_OP_INCOMPLETE,
3741				    "operator %s cannot be applied to a "
3742				    "forward declaration: no %s definition "
3743				    "is available\n", opstr(op), tag);
3744			}
3745		}
3746
3747		if (kind != CTF_K_STRUCT && kind != CTF_K_UNION) {
3748			if (op == DT_TOK_PTR) {
3749				xyerror(D_OP_SOU, "operator -> cannot be "
3750				    "applied to pointer to type \"%s\"; must "
3751				    "be applied to a struct or union pointer\n",
3752				    ctf_type_name(ctfp, type, n1, sizeof (n1)));
3753			} else {
3754				xyerror(D_OP_SOU, "operator %s cannot be "
3755				    "applied to type \"%s\"; must be applied "
3756				    "to a struct or union\n", opstr(op),
3757				    ctf_type_name(ctfp, type, n1, sizeof (n1)));
3758			}
3759		}
3760
3761		if (ctf_member_info(ctfp, type, rp->dn_string, &m) == CTF_ERR) {
3762			xyerror(D_TYPE_MEMBER,
3763			    "%s is not a member of %s\n", rp->dn_string,
3764			    ctf_type_name(ctfp, type, n1, sizeof (n1)));
3765		}
3766
3767		type = ctf_type_resolve(ctfp, m.ctm_type);
3768		kind = ctf_type_kind(ctfp, type);
3769
3770		dt_node_type_assign(dnp, ctfp, m.ctm_type, B_FALSE);
3771		dt_node_attr_assign(dnp, lp->dn_attr);
3772
3773		if (op == DT_TOK_PTR && (kind != CTF_K_ARRAY ||
3774		    dt_node_is_string(dnp)))
3775			dnp->dn_flags |= DT_NF_LVALUE; /* see K&R[A7.3.3] */
3776
3777		if (op == DT_TOK_DOT && (lp->dn_flags & DT_NF_LVALUE) &&
3778		    (kind != CTF_K_ARRAY || dt_node_is_string(dnp)))
3779			dnp->dn_flags |= DT_NF_LVALUE; /* see K&R[A7.3.3] */
3780
3781		if (lp->dn_flags & DT_NF_WRITABLE)
3782			dnp->dn_flags |= DT_NF_WRITABLE;
3783
3784		if (uref && (kind == CTF_K_POINTER ||
3785		    (dnp->dn_flags & DT_NF_REF)))
3786			dnp->dn_flags |= DT_NF_USERLAND;
3787		break;
3788
3789	case DT_TOK_LBRAC: {
3790		/*
3791		 * If op is DT_TOK_LBRAC, we know from the special-case code at
3792		 * the top that lp is either a D variable or an aggregation.
3793		 */
3794		dt_node_t *lnp;
3795
3796		/*
3797		 * If the left-hand side is an aggregation, just set dn_aggtup
3798		 * to the right-hand side and return the cooked aggregation.
3799		 * This transformation is legal since we are just collapsing
3800		 * nodes to simplify later processing, and the entire aggtup
3801		 * parse subtree is retained for subsequent cooking passes.
3802		 */
3803		if (lp->dn_kind == DT_NODE_AGG) {
3804			if (lp->dn_aggtup != NULL) {
3805				xyerror(D_AGG_MDIM, "improper attempt to "
3806				    "reference @%s as a multi-dimensional "
3807				    "array\n", lp->dn_ident->di_name);
3808			}
3809
3810			lp->dn_aggtup = rp;
3811			lp = dt_node_cook(lp, 0);
3812
3813			dnp->dn_left = dnp->dn_right = NULL;
3814			dt_node_free(dnp);
3815
3816			return (lp);
3817		}
3818
3819		assert(lp->dn_kind == DT_NODE_VAR);
3820		idp = lp->dn_ident;
3821
3822		/*
3823		 * If the left-hand side is a non-global scalar that hasn't yet
3824		 * been referenced or modified, it was just created by self->
3825		 * or this-> and we can convert it from scalar to assoc array.
3826		 */
3827		if (idp->di_kind == DT_IDENT_SCALAR && dt_ident_unref(idp) &&
3828		    (idp->di_flags & (DT_IDFLG_LOCAL | DT_IDFLG_TLS)) != 0) {
3829
3830			if (idp->di_flags & DT_IDFLG_LOCAL) {
3831				xyerror(D_ARR_LOCAL,
3832				    "local variables may not be used as "
3833				    "associative arrays: %s\n", idp->di_name);
3834			}
3835
3836			dt_dprintf("morph variable %s (id %u) from scalar to "
3837			    "array\n", idp->di_name, idp->di_id);
3838
3839			dt_ident_morph(idp, DT_IDENT_ARRAY,
3840			    &dt_idops_assc, NULL);
3841		}
3842
3843		if (idp->di_kind != DT_IDENT_ARRAY) {
3844			xyerror(D_IDENT_BADREF, "%s '%s' may not be referenced "
3845			    "as %s\n", dt_idkind_name(idp->di_kind),
3846			    idp->di_name, dt_idkind_name(DT_IDENT_ARRAY));
3847		}
3848
3849		/*
3850		 * Now that we've confirmed our left-hand side is a DT_NODE_VAR
3851		 * of idkind DT_IDENT_ARRAY, we need to splice the [ node from
3852		 * the parse tree and leave a cooked DT_NODE_VAR in its place
3853		 * where dn_args for the VAR node is the right-hand 'rp' tree,
3854		 * as shown in the parse tree diagram below:
3855		 *
3856		 *	  /			    /
3857		 * [ OP2 "[" ]=dnp		[ VAR ]=dnp
3858		 *	 /	\	  =>	   |
3859		 *	/	 \		   +- dn_args -> [ ??? ]=rp
3860		 * [ VAR ]=lp  [ ??? ]=rp
3861		 *
3862		 * Since the final dt_node_cook(dnp) can fail using longjmp we
3863		 * must perform the transformations as a group first by over-
3864		 * writing 'dnp' to become the VAR node, so that the parse tree
3865		 * is guaranteed to be in a consistent state if the cook fails.
3866		 */
3867		assert(lp->dn_kind == DT_NODE_VAR);
3868		assert(lp->dn_args == NULL);
3869
3870		lnp = dnp->dn_link;
3871		bcopy(lp, dnp, sizeof (dt_node_t));
3872		dnp->dn_link = lnp;
3873
3874		dnp->dn_args = rp;
3875		dnp->dn_list = NULL;
3876
3877		dt_node_free(lp);
3878		return (dt_node_cook(dnp, idflags));
3879	}
3880
3881	case DT_TOK_XLATE: {
3882		dt_xlator_t *dxp;
3883
3884		assert(lp->dn_kind == DT_NODE_TYPE);
3885		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3886		dxp = dt_xlator_lookup(dtp, rp, lp, DT_XLATE_FUZZY);
3887
3888		if (dxp == NULL) {
3889			xyerror(D_XLATE_NONE,
3890			    "cannot translate from \"%s\" to \"%s\"\n",
3891			    dt_node_type_name(rp, n1, sizeof (n1)),
3892			    dt_node_type_name(lp, n2, sizeof (n2)));
3893		}
3894
3895		dnp->dn_ident = dt_xlator_ident(dxp, lp->dn_ctfp, lp->dn_type);
3896		dt_node_type_assign(dnp, DT_DYN_CTFP(dtp), DT_DYN_TYPE(dtp),
3897		    B_FALSE);
3898		dt_node_attr_assign(dnp,
3899		    dt_attr_min(rp->dn_attr, dnp->dn_ident->di_attr));
3900		break;
3901	}
3902
3903	case DT_TOK_LPAR: {
3904		ctf_id_t ltype, rtype;
3905		uint_t lkind, rkind;
3906
3907		assert(lp->dn_kind == DT_NODE_TYPE);
3908		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3909
3910		ltype = ctf_type_resolve(lp->dn_ctfp, lp->dn_type);
3911		lkind = ctf_type_kind(lp->dn_ctfp, ltype);
3912
3913		rtype = ctf_type_resolve(rp->dn_ctfp, rp->dn_type);
3914		rkind = ctf_type_kind(rp->dn_ctfp, rtype);
3915
3916		/*
3917		 * The rules for casting are loosely explained in K&R[A7.5]
3918		 * and K&R[A6].  Basically, we can cast to the same type or
3919		 * same base type, between any kind of scalar values, from
3920		 * arrays to pointers, and we can cast anything to void.
3921		 * To these rules D adds casts from scalars to strings.
3922		 */
3923		if (ctf_type_compat(lp->dn_ctfp, lp->dn_type,
3924		    rp->dn_ctfp, rp->dn_type))
3925			/*EMPTY*/;
3926		else if (dt_node_is_scalar(lp) &&
3927		    (dt_node_is_scalar(rp) || rkind == CTF_K_FUNCTION))
3928			/*EMPTY*/;
3929		else if (dt_node_is_void(lp))
3930			/*EMPTY*/;
3931		else if (lkind == CTF_K_POINTER && dt_node_is_pointer(rp))
3932			/*EMPTY*/;
3933		else if (dt_node_is_string(lp) && (dt_node_is_scalar(rp) ||
3934		    dt_node_is_pointer(rp) || dt_node_is_strcompat(rp)))
3935			/*EMPTY*/;
3936		else {
3937			xyerror(D_CAST_INVAL,
3938			    "invalid cast expression: \"%s\" to \"%s\"\n",
3939			    dt_node_type_name(rp, n1, sizeof (n1)),
3940			    dt_node_type_name(lp, n2, sizeof (n2)));
3941		}
3942
3943		dt_node_type_propagate(lp, dnp); /* see K&R[A7.5] */
3944		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3945
3946		/*
3947		 * If it's a pointer then should be able to (attempt to)
3948		 * assign to it.
3949		 */
3950		if (lkind == CTF_K_POINTER)
3951			dnp->dn_flags |= DT_NF_WRITABLE;
3952
3953		break;
3954	}
3955
3956	case DT_TOK_COMMA:
3957		lp = dnp->dn_left = dt_node_cook(lp, DT_IDFLG_REF);
3958		rp = dnp->dn_right = dt_node_cook(rp, DT_IDFLG_REF);
3959
3960		if (dt_node_is_dynamic(lp) || dt_node_is_dynamic(rp)) {
3961			xyerror(D_OP_DYN, "operator %s operands "
3962			    "cannot be of dynamic type\n", opstr(op));
3963		}
3964
3965		if (dt_node_is_actfunc(lp) || dt_node_is_actfunc(rp)) {
3966			xyerror(D_OP_ACT, "operator %s operands "
3967			    "cannot be actions\n", opstr(op));
3968		}
3969
3970		dt_node_type_propagate(rp, dnp); /* see K&R[A7.18] */
3971		dt_node_attr_assign(dnp, dt_attr_min(lp->dn_attr, rp->dn_attr));
3972		break;
3973
3974	default:
3975		xyerror(D_UNKNOWN, "invalid binary op %s\n", opstr(op));
3976	}
3977
3978	/*
3979	 * Complete the conversion of E1[E2] to *((E1)+(E2)) that we started
3980	 * at the top of our switch() above (see K&R[A7.3.1]).  Since E2 is
3981	 * parsed as an argument_expression_list by dt_grammar.y, we can
3982	 * end up with a comma-separated list inside of a non-associative
3983	 * array reference.  We check for this and report an appropriate error.
3984	 */
3985	if (dnp->dn_op == DT_TOK_LBRAC && op == DT_TOK_ADD) {
3986		dt_node_t *pnp;
3987
3988		if (rp->dn_list != NULL) {
3989			xyerror(D_ARR_BADREF,
3990			    "cannot access %s as an associative array\n",
3991			    dt_node_name(lp, n1, sizeof (n1)));
3992		}
3993
3994		dnp->dn_op = DT_TOK_ADD;
3995		pnp = dt_node_op1(DT_TOK_DEREF, dnp);
3996
3997		/*
3998		 * Cook callbacks are not typically permitted to allocate nodes.
3999		 * When we do, we must insert them in the middle of an existing
4000		 * allocation list rather than having them appended to the pcb
4001		 * list because the sub-expression may be part of a definition.
4002		 */
4003		assert(yypcb->pcb_list == pnp);
4004		yypcb->pcb_list = pnp->dn_link;
4005
4006		pnp->dn_link = dnp->dn_link;
4007		dnp->dn_link = pnp;
4008
4009		return (dt_node_cook(pnp, DT_IDFLG_REF));
4010	}
4011
4012	return (dnp);
4013}
4014
4015/*ARGSUSED*/
4016static dt_node_t *
4017dt_cook_op3(dt_node_t *dnp, uint_t idflags)
4018{
4019	dt_node_t *lp, *rp;
4020	ctf_file_t *ctfp;
4021	ctf_id_t type;
4022
4023	dnp->dn_expr = dt_node_cook(dnp->dn_expr, DT_IDFLG_REF);
4024	lp = dnp->dn_left = dt_node_cook(dnp->dn_left, DT_IDFLG_REF);
4025	rp = dnp->dn_right = dt_node_cook(dnp->dn_right, DT_IDFLG_REF);
4026
4027	if (!dt_node_is_scalar(dnp->dn_expr)) {
4028		xyerror(D_OP_SCALAR,
4029		    "operator ?: expression must be of scalar type\n");
4030	}
4031
4032	if (dt_node_is_dynamic(lp) || dt_node_is_dynamic(rp)) {
4033		xyerror(D_OP_DYN,
4034		    "operator ?: operands cannot be of dynamic type\n");
4035	}
4036
4037	/*
4038	 * The rules for type checking for the ternary operator are complex and
4039	 * are described in the ANSI-C spec (see K&R[A7.16]).  We implement
4040	 * the various tests in order from least to most expensive.
4041	 */
4042	if (ctf_type_compat(lp->dn_ctfp, lp->dn_type,
4043	    rp->dn_ctfp, rp->dn_type)) {
4044		ctfp = lp->dn_ctfp;
4045		type = lp->dn_type;
4046	} else if (dt_node_is_integer(lp) && dt_node_is_integer(rp)) {
4047		dt_type_promote(lp, rp, &ctfp, &type);
4048	} else if (dt_node_is_strcompat(lp) && dt_node_is_strcompat(rp) &&
4049	    (dt_node_is_string(lp) || dt_node_is_string(rp))) {
4050		ctfp = DT_STR_CTFP(yypcb->pcb_hdl);
4051		type = DT_STR_TYPE(yypcb->pcb_hdl);
4052	} else if (dt_node_is_ptrcompat(lp, rp, &ctfp, &type) == 0) {
4053		xyerror(D_OP_INCOMPAT,
4054		    "operator ?: operands must have compatible types\n");
4055	}
4056
4057	if (dt_node_is_actfunc(lp) || dt_node_is_actfunc(rp)) {
4058		xyerror(D_OP_ACT, "action cannot be "
4059		    "used in a conditional context\n");
4060	}
4061
4062	dt_node_type_assign(dnp, ctfp, type, B_FALSE);
4063	dt_node_attr_assign(dnp, dt_attr_min(dnp->dn_expr->dn_attr,
4064	    dt_attr_min(lp->dn_attr, rp->dn_attr)));
4065
4066	return (dnp);
4067}
4068
4069static dt_node_t *
4070dt_cook_statement(dt_node_t *dnp, uint_t idflags)
4071{
4072	dnp->dn_expr = dt_node_cook(dnp->dn_expr, idflags);
4073	dt_node_attr_assign(dnp, dnp->dn_expr->dn_attr);
4074
4075	return (dnp);
4076}
4077
4078/*
4079 * If dn_aggfun is set, this node is a collapsed aggregation assignment (see
4080 * the special case code for DT_TOK_ASGN in dt_cook_op2() above), in which
4081 * case we cook both the tuple and the function call.  If dn_aggfun is NULL,
4082 * this node is just a reference to the aggregation's type and attributes.
4083 */
4084/*ARGSUSED*/
4085static dt_node_t *
4086dt_cook_aggregation(dt_node_t *dnp, uint_t idflags)
4087{
4088	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
4089
4090	if (dnp->dn_aggfun != NULL) {
4091		dnp->dn_aggfun = dt_node_cook(dnp->dn_aggfun, DT_IDFLG_REF);
4092		dt_node_attr_assign(dnp, dt_ident_cook(dnp,
4093		    dnp->dn_ident, &dnp->dn_aggtup));
4094	} else {
4095		dt_node_type_assign(dnp, DT_DYN_CTFP(dtp), DT_DYN_TYPE(dtp),
4096		    B_FALSE);
4097		dt_node_attr_assign(dnp, dnp->dn_ident->di_attr);
4098	}
4099
4100	return (dnp);
4101}
4102
4103/*
4104 * Since D permits new variable identifiers to be instantiated in any program
4105 * expression, we may need to cook a clause's predicate either before or after
4106 * the action list depending on the program code in question.  Consider:
4107 *
4108 * probe-description-list	probe-description-list
4109 * /x++/			/x == 0/
4110 * {				{
4111 *     trace(x);		    trace(x++);
4112 * }				}
4113 *
4114 * In the left-hand example, the predicate uses operator ++ to instantiate 'x'
4115 * as a variable of type int64_t.  The predicate must be cooked first because
4116 * otherwise the statement trace(x) refers to an unknown identifier.  In the
4117 * right-hand example, the action list uses ++ to instantiate 'x'; the action
4118 * list must be cooked first because otherwise the predicate x == 0 refers to
4119 * an unknown identifier.  In order to simplify programming, we support both.
4120 *
4121 * When cooking a clause, we cook the action statements before the predicate by
4122 * default, since it seems more common to create or modify identifiers in the
4123 * action list.  If cooking fails due to an unknown identifier, we attempt to
4124 * cook the predicate (i.e. do it first) and then go back and cook the actions.
4125 * If this, too, fails (or if we get an error other than D_IDENT_UNDEF) we give
4126 * up and report failure back to the user.  There are five possible paths:
4127 *
4128 * cook actions = OK, cook predicate = OK -> OK
4129 * cook actions = OK, cook predicate = ERR -> ERR
4130 * cook actions = ERR, cook predicate = ERR -> ERR
4131 * cook actions = ERR, cook predicate = OK, cook actions = OK -> OK
4132 * cook actions = ERR, cook predicate = OK, cook actions = ERR -> ERR
4133 *
4134 * The programmer can still defeat our scheme by creating circular definition
4135 * dependencies between predicates and actions, as in this example clause:
4136 *
4137 * probe-description-list
4138 * /x++ && y == 0/
4139 * {
4140 * 	trace(x + y++);
4141 * }
4142 *
4143 * but it doesn't seem worth the complexity to handle such rare cases.  The
4144 * user can simply use the D variable declaration syntax to work around them.
4145 */
4146static dt_node_t *
4147dt_cook_clause(dt_node_t *dnp, uint_t idflags)
4148{
4149	volatile int err, tries;
4150	jmp_buf ojb;
4151
4152	/*
4153	 * Before assigning dn_ctxattr, temporarily assign the probe attribute
4154	 * to 'dnp' itself to force an attribute check and minimum violation.
4155	 */
4156	dt_node_attr_assign(dnp, yypcb->pcb_pinfo.dtp_attr);
4157	dnp->dn_ctxattr = yypcb->pcb_pinfo.dtp_attr;
4158
4159	bcopy(yypcb->pcb_jmpbuf, ojb, sizeof (jmp_buf));
4160	tries = 0;
4161
4162	if (dnp->dn_pred != NULL && (err = setjmp(yypcb->pcb_jmpbuf)) != 0) {
4163		bcopy(ojb, yypcb->pcb_jmpbuf, sizeof (jmp_buf));
4164		if (tries++ != 0 || err != EDT_COMPILER || (
4165		    yypcb->pcb_hdl->dt_errtag != dt_errtag(D_IDENT_UNDEF) &&
4166		    yypcb->pcb_hdl->dt_errtag != dt_errtag(D_VAR_UNDEF)))
4167			longjmp(yypcb->pcb_jmpbuf, err);
4168	}
4169
4170	if (tries == 0) {
4171		yylabel("action list");
4172
4173		dt_node_attr_assign(dnp,
4174		    dt_node_list_cook(&dnp->dn_acts, idflags));
4175
4176		bcopy(ojb, yypcb->pcb_jmpbuf, sizeof (jmp_buf));
4177		yylabel(NULL);
4178	}
4179
4180	if (dnp->dn_pred != NULL) {
4181		yylabel("predicate");
4182
4183		dnp->dn_pred = dt_node_cook(dnp->dn_pred, idflags);
4184		dt_node_attr_assign(dnp,
4185		    dt_attr_min(dnp->dn_attr, dnp->dn_pred->dn_attr));
4186
4187		if (!dt_node_is_scalar(dnp->dn_pred)) {
4188			xyerror(D_PRED_SCALAR,
4189			    "predicate result must be of scalar type\n");
4190		}
4191
4192		yylabel(NULL);
4193	}
4194
4195	if (tries != 0) {
4196		yylabel("action list");
4197
4198		dt_node_attr_assign(dnp,
4199		    dt_node_list_cook(&dnp->dn_acts, idflags));
4200
4201		yylabel(NULL);
4202	}
4203
4204	return (dnp);
4205}
4206
4207/*ARGSUSED*/
4208static dt_node_t *
4209dt_cook_inline(dt_node_t *dnp, uint_t idflags)
4210{
4211	dt_idnode_t *inp = dnp->dn_ident->di_iarg;
4212	dt_ident_t *rdp;
4213
4214	char n1[DT_TYPE_NAMELEN];
4215	char n2[DT_TYPE_NAMELEN];
4216
4217	assert(dnp->dn_ident->di_flags & DT_IDFLG_INLINE);
4218	assert(inp->din_root->dn_flags & DT_NF_COOKED);
4219
4220	/*
4221	 * If we are inlining a translation, verify that the inline declaration
4222	 * type exactly matches the type that is returned by the translation.
4223	 * Otherwise just use dt_node_is_argcompat() to check the types.
4224	 */
4225	if ((rdp = dt_node_resolve(inp->din_root, DT_IDENT_XLSOU)) != NULL ||
4226	    (rdp = dt_node_resolve(inp->din_root, DT_IDENT_XLPTR)) != NULL) {
4227
4228		ctf_file_t *lctfp = dnp->dn_ctfp;
4229		ctf_id_t ltype = ctf_type_resolve(lctfp, dnp->dn_type);
4230
4231		dt_xlator_t *dxp = rdp->di_data;
4232		ctf_file_t *rctfp = dxp->dx_dst_ctfp;
4233		ctf_id_t rtype = dxp->dx_dst_base;
4234
4235		if (ctf_type_kind(lctfp, ltype) == CTF_K_POINTER) {
4236			ltype = ctf_type_reference(lctfp, ltype);
4237			ltype = ctf_type_resolve(lctfp, ltype);
4238		}
4239
4240		if (ctf_type_compat(lctfp, ltype, rctfp, rtype) == 0) {
4241			dnerror(dnp, D_OP_INCOMPAT,
4242			    "inline %s definition uses incompatible types: "
4243			    "\"%s\" = \"%s\"\n", dnp->dn_ident->di_name,
4244			    dt_type_name(lctfp, ltype, n1, sizeof (n1)),
4245			    dt_type_name(rctfp, rtype, n2, sizeof (n2)));
4246		}
4247
4248	} else if (dt_node_is_argcompat(dnp, inp->din_root) == 0) {
4249		dnerror(dnp, D_OP_INCOMPAT,
4250		    "inline %s definition uses incompatible types: "
4251		    "\"%s\" = \"%s\"\n", dnp->dn_ident->di_name,
4252		    dt_node_type_name(dnp, n1, sizeof (n1)),
4253		    dt_node_type_name(inp->din_root, n2, sizeof (n2)));
4254	}
4255
4256	return (dnp);
4257}
4258
4259static dt_node_t *
4260dt_cook_member(dt_node_t *dnp, uint_t idflags)
4261{
4262	dnp->dn_membexpr = dt_node_cook(dnp->dn_membexpr, idflags);
4263	dt_node_attr_assign(dnp, dnp->dn_membexpr->dn_attr);
4264	return (dnp);
4265}
4266
4267/*ARGSUSED*/
4268static dt_node_t *
4269dt_cook_xlator(dt_node_t *dnp, uint_t idflags)
4270{
4271	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
4272	dt_xlator_t *dxp = dnp->dn_xlator;
4273	dt_node_t *mnp;
4274
4275	char n1[DT_TYPE_NAMELEN];
4276	char n2[DT_TYPE_NAMELEN];
4277
4278	dtrace_attribute_t attr = _dtrace_maxattr;
4279	ctf_membinfo_t ctm;
4280
4281	/*
4282	 * Before cooking each translator member, we push a reference to the
4283	 * hash containing translator-local identifiers on to pcb_globals to
4284	 * temporarily interpose these identifiers in front of other globals.
4285	 */
4286	dt_idstack_push(&yypcb->pcb_globals, dxp->dx_locals);
4287
4288	for (mnp = dnp->dn_members; mnp != NULL; mnp = mnp->dn_list) {
4289		if (ctf_member_info(dxp->dx_dst_ctfp, dxp->dx_dst_type,
4290		    mnp->dn_membname, &ctm) == CTF_ERR) {
4291			xyerror(D_XLATE_MEMB,
4292			    "translator member %s is not a member of %s\n",
4293			    mnp->dn_membname, ctf_type_name(dxp->dx_dst_ctfp,
4294			    dxp->dx_dst_type, n1, sizeof (n1)));
4295		}
4296
4297		(void) dt_node_cook(mnp, DT_IDFLG_REF);
4298		dt_node_type_assign(mnp, dxp->dx_dst_ctfp, ctm.ctm_type,
4299		    B_FALSE);
4300		attr = dt_attr_min(attr, mnp->dn_attr);
4301
4302		if (dt_node_is_argcompat(mnp, mnp->dn_membexpr) == 0) {
4303			xyerror(D_XLATE_INCOMPAT,
4304			    "translator member %s definition uses "
4305			    "incompatible types: \"%s\" = \"%s\"\n",
4306			    mnp->dn_membname,
4307			    dt_node_type_name(mnp, n1, sizeof (n1)),
4308			    dt_node_type_name(mnp->dn_membexpr,
4309			    n2, sizeof (n2)));
4310		}
4311	}
4312
4313	dt_idstack_pop(&yypcb->pcb_globals, dxp->dx_locals);
4314
4315	dxp->dx_souid.di_attr = attr;
4316	dxp->dx_ptrid.di_attr = attr;
4317
4318	dt_node_type_assign(dnp, DT_DYN_CTFP(dtp), DT_DYN_TYPE(dtp), B_FALSE);
4319	dt_node_attr_assign(dnp, _dtrace_defattr);
4320
4321	return (dnp);
4322}
4323
4324static void
4325dt_node_provider_cmp_argv(dt_provider_t *pvp, dt_node_t *pnp, const char *kind,
4326    uint_t old_argc, dt_node_t *old_argv, uint_t new_argc, dt_node_t *new_argv)
4327{
4328	dt_probe_t *prp = pnp->dn_ident->di_data;
4329	uint_t i;
4330
4331	char n1[DT_TYPE_NAMELEN];
4332	char n2[DT_TYPE_NAMELEN];
4333
4334	if (old_argc != new_argc) {
4335		dnerror(pnp, D_PROV_INCOMPAT,
4336		    "probe %s:%s %s prototype mismatch:\n"
4337		    "\t current: %u arg%s\n\tprevious: %u arg%s\n",
4338		    pvp->pv_desc.dtvd_name, prp->pr_ident->di_name, kind,
4339		    new_argc, new_argc != 1 ? "s" : "",
4340		    old_argc, old_argc != 1 ? "s" : "");
4341	}
4342
4343	for (i = 0; i < old_argc; i++,
4344	    old_argv = old_argv->dn_list, new_argv = new_argv->dn_list) {
4345		if (ctf_type_cmp(old_argv->dn_ctfp, old_argv->dn_type,
4346		    new_argv->dn_ctfp, new_argv->dn_type) == 0)
4347			continue;
4348
4349		dnerror(pnp, D_PROV_INCOMPAT,
4350		    "probe %s:%s %s prototype argument #%u mismatch:\n"
4351		    "\t current: %s\n\tprevious: %s\n",
4352		    pvp->pv_desc.dtvd_name, prp->pr_ident->di_name, kind, i + 1,
4353		    dt_node_type_name(new_argv, n1, sizeof (n1)),
4354		    dt_node_type_name(old_argv, n2, sizeof (n2)));
4355	}
4356}
4357
4358/*
4359 * Compare a new probe declaration with an existing probe definition (either
4360 * from a previous declaration or cached from the kernel).  If the existing
4361 * definition and declaration both have an input and output parameter list,
4362 * compare both lists.  Otherwise compare only the output parameter lists.
4363 */
4364static void
4365dt_node_provider_cmp(dt_provider_t *pvp, dt_node_t *pnp,
4366    dt_probe_t *old, dt_probe_t *new)
4367{
4368	dt_node_provider_cmp_argv(pvp, pnp, "output",
4369	    old->pr_xargc, old->pr_xargs, new->pr_xargc, new->pr_xargs);
4370
4371	if (old->pr_nargs != old->pr_xargs && new->pr_nargs != new->pr_xargs) {
4372		dt_node_provider_cmp_argv(pvp, pnp, "input",
4373		    old->pr_nargc, old->pr_nargs, new->pr_nargc, new->pr_nargs);
4374	}
4375
4376	if (old->pr_nargs == old->pr_xargs && new->pr_nargs != new->pr_xargs) {
4377		if (pvp->pv_flags & DT_PROVIDER_IMPL) {
4378			dnerror(pnp, D_PROV_INCOMPAT,
4379			    "provider interface mismatch: %s\n"
4380			    "\t current: probe %s:%s has an output prototype\n"
4381			    "\tprevious: probe %s:%s has no output prototype\n",
4382			    pvp->pv_desc.dtvd_name, pvp->pv_desc.dtvd_name,
4383			    new->pr_ident->di_name, pvp->pv_desc.dtvd_name,
4384			    old->pr_ident->di_name);
4385		}
4386
4387		if (old->pr_ident->di_gen == yypcb->pcb_hdl->dt_gen)
4388			old->pr_ident->di_flags |= DT_IDFLG_ORPHAN;
4389
4390		dt_idhash_delete(pvp->pv_probes, old->pr_ident);
4391		dt_probe_declare(pvp, new);
4392	}
4393}
4394
4395static void
4396dt_cook_probe(dt_node_t *dnp, dt_provider_t *pvp)
4397{
4398	dtrace_hdl_t *dtp = yypcb->pcb_hdl;
4399	dt_probe_t *prp = dnp->dn_ident->di_data;
4400
4401	dt_xlator_t *dxp;
4402	uint_t i;
4403
4404	char n1[DT_TYPE_NAMELEN];
4405	char n2[DT_TYPE_NAMELEN];
4406
4407	if (prp->pr_nargs == prp->pr_xargs)
4408		return;
4409
4410	for (i = 0; i < prp->pr_xargc; i++) {
4411		dt_node_t *xnp = prp->pr_xargv[i];
4412		dt_node_t *nnp = prp->pr_nargv[prp->pr_mapping[i]];
4413
4414		if ((dxp = dt_xlator_lookup(dtp,
4415		    nnp, xnp, DT_XLATE_FUZZY)) != NULL) {
4416			if (dt_provider_xref(dtp, pvp, dxp->dx_id) != 0)
4417				longjmp(yypcb->pcb_jmpbuf, EDT_NOMEM);
4418			continue;
4419		}
4420
4421		if (dt_node_is_argcompat(nnp, xnp))
4422			continue; /* no translator defined and none required */
4423
4424		dnerror(dnp, D_PROV_PRXLATOR, "translator for %s:%s output "
4425		    "argument #%u from %s to %s is not defined\n",
4426		    pvp->pv_desc.dtvd_name, dnp->dn_ident->di_name, i + 1,
4427		    dt_node_type_name(nnp, n1, sizeof (n1)),
4428		    dt_node_type_name(xnp, n2, sizeof (n2)));
4429	}
4430}
4431
4432/*ARGSUSED*/
4433static dt_node_t *
4434dt_cook_provider(dt_node_t *dnp, uint_t idflags)
4435{
4436	dt_provider_t *pvp = dnp->dn_provider;
4437	dt_node_t *pnp;
4438
4439	/*
4440	 * If we're declaring a provider for the first time and it is unknown
4441	 * to dtrace(7D), insert the probe definitions into the provider's hash.
4442	 * If we're redeclaring a known provider, verify the interface matches.
4443	 */
4444	for (pnp = dnp->dn_probes; pnp != NULL; pnp = pnp->dn_list) {
4445		const char *probename = pnp->dn_ident->di_name;
4446		dt_probe_t *prp = dt_probe_lookup(pvp, probename);
4447
4448		assert(pnp->dn_kind == DT_NODE_PROBE);
4449
4450		if (prp != NULL && dnp->dn_provred) {
4451			dt_node_provider_cmp(pvp, pnp,
4452			    prp, pnp->dn_ident->di_data);
4453		} else if (prp == NULL && dnp->dn_provred) {
4454			dnerror(pnp, D_PROV_INCOMPAT,
4455			    "provider interface mismatch: %s\n"
4456			    "\t current: probe %s:%s defined\n"
4457			    "\tprevious: probe %s:%s not defined\n",
4458			    dnp->dn_provname, dnp->dn_provname,
4459			    probename, dnp->dn_provname, probename);
4460		} else if (prp != NULL) {
4461			dnerror(pnp, D_PROV_PRDUP, "probe redeclared: %s:%s\n",
4462			    dnp->dn_provname, probename);
4463		} else
4464			dt_probe_declare(pvp, pnp->dn_ident->di_data);
4465
4466		dt_cook_probe(pnp, pvp);
4467	}
4468
4469	return (dnp);
4470}
4471
4472/*ARGSUSED*/
4473static dt_node_t *
4474dt_cook_none(dt_node_t *dnp, uint_t idflags)
4475{
4476	return (dnp);
4477}
4478
4479static dt_node_t *(*dt_cook_funcs[])(dt_node_t *, uint_t) = {
4480	dt_cook_none,		/* DT_NODE_FREE */
4481	dt_cook_none,		/* DT_NODE_INT */
4482	dt_cook_none,		/* DT_NODE_STRING */
4483	dt_cook_ident,		/* DT_NODE_IDENT */
4484	dt_cook_var,		/* DT_NODE_VAR */
4485	dt_cook_none,		/* DT_NODE_SYM */
4486	dt_cook_none,		/* DT_NODE_TYPE */
4487	dt_cook_func,		/* DT_NODE_FUNC */
4488	dt_cook_op1,		/* DT_NODE_OP1 */
4489	dt_cook_op2,		/* DT_NODE_OP2 */
4490	dt_cook_op3,		/* DT_NODE_OP3 */
4491	dt_cook_statement,	/* DT_NODE_DEXPR */
4492	dt_cook_statement,	/* DT_NODE_DFUNC */
4493	dt_cook_aggregation,	/* DT_NODE_AGG */
4494	dt_cook_none,		/* DT_NODE_PDESC */
4495	dt_cook_clause,		/* DT_NODE_CLAUSE */
4496	dt_cook_inline,		/* DT_NODE_INLINE */
4497	dt_cook_member,		/* DT_NODE_MEMBER */
4498	dt_cook_xlator,		/* DT_NODE_XLATOR */
4499	dt_cook_none,		/* DT_NODE_PROBE */
4500	dt_cook_provider,	/* DT_NODE_PROVIDER */
4501	dt_cook_none,		/* DT_NODE_PROG */
4502	dt_cook_none,		/* DT_NODE_IF */
4503};
4504
4505/*
4506 * Recursively cook the parse tree starting at the specified node.  The idflags
4507 * parameter is used to indicate the type of reference (r/w) and is applied to
4508 * the resulting identifier if it is a D variable or D aggregation.
4509 */
4510dt_node_t *
4511dt_node_cook(dt_node_t *dnp, uint_t idflags)
4512{
4513	int oldlineno = yylineno;
4514
4515	yylineno = dnp->dn_line;
4516
4517	assert(dnp->dn_kind <
4518	    sizeof (dt_cook_funcs) / sizeof (dt_cook_funcs[0]));
4519	dnp = dt_cook_funcs[dnp->dn_kind](dnp, idflags);
4520	dnp->dn_flags |= DT_NF_COOKED;
4521
4522	if (dnp->dn_kind == DT_NODE_VAR || dnp->dn_kind == DT_NODE_AGG)
4523		dnp->dn_ident->di_flags |= idflags;
4524
4525	yylineno = oldlineno;
4526	return (dnp);
4527}
4528
4529dtrace_attribute_t
4530dt_node_list_cook(dt_node_t **pnp, uint_t idflags)
4531{
4532	dtrace_attribute_t attr = _dtrace_defattr;
4533	dt_node_t *dnp, *nnp;
4534
4535	for (dnp = (pnp != NULL ? *pnp : NULL); dnp != NULL; dnp = nnp) {
4536		nnp = dnp->dn_list;
4537		dnp = *pnp = dt_node_cook(dnp, idflags);
4538		attr = dt_attr_min(attr, dnp->dn_attr);
4539		dnp->dn_list = nnp;
4540		pnp = &dnp->dn_list;
4541	}
4542
4543	return (attr);
4544}
4545
4546void
4547dt_node_list_free(dt_node_t **pnp)
4548{
4549	dt_node_t *dnp, *nnp;
4550
4551	for (dnp = (pnp != NULL ? *pnp : NULL); dnp != NULL; dnp = nnp) {
4552		nnp = dnp->dn_list;
4553		dt_node_free(dnp);
4554	}
4555
4556	if (pnp != NULL)
4557		*pnp = NULL;
4558}
4559
4560void
4561dt_node_link_free(dt_node_t **pnp)
4562{
4563	dt_node_t *dnp, *nnp;
4564
4565	for (dnp = (pnp != NULL ? *pnp : NULL); dnp != NULL; dnp = nnp) {
4566		nnp = dnp->dn_link;
4567		dt_node_free(dnp);
4568	}
4569
4570	for (dnp = (pnp != NULL ? *pnp : NULL); dnp != NULL; dnp = nnp) {
4571		nnp = dnp->dn_link;
4572		free(dnp);
4573	}
4574
4575	if (pnp != NULL)
4576		*pnp = NULL;
4577}
4578
4579dt_node_t *
4580dt_node_link(dt_node_t *lp, dt_node_t *rp)
4581{
4582	dt_node_t *dnp;
4583
4584	if (lp == NULL)
4585		return (rp);
4586	else if (rp == NULL)
4587		return (lp);
4588
4589	for (dnp = lp; dnp->dn_list != NULL; dnp = dnp->dn_list)
4590		continue;
4591
4592	dnp->dn_list = rp;
4593	return (lp);
4594}
4595
4596/*
4597 * Compute the DOF dtrace_diftype_t representation of a node's type.  This is
4598 * called from a variety of places in the library so it cannot assume yypcb
4599 * is valid: any references to handle-specific data must be made through 'dtp'.
4600 */
4601void
4602dt_node_diftype(dtrace_hdl_t *dtp, const dt_node_t *dnp, dtrace_diftype_t *tp)
4603{
4604	if (dnp->dn_ctfp == DT_STR_CTFP(dtp) &&
4605	    dnp->dn_type == DT_STR_TYPE(dtp)) {
4606		tp->dtdt_kind = DIF_TYPE_STRING;
4607		tp->dtdt_ckind = CTF_K_UNKNOWN;
4608	} else {
4609		tp->dtdt_kind = DIF_TYPE_CTF;
4610		tp->dtdt_ckind = ctf_type_kind(dnp->dn_ctfp,
4611		    ctf_type_resolve(dnp->dn_ctfp, dnp->dn_type));
4612	}
4613
4614	tp->dtdt_flags = (dnp->dn_flags & DT_NF_REF) ?
4615	    (dnp->dn_flags & DT_NF_USERLAND) ? DIF_TF_BYUREF :
4616	    DIF_TF_BYREF : 0;
4617	tp->dtdt_pad = 0;
4618	tp->dtdt_size = ctf_type_size(dnp->dn_ctfp, dnp->dn_type);
4619}
4620
4621/*
4622 * Output the parse tree as D.  The "-xtree=8" argument will call this
4623 * function to print out the program after any syntactic sugar
4624 * transformations have been applied (e.g. to implement "if").  The
4625 * resulting output can be used to understand the transformations
4626 * applied by these features, or to run such a script on a system that
4627 * does not support these features
4628 *
4629 * Note that the output does not express precisely the same program as
4630 * the input.  In particular:
4631 *  - Only the clauses are output.  #pragma options, variable
4632 *    declarations, etc. are excluded.
4633 *  - Command argument substitution has already been done, so the output
4634 *    will not contain e.g. $$1, but rather the substituted string.
4635 */
4636void
4637dt_printd(dt_node_t *dnp, FILE *fp, int depth)
4638{
4639	dt_node_t *arg;
4640
4641	switch (dnp->dn_kind) {
4642	case DT_NODE_INT:
4643		(void) fprintf(fp, "0x%llx", (u_longlong_t)dnp->dn_value);
4644		if (!(dnp->dn_flags & DT_NF_SIGNED))
4645			(void) fprintf(fp, "u");
4646		break;
4647
4648	case DT_NODE_STRING: {
4649		char *escd = strchr2esc(dnp->dn_string, strlen(dnp->dn_string));
4650		(void) fprintf(fp, "\"%s\"", escd);
4651		free(escd);
4652		break;
4653	}
4654
4655	case DT_NODE_IDENT:
4656		(void) fprintf(fp, "%s", dnp->dn_string);
4657		break;
4658
4659	case DT_NODE_VAR:
4660		(void) fprintf(fp, "%s%s",
4661		    (dnp->dn_ident->di_flags & DT_IDFLG_LOCAL) ? "this->" :
4662		    (dnp->dn_ident->di_flags & DT_IDFLG_TLS) ? "self->" : "",
4663		    dnp->dn_ident->di_name);
4664
4665		if (dnp->dn_args != NULL) {
4666			(void) fprintf(fp, "[");
4667
4668			for (arg = dnp->dn_args; arg != NULL;
4669			    arg = arg->dn_list) {
4670				dt_printd(arg, fp, 0);
4671				if (arg->dn_list != NULL)
4672					(void) fprintf(fp, ", ");
4673			}
4674
4675			(void) fprintf(fp, "]");
4676		}
4677		break;
4678
4679	case DT_NODE_SYM: {
4680		const dtrace_syminfo_t *dts = dnp->dn_ident->di_data;
4681		(void) fprintf(fp, "%s`%s", dts->dts_object, dts->dts_name);
4682		break;
4683	}
4684	case DT_NODE_FUNC:
4685		(void) fprintf(fp, "%s(", dnp->dn_ident->di_name);
4686
4687		for (arg = dnp->dn_args; arg != NULL; arg = arg->dn_list) {
4688			dt_printd(arg, fp, 0);
4689			if (arg->dn_list != NULL)
4690				(void) fprintf(fp, ", ");
4691		}
4692		(void) fprintf(fp, ")");
4693		break;
4694
4695	case DT_NODE_OP1:
4696		(void) fprintf(fp, "%s(", opstr(dnp->dn_op));
4697		dt_printd(dnp->dn_child, fp, 0);
4698		(void) fprintf(fp, ")");
4699		break;
4700
4701	case DT_NODE_OP2:
4702		(void) fprintf(fp, "(");
4703		dt_printd(dnp->dn_left, fp, 0);
4704		if (dnp->dn_op == DT_TOK_LPAR) {
4705			(void) fprintf(fp, ")");
4706			dt_printd(dnp->dn_right, fp, 0);
4707			break;
4708		}
4709		if (dnp->dn_op == DT_TOK_PTR || dnp->dn_op == DT_TOK_DOT ||
4710		    dnp->dn_op == DT_TOK_LBRAC)
4711			(void) fprintf(fp, "%s", opstr(dnp->dn_op));
4712		else
4713			(void) fprintf(fp, " %s ", opstr(dnp->dn_op));
4714		dt_printd(dnp->dn_right, fp, 0);
4715		if (dnp->dn_op == DT_TOK_LBRAC) {
4716			dt_node_t *ln = dnp->dn_right;
4717			while (ln->dn_list != NULL) {
4718				(void) fprintf(fp, ", ");
4719				dt_printd(ln->dn_list, fp, depth);
4720				ln = ln->dn_list;
4721			}
4722			(void) fprintf(fp, "]");
4723		}
4724		(void) fprintf(fp, ")");
4725		break;
4726
4727	case DT_NODE_OP3:
4728		(void) fprintf(fp, "(");
4729		dt_printd(dnp->dn_expr, fp, 0);
4730		(void) fprintf(fp, " ? ");
4731		dt_printd(dnp->dn_left, fp, 0);
4732		(void) fprintf(fp, " : ");
4733		dt_printd(dnp->dn_right, fp, 0);
4734		(void) fprintf(fp, ")");
4735		break;
4736
4737	case DT_NODE_DEXPR:
4738	case DT_NODE_DFUNC:
4739		(void) fprintf(fp, "%*s", depth * 8, "");
4740		dt_printd(dnp->dn_expr, fp, depth + 1);
4741		(void) fprintf(fp, ";\n");
4742		break;
4743
4744	case DT_NODE_PDESC:
4745		(void) fprintf(fp, "%s:%s:%s:%s",
4746		    dnp->dn_desc->dtpd_provider, dnp->dn_desc->dtpd_mod,
4747		    dnp->dn_desc->dtpd_func, dnp->dn_desc->dtpd_name);
4748		break;
4749
4750	case DT_NODE_CLAUSE:
4751		for (arg = dnp->dn_pdescs; arg != NULL; arg = arg->dn_list) {
4752			dt_printd(arg, fp, 0);
4753			if (arg->dn_list != NULL)
4754				(void) fprintf(fp, ",");
4755			(void) fprintf(fp, "\n");
4756		}
4757
4758		if (dnp->dn_pred != NULL) {
4759			(void) fprintf(fp, "/");
4760			dt_printd(dnp->dn_pred, fp, 0);
4761			(void) fprintf(fp, "/\n");
4762		}
4763			(void) fprintf(fp, "{\n");
4764
4765		for (arg = dnp->dn_acts; arg != NULL; arg = arg->dn_list)
4766			dt_printd(arg, fp, depth + 1);
4767		(void) fprintf(fp, "}\n");
4768		(void) fprintf(fp, "\n");
4769		break;
4770
4771	case DT_NODE_IF:
4772		(void) fprintf(fp, "%*sif (", depth * 8, "");
4773		dt_printd(dnp->dn_conditional, fp, 0);
4774		(void) fprintf(fp, ") {\n");
4775
4776		for (arg = dnp->dn_body; arg != NULL; arg = arg->dn_list)
4777			dt_printd(arg, fp, depth + 1);
4778		if (dnp->dn_alternate_body == NULL) {
4779			(void) fprintf(fp, "%*s}\n", depth * 8, "");
4780		} else {
4781			(void) fprintf(fp, "%*s} else {\n", depth * 8, "");
4782			for (arg = dnp->dn_alternate_body; arg != NULL;
4783			    arg = arg->dn_list)
4784				dt_printd(arg, fp, depth + 1);
4785			(void) fprintf(fp, "%*s}\n", depth * 8, "");
4786		}
4787
4788		break;
4789
4790	default:
4791		(void) fprintf(fp, "/* bad node %p, kind %d */\n",
4792		    (void *)dnp, dnp->dn_kind);
4793	}
4794}
4795
4796void
4797dt_node_printr(dt_node_t *dnp, FILE *fp, int depth)
4798{
4799	char n[DT_TYPE_NAMELEN], buf[BUFSIZ], a[8];
4800	const dtrace_syminfo_t *dts;
4801	const dt_idnode_t *inp;
4802	dt_node_t *arg;
4803
4804	(void) fprintf(fp, "%*s", depth * 2, "");
4805	(void) dt_attr_str(dnp->dn_attr, a, sizeof (a));
4806
4807	if (dnp->dn_ctfp != NULL && dnp->dn_type != CTF_ERR &&
4808	    ctf_type_name(dnp->dn_ctfp, dnp->dn_type, n, sizeof (n)) != NULL) {
4809		(void) snprintf(buf, BUFSIZ, "type=<%s> attr=%s flags=", n, a);
4810	} else {
4811		(void) snprintf(buf, BUFSIZ, "type=<%ld> attr=%s flags=",
4812		    dnp->dn_type, a);
4813	}
4814
4815	if (dnp->dn_flags != 0) {
4816		n[0] = '\0';
4817		if (dnp->dn_flags & DT_NF_SIGNED)
4818			(void) strcat(n, ",SIGN");
4819		if (dnp->dn_flags & DT_NF_COOKED)
4820			(void) strcat(n, ",COOK");
4821		if (dnp->dn_flags & DT_NF_REF)
4822			(void) strcat(n, ",REF");
4823		if (dnp->dn_flags & DT_NF_LVALUE)
4824			(void) strcat(n, ",LVAL");
4825		if (dnp->dn_flags & DT_NF_WRITABLE)
4826			(void) strcat(n, ",WRITE");
4827		if (dnp->dn_flags & DT_NF_BITFIELD)
4828			(void) strcat(n, ",BITF");
4829		if (dnp->dn_flags & DT_NF_USERLAND)
4830			(void) strcat(n, ",USER");
4831		(void) strcat(buf, n + 1);
4832	} else
4833		(void) strcat(buf, "0");
4834
4835	switch (dnp->dn_kind) {
4836	case DT_NODE_FREE:
4837		(void) fprintf(fp, "FREE <node %p>\n", (void *)dnp);
4838		break;
4839
4840	case DT_NODE_INT:
4841		(void) fprintf(fp, "INT 0x%llx (%s)\n",
4842		    (u_longlong_t)dnp->dn_value, buf);
4843		break;
4844
4845	case DT_NODE_STRING:
4846		(void) fprintf(fp, "STRING \"%s\" (%s)\n", dnp->dn_string, buf);
4847		break;
4848
4849	case DT_NODE_IDENT:
4850		(void) fprintf(fp, "IDENT %s (%s)\n", dnp->dn_string, buf);
4851		break;
4852
4853	case DT_NODE_VAR:
4854		(void) fprintf(fp, "VARIABLE %s%s (%s)\n",
4855		    (dnp->dn_ident->di_flags & DT_IDFLG_LOCAL) ? "this->" :
4856		    (dnp->dn_ident->di_flags & DT_IDFLG_TLS) ? "self->" : "",
4857		    dnp->dn_ident->di_name, buf);
4858
4859		if (dnp->dn_args != NULL)
4860			(void) fprintf(fp, "%*s[\n", depth * 2, "");
4861
4862		for (arg = dnp->dn_args; arg != NULL; arg = arg->dn_list) {
4863			dt_node_printr(arg, fp, depth + 1);
4864			if (arg->dn_list != NULL)
4865				(void) fprintf(fp, "%*s,\n", depth * 2, "");
4866		}
4867
4868		if (dnp->dn_args != NULL)
4869			(void) fprintf(fp, "%*s]\n", depth * 2, "");
4870		break;
4871
4872	case DT_NODE_SYM:
4873		dts = dnp->dn_ident->di_data;
4874		(void) fprintf(fp, "SYMBOL %s`%s (%s)\n",
4875		    dts->dts_object, dts->dts_name, buf);
4876		break;
4877
4878	case DT_NODE_TYPE:
4879		if (dnp->dn_string != NULL) {
4880			(void) fprintf(fp, "TYPE (%s) %s\n",
4881			    buf, dnp->dn_string);
4882		} else
4883			(void) fprintf(fp, "TYPE (%s)\n", buf);
4884		break;
4885
4886	case DT_NODE_FUNC:
4887		(void) fprintf(fp, "FUNC %s (%s)\n",
4888		    dnp->dn_ident->di_name, buf);
4889
4890		for (arg = dnp->dn_args; arg != NULL; arg = arg->dn_list) {
4891			dt_node_printr(arg, fp, depth + 1);
4892			if (arg->dn_list != NULL)
4893				(void) fprintf(fp, "%*s,\n", depth * 2, "");
4894		}
4895		break;
4896
4897	case DT_NODE_OP1:
4898		(void) fprintf(fp, "OP1 %s (%s)\n", opstr(dnp->dn_op), buf);
4899		dt_node_printr(dnp->dn_child, fp, depth + 1);
4900		break;
4901
4902	case DT_NODE_OP2:
4903		(void) fprintf(fp, "OP2 %s (%s)\n", opstr(dnp->dn_op), buf);
4904		dt_node_printr(dnp->dn_left, fp, depth + 1);
4905		dt_node_printr(dnp->dn_right, fp, depth + 1);
4906		if (dnp->dn_op == DT_TOK_LBRAC) {
4907			dt_node_t *ln = dnp->dn_right;
4908			while (ln->dn_list != NULL) {
4909				dt_node_printr(ln->dn_list, fp, depth + 1);
4910				ln = ln->dn_list;
4911			}
4912		}
4913		break;
4914
4915	case DT_NODE_OP3:
4916		(void) fprintf(fp, "OP3 (%s)\n", buf);
4917		dt_node_printr(dnp->dn_expr, fp, depth + 1);
4918		(void) fprintf(fp, "%*s?\n", depth * 2, "");
4919		dt_node_printr(dnp->dn_left, fp, depth + 1);
4920		(void) fprintf(fp, "%*s:\n", depth * 2, "");
4921		dt_node_printr(dnp->dn_right, fp, depth + 1);
4922		break;
4923
4924	case DT_NODE_DEXPR:
4925	case DT_NODE_DFUNC:
4926		(void) fprintf(fp, "D EXPRESSION attr=%s\n", a);
4927		dt_node_printr(dnp->dn_expr, fp, depth + 1);
4928		break;
4929
4930	case DT_NODE_AGG:
4931		(void) fprintf(fp, "AGGREGATE @%s attr=%s [\n",
4932		    dnp->dn_ident->di_name, a);
4933
4934		for (arg = dnp->dn_aggtup; arg != NULL; arg = arg->dn_list) {
4935			dt_node_printr(arg, fp, depth + 1);
4936			if (arg->dn_list != NULL)
4937				(void) fprintf(fp, "%*s,\n", depth * 2, "");
4938		}
4939
4940		if (dnp->dn_aggfun) {
4941			(void) fprintf(fp, "%*s] = ", depth * 2, "");
4942			dt_node_printr(dnp->dn_aggfun, fp, depth + 1);
4943		} else
4944			(void) fprintf(fp, "%*s]\n", depth * 2, "");
4945
4946		if (dnp->dn_aggfun)
4947			(void) fprintf(fp, "%*s)\n", depth * 2, "");
4948		break;
4949
4950	case DT_NODE_PDESC:
4951		(void) fprintf(fp, "PDESC %s:%s:%s:%s [%u]\n",
4952		    dnp->dn_desc->dtpd_provider, dnp->dn_desc->dtpd_mod,
4953		    dnp->dn_desc->dtpd_func, dnp->dn_desc->dtpd_name,
4954		    dnp->dn_desc->dtpd_id);
4955		break;
4956
4957	case DT_NODE_CLAUSE:
4958		(void) fprintf(fp, "CLAUSE attr=%s\n", a);
4959
4960		for (arg = dnp->dn_pdescs; arg != NULL; arg = arg->dn_list)
4961			dt_node_printr(arg, fp, depth + 1);
4962
4963		(void) fprintf(fp, "%*sCTXATTR %s\n", depth * 2, "",
4964		    dt_attr_str(dnp->dn_ctxattr, a, sizeof (a)));
4965
4966		if (dnp->dn_pred != NULL) {
4967			(void) fprintf(fp, "%*sPREDICATE /\n", depth * 2, "");
4968			dt_node_printr(dnp->dn_pred, fp, depth + 1);
4969			(void) fprintf(fp, "%*s/\n", depth * 2, "");
4970		}
4971
4972		for (arg = dnp->dn_acts; arg != NULL; arg = arg->dn_list)
4973			dt_node_printr(arg, fp, depth + 1);
4974		(void) fprintf(fp, "\n");
4975		break;
4976
4977	case DT_NODE_INLINE:
4978		inp = dnp->dn_ident->di_iarg;
4979
4980		(void) fprintf(fp, "INLINE %s (%s)\n",
4981		    dnp->dn_ident->di_name, buf);
4982		dt_node_printr(inp->din_root, fp, depth + 1);
4983		break;
4984
4985	case DT_NODE_MEMBER:
4986		(void) fprintf(fp, "MEMBER %s (%s)\n", dnp->dn_membname, buf);
4987		if (dnp->dn_membexpr)
4988			dt_node_printr(dnp->dn_membexpr, fp, depth + 1);
4989		break;
4990
4991	case DT_NODE_XLATOR:
4992		(void) fprintf(fp, "XLATOR (%s)", buf);
4993
4994		if (ctf_type_name(dnp->dn_xlator->dx_src_ctfp,
4995		    dnp->dn_xlator->dx_src_type, n, sizeof (n)) != NULL)
4996			(void) fprintf(fp, " from <%s>", n);
4997
4998		if (ctf_type_name(dnp->dn_xlator->dx_dst_ctfp,
4999		    dnp->dn_xlator->dx_dst_type, n, sizeof (n)) != NULL)
5000			(void) fprintf(fp, " to <%s>", n);
5001
5002		(void) fprintf(fp, "\n");
5003
5004		for (arg = dnp->dn_members; arg != NULL; arg = arg->dn_list)
5005			dt_node_printr(arg, fp, depth + 1);
5006		break;
5007
5008	case DT_NODE_PROBE:
5009		(void) fprintf(fp, "PROBE %s\n", dnp->dn_ident->di_name);
5010		break;
5011
5012	case DT_NODE_PROVIDER:
5013		(void) fprintf(fp, "PROVIDER %s (%s)\n",
5014		    dnp->dn_provname, dnp->dn_provred ? "redecl" : "decl");
5015		for (arg = dnp->dn_probes; arg != NULL; arg = arg->dn_list)
5016			dt_node_printr(arg, fp, depth + 1);
5017		break;
5018
5019	case DT_NODE_PROG:
5020		(void) fprintf(fp, "PROGRAM attr=%s\n", a);
5021		for (arg = dnp->dn_list; arg != NULL; arg = arg->dn_list)
5022			dt_node_printr(arg, fp, depth + 1);
5023		break;
5024
5025	case DT_NODE_IF:
5026		(void) fprintf(fp, "IF attr=%s CONDITION:\n", a);
5027
5028		dt_node_printr(dnp->dn_conditional, fp, depth + 1);
5029
5030		(void) fprintf(fp, "%*sIF BODY: \n", depth * 2, "");
5031		for (arg = dnp->dn_body; arg != NULL; arg = arg->dn_list)
5032			dt_node_printr(arg, fp, depth + 1);
5033
5034		if (dnp->dn_alternate_body != NULL) {
5035			(void) fprintf(fp, "%*sIF ELSE: \n", depth * 2, "");
5036			for (arg = dnp->dn_alternate_body; arg != NULL;
5037			    arg = arg->dn_list)
5038				dt_node_printr(arg, fp, depth + 1);
5039		}
5040
5041		break;
5042
5043	default:
5044		(void) fprintf(fp, "<bad node %p, kind %d>\n",
5045		    (void *)dnp, dnp->dn_kind);
5046	}
5047}
5048
5049int
5050dt_node_root(dt_node_t *dnp)
5051{
5052	yypcb->pcb_root = dnp;
5053	return (0);
5054}
5055
5056/*PRINTFLIKE3*/
5057void
5058dnerror(const dt_node_t *dnp, dt_errtag_t tag, const char *format, ...)
5059{
5060	int oldlineno = yylineno;
5061	va_list ap;
5062
5063	yylineno = dnp->dn_line;
5064
5065	va_start(ap, format);
5066	xyvwarn(tag, format, ap);
5067	va_end(ap);
5068
5069	yylineno = oldlineno;
5070	longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
5071}
5072
5073/*PRINTFLIKE3*/
5074void
5075dnwarn(const dt_node_t *dnp, dt_errtag_t tag, const char *format, ...)
5076{
5077	int oldlineno = yylineno;
5078	va_list ap;
5079
5080	yylineno = dnp->dn_line;
5081
5082	va_start(ap, format);
5083	xyvwarn(tag, format, ap);
5084	va_end(ap);
5085
5086	yylineno = oldlineno;
5087}
5088
5089/*PRINTFLIKE2*/
5090void
5091xyerror(dt_errtag_t tag, const char *format, ...)
5092{
5093	va_list ap;
5094
5095	va_start(ap, format);
5096	xyvwarn(tag, format, ap);
5097	va_end(ap);
5098
5099	longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
5100}
5101
5102/*PRINTFLIKE2*/
5103void
5104xywarn(dt_errtag_t tag, const char *format, ...)
5105{
5106	va_list ap;
5107
5108	va_start(ap, format);
5109	xyvwarn(tag, format, ap);
5110	va_end(ap);
5111}
5112
5113void
5114xyvwarn(dt_errtag_t tag, const char *format, va_list ap)
5115{
5116	if (yypcb == NULL)
5117		return; /* compiler is not currently active: act as a no-op */
5118
5119	dt_set_errmsg(yypcb->pcb_hdl, dt_errtag(tag), yypcb->pcb_region,
5120	    yypcb->pcb_filetag, yypcb->pcb_fileptr ? yylineno : 0, format, ap);
5121}
5122
5123/*PRINTFLIKE1*/
5124void
5125yyerror(const char *format, ...)
5126{
5127	va_list ap;
5128
5129	va_start(ap, format);
5130	yyvwarn(format, ap);
5131	va_end(ap);
5132
5133	longjmp(yypcb->pcb_jmpbuf, EDT_COMPILER);
5134}
5135
5136/*PRINTFLIKE1*/
5137void
5138yywarn(const char *format, ...)
5139{
5140	va_list ap;
5141
5142	va_start(ap, format);
5143	yyvwarn(format, ap);
5144	va_end(ap);
5145}
5146
5147void
5148yyvwarn(const char *format, va_list ap)
5149{
5150	if (yypcb == NULL)
5151		return; /* compiler is not currently active: act as a no-op */
5152
5153	dt_set_errmsg(yypcb->pcb_hdl, dt_errtag(D_SYNTAX), yypcb->pcb_region,
5154	    yypcb->pcb_filetag, yypcb->pcb_fileptr ? yylineno : 0, format, ap);
5155
5156	if (strchr(format, '\n') == NULL) {
5157		dtrace_hdl_t *dtp = yypcb->pcb_hdl;
5158		size_t len = strlen(dtp->dt_errmsg);
5159		char *p, *s = dtp->dt_errmsg + len;
5160		size_t n = sizeof (dtp->dt_errmsg) - len;
5161
5162		if (yytext[0] == '\0')
5163			(void) snprintf(s, n, " near end of input");
5164		else if (yytext[0] == '\n')
5165			(void) snprintf(s, n, " near end of line");
5166		else {
5167			if ((p = strchr(yytext, '\n')) != NULL)
5168				*p = '\0'; /* crop at newline */
5169			(void) snprintf(s, n, " near \"%s\"", yytext);
5170		}
5171	}
5172}
5173
5174void
5175yylabel(const char *label)
5176{
5177	dt_dprintf("set label to <%s>\n", label ? label : "NULL");
5178	yypcb->pcb_region = label;
5179}
5180
5181int
5182yywrap(void)
5183{
5184	return (1); /* indicate that lex should return a zero token for EOF */
5185}
5186