ctf_create.c revision 1.8 1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
7 * with the License.
8 *
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
13 *
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
19 *
20 * CDDL HEADER END
21 */
22 #ifdef HAVE_NBTOOL_CONFIG_H
23 #include "nbtool_config.h"
24 #endif
25
26 /*
27 * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
28 * Use is subject to license terms.
29 */
30 /*
31 * Copyright (c) 2013, Joyent, Inc. All rights reserved.
32 */
33
34 #include <sys/sysmacros.h>
35 #include <sys/param.h>
36 #include <sys/mman.h>
37 #include <ctf_impl.h>
38 #include <sys/debug.h>
39
40 /*
41 * This static string is used as the template for initially populating a
42 * dynamic container's string table. We always store \0 in the first byte,
43 * and we use the generic string "PARENT" to mark this container's parent
44 * if one is associated with the container using ctf_import().
45 */
46 static const char _CTF_STRTAB_TEMPLATE[] = "\0PARENT";
47
48 /*
49 * To create an empty CTF container, we just declare a zeroed header and call
50 * ctf_bufopen() on it. If ctf_bufopen succeeds, we mark the new container r/w
51 * and initialize the dynamic members. We set dtstrlen to 1 to reserve the
52 * first byte of the string table for a \0 byte, and we start assigning type
53 * IDs at 1 because type ID 0 is used as a sentinel.
54 */
55 ctf_file_t *
56 ctf_create(int *errp)
57 {
58 static const ctf_header_t hdr = { .cth_preamble = {
59 .ctp_magic = CTF_MAGIC,
60 .ctp_version = CTF_VERSION,
61 .ctp_flags = 0
62 } };
63
64 const ulong_t hashlen = 128;
65 ctf_dtdef_t **hash = ctf_alloc(hashlen * sizeof (ctf_dtdef_t *));
66 ctf_sect_t cts;
67 ctf_file_t *fp;
68
69 if (hash == NULL)
70 return (ctf_set_open_errno(errp, EAGAIN));
71
72 cts.cts_name = __UNCONST(_CTF_SECTION);
73 cts.cts_type = SHT_PROGBITS;
74 cts.cts_flags = 0;
75 cts.cts_data = __UNCONST(&hdr);
76 cts.cts_size = sizeof (hdr);
77 cts.cts_entsize = 1;
78 cts.cts_offset = 0;
79
80 if ((fp = ctf_bufopen(&cts, NULL, NULL, errp)) == NULL) {
81 ctf_free(hash, hashlen * sizeof (ctf_dtdef_t *));
82 return (NULL);
83 }
84
85 fp->ctf_flags |= LCTF_RDWR;
86 fp->ctf_dthashlen = hashlen;
87 memset(hash, 0, hashlen * sizeof (ctf_dtdef_t *));
88 fp->ctf_dthash = hash;
89 fp->ctf_dtstrlen = sizeof (_CTF_STRTAB_TEMPLATE);
90 fp->ctf_dtnextid = 1;
91 fp->ctf_dtoldid = 0;
92
93 return (fp);
94 }
95
96 static uchar_t *
97 ctf_copy_smembers(const ctf_file_t *fp, ctf_dtdef_t *dtd, uint_t soff,
98 uchar_t *t)
99 {
100 ctf_dmdef_t *dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
101 size_t sz;
102 uint_t name;
103
104 for (; dmd != NULL; dmd = ctf_list_next(dmd)) {
105 if (dmd->dmd_name) {
106 name = soff;
107 soff += strlen(dmd->dmd_name) + 1;
108 } else
109 name = 0;
110
111 if (fp->ctf_version == CTF_VERSION_2) {
112 struct ctf_member_v2 ctm;
113
114 ctm.ctm_name = name;
115 ctm.ctm_type = (ushort_t)dmd->dmd_type;
116 ctm.ctm_offset = (ushort_t)dmd->dmd_offset;
117
118 sz = sizeof (ctm);
119 memcpy(t, &ctm, sz);
120 t += sz;
121 } else {
122 struct ctf_member_v3 ctm;
123
124 ctm.ctm_name = name;
125 ctm.ctm_type = dmd->dmd_type;
126 ctm.ctm_offset = dmd->dmd_offset;
127
128 sz = sizeof (ctm);
129 memcpy(t, &ctm, sz);
130 t += sz;
131 }
132 }
133
134 return (t);
135 }
136
137 static uchar_t *
138 ctf_copy_lmembers(const ctf_file_t *fp, ctf_dtdef_t *dtd, uint_t soff,
139 uchar_t *t)
140 {
141 ctf_dmdef_t *dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
142 size_t sz;
143 uint_t name;
144
145 for (; dmd != NULL; dmd = ctf_list_next(dmd)) {
146 if (dmd->dmd_name) {
147 name = soff;
148 soff += strlen(dmd->dmd_name) + 1;
149 } else
150 name = 0;
151
152 if (fp->ctf_version == CTF_VERSION_2) {
153 struct ctf_lmember_v2 ctlm;
154
155 ctlm.ctlm_name = name;
156 ctlm.ctlm_type = (ushort_t)dmd->dmd_type;
157 ctlm.ctlm_pad = 0;
158 ctlm.ctlm_offsethi = CTF_OFFSET_TO_LMEMHI(dmd->dmd_offset);
159 ctlm.ctlm_offsetlo = CTF_OFFSET_TO_LMEMLO(dmd->dmd_offset);
160
161 sz = sizeof (ctlm);
162 memcpy(t, &ctlm, sz);
163 t += sz;
164 } else {
165 struct ctf_lmember_v3 ctlm;
166
167 ctlm.ctlm_name = name;
168 ctlm.ctlm_type = dmd->dmd_type;
169 ctlm.ctlm_offsethi = CTF_OFFSET_TO_LMEMHI(dmd->dmd_offset);
170 ctlm.ctlm_offsetlo = CTF_OFFSET_TO_LMEMLO(dmd->dmd_offset);
171
172 sz = sizeof (ctlm);
173 memcpy(t, &ctlm, sz);
174 t += sz;
175 }
176
177 }
178
179 return (t);
180 }
181
182 static uchar_t *
183 ctf_copy_emembers(ctf_dtdef_t *dtd, uint_t soff, uchar_t *t)
184 {
185 ctf_dmdef_t *dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
186 ctf_enum_t cte;
187
188 for (; dmd != NULL; dmd = ctf_list_next(dmd)) {
189 cte.cte_name = soff;
190 cte.cte_value = dmd->dmd_value;
191 soff += strlen(dmd->dmd_name) + 1;
192 memcpy(t, &cte, sizeof (cte));
193 t += sizeof (cte);
194 }
195
196 return (t);
197 }
198
199 static uchar_t *
200 ctf_copy_membnames(ctf_dtdef_t *dtd, uchar_t *s)
201 {
202 ctf_dmdef_t *dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
203 size_t len;
204
205 for (; dmd != NULL; dmd = ctf_list_next(dmd)) {
206 if (dmd->dmd_name == NULL)
207 continue; /* skip anonymous members */
208 len = strlen(dmd->dmd_name) + 1;
209 memcpy(s, dmd->dmd_name, len);
210 s += len;
211 }
212
213 return (s);
214 }
215
216 /*
217 * Only types of dyanmic CTF containers contain reference counts. These
218 * containers are marked RD/WR. Because of that we basically make this a no-op
219 * for compatability with non-dynamic CTF sections. This is also a no-op for
220 * types which are not dynamic types. It is the responsibility of the caller to
221 * make sure it is a valid type. We help that caller out on debug builds.
222 *
223 * Note that the reference counts are not maintained for types that are not
224 * within this container. In other words if we have a type in a parent, that
225 * will not have its reference count increased. On the flip side, the parent
226 * will not be allowed to remove dynamic types if it has children.
227 */
228 static void
229 ctf_ref_inc(ctf_file_t *fp, ctf_id_t tid)
230 {
231 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, tid);
232
233 if (dtd == NULL)
234 return;
235
236 if (!(fp->ctf_flags & LCTF_RDWR))
237 return;
238
239 dtd->dtd_ref++;
240 }
241
242 /*
243 * Just as with ctf_ref_inc, this is a no-op on non-writeable containers and the
244 * caller should ensure that this is already a valid type.
245 */
246 static void
247 ctf_ref_dec(ctf_file_t *fp, ctf_id_t tid)
248 {
249 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, tid);
250
251 if (dtd == NULL)
252 return;
253
254 if (!(fp->ctf_flags & LCTF_RDWR))
255 return;
256
257 ASSERT(dtd->dtd_ref >= 1);
258 dtd->dtd_ref--;
259 }
260
261 /*
262 * If the specified CTF container is writable and has been modified, reload
263 * this container with the updated type definitions. In order to make this
264 * code and the rest of libctf as simple as possible, we perform updates by
265 * taking the dynamic type definitions and creating an in-memory CTF file
266 * containing the definitions, and then call ctf_bufopen() on it. This not
267 * only leverages ctf_bufopen(), but also avoids having to bifurcate the rest
268 * of the library code with different lookup paths for static and dynamic
269 * type definitions. We are therefore optimizing greatly for lookup over
270 * update, which we assume will be an uncommon operation. We perform one
271 * extra trick here for the benefit of callers and to keep our code simple:
272 * ctf_bufopen() will return a new ctf_file_t, but we want to keep the fp
273 * constant for the caller, so after ctf_bufopen() returns, we use memcpy to
274 * swap the interior of the old and new ctf_file_t's, and then free the old.
275 *
276 * Note that the lists of dynamic types stays around and the resulting container
277 * is still writeable. Furthermore, the reference counts that are on the dtd's
278 * are still valid.
279 */
280 int
281 ctf_update(ctf_file_t *fp)
282 {
283 ctf_file_t ofp, *nfp;
284 ctf_header_t hdr;
285 ctf_dtdef_t *dtd;
286 ctf_sect_t cts;
287
288 uchar_t *s, *s0, *t;
289 size_t size;
290 void *buf;
291 int err;
292
293 if (!(fp->ctf_flags & LCTF_RDWR))
294 return (ctf_set_errno(fp, ECTF_RDONLY));
295
296 if (!(fp->ctf_flags & LCTF_DIRTY))
297 return (0); /* no update required */
298
299 /*
300 * Fill in an initial CTF header. We will leave the label, object,
301 * and function sections empty and only output a header, type section,
302 * and string table. The type section begins at a 4-byte aligned
303 * boundary past the CTF header itself (at relative offset zero).
304 */
305 memset(&hdr, 0, sizeof (hdr));
306 hdr.cth_magic = CTF_MAGIC;
307 hdr.cth_version = fp->ctf_version;
308
309 if (fp->ctf_flags & LCTF_CHILD)
310 hdr.cth_parname = 1; /* i.e. _CTF_STRTAB_TEMPLATE[1] */
311
312 /*
313 * Iterate through the dynamic type definition list and compute the
314 * size of the CTF type section we will need to generate.
315 */
316 for (size = 0, dtd = ctf_list_next(&fp->ctf_dtdefs);
317 dtd != NULL; dtd = ctf_list_next(dtd)) {
318
319 uint_t kind = LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info);
320 uint_t vlen = LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info);
321
322 if (fp->ctf_version == CTF_VERSION_2) {
323 if (dtd->dtd_data.ctt_size != CTF_V2_LSIZE_SENT)
324 size += sizeof (struct ctf_stype_v2);
325 else
326 size += sizeof (struct ctf_type_v2);
327 } else {
328 if (dtd->dtd_data.ctt_size != LCTF_LSIZE_SENT(fp))
329 size += sizeof (struct ctf_stype_v3);
330 else
331 size += sizeof (struct ctf_type_v3);
332 }
333
334 switch (kind) {
335 case CTF_K_INTEGER:
336 case CTF_K_FLOAT:
337 size += sizeof (uint_t);
338 break;
339 case CTF_K_ARRAY:
340 size += fp->ctf_version == CTF_VERSION_2 ?
341 sizeof (struct ctf_array_v2) :
342 sizeof (struct ctf_array_v3);
343 break;
344 case CTF_K_FUNCTION:
345 size += roundup2(fp->ctf_idwidth * vlen, 4);
346 break;
347 case CTF_K_STRUCT:
348 case CTF_K_UNION:
349 if (fp->ctf_version == CTF_VERSION_2) {
350 if (dtd->dtd_data.ctt_size <
351 LCTF_LSTRUCT_THRESH(fp))
352 size += sizeof (struct ctf_member_v2) *
353 vlen;
354 else
355 size += sizeof (struct ctf_lmember_v2) *
356 vlen;
357 } else {
358 if (dtd->dtd_data.ctt_size <
359 LCTF_LSTRUCT_THRESH(fp))
360 size += sizeof (struct ctf_member_v3) *
361 vlen;
362 else
363 size += sizeof (struct ctf_lmember_v3) *
364 vlen;
365 }
366 break;
367 case CTF_K_ENUM:
368 size += sizeof (ctf_enum_t) * vlen;
369 break;
370 }
371 }
372
373 /*
374 * Fill in the string table offset and size, compute the size of the
375 * entire CTF buffer we need, and then allocate a new buffer and
376 * memcpy the finished header to the start of the buffer.
377 */
378 hdr.cth_stroff = hdr.cth_typeoff + size;
379 hdr.cth_strlen = fp->ctf_dtstrlen;
380 size = sizeof (ctf_header_t) + hdr.cth_stroff + hdr.cth_strlen;
381
382 if ((buf = ctf_data_alloc(size)) == MAP_FAILED)
383 return (ctf_set_errno(fp, EAGAIN));
384
385 memcpy(buf, &hdr, sizeof (ctf_header_t));
386 t = (uchar_t *)buf + sizeof (ctf_header_t);
387 s = s0 = (uchar_t *)buf + sizeof (ctf_header_t) + hdr.cth_stroff;
388
389 memcpy(s, _CTF_STRTAB_TEMPLATE, sizeof (_CTF_STRTAB_TEMPLATE));
390 s += sizeof (_CTF_STRTAB_TEMPLATE);
391
392 /*
393 * We now take a final lap through the dynamic type definition list and
394 * copy the appropriate type records and strings to the output buffer.
395 */
396 for (dtd = ctf_list_next(&fp->ctf_dtdefs);
397 dtd != NULL; dtd = ctf_list_next(dtd)) {
398 void *tp;
399 uint_t kind = LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info);
400 uint_t vlen = LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info);
401 struct ctf_type_v2 ctt;
402
403 uint_t encoding;
404 size_t len;
405
406 if (dtd->dtd_name != NULL) {
407 dtd->dtd_data.ctt_name = (uint_t)(s - s0);
408 len = strlen(dtd->dtd_name) + 1;
409 memcpy(s, dtd->dtd_name, len);
410 s += len;
411 } else
412 dtd->dtd_data.ctt_name = 0;
413
414 if (fp->ctf_version == CTF_VERSION_2) {
415 ctt.ctt_name = dtd->dtd_data.ctt_name;
416 ctt.ctt_info = (ushort_t)dtd->dtd_data.ctt_info;
417 ctt.ctt_size = (ushort_t)dtd->dtd_data.ctt_size;
418 if (dtd->dtd_data.ctt_size != CTF_V2_LSIZE_SENT)
419 len = sizeof (struct ctf_stype_v2);
420 else {
421 len = sizeof (struct ctf_type_v2);
422 ctt.ctt_lsizehi = dtd->dtd_data.ctt_lsizehi;
423 ctt.ctt_lsizelo = dtd->dtd_data.ctt_lsizelo;
424 }
425 tp = &ctt;
426 } else {
427 if (dtd->dtd_data.ctt_size != LCTF_LSIZE_SENT(fp))
428 len = sizeof (struct ctf_stype_v3);
429 else
430 len = sizeof (struct ctf_type_v3);
431 tp = &dtd->dtd_data;
432 }
433
434 memcpy(t, tp, len);
435 t += len;
436
437 switch (kind) {
438 case CTF_K_INTEGER:
439 case CTF_K_FLOAT:
440 if (kind == CTF_K_INTEGER) {
441 encoding = CTF_INT_DATA(
442 dtd->dtd_u.dtu_enc.cte_format,
443 dtd->dtd_u.dtu_enc.cte_offset,
444 dtd->dtd_u.dtu_enc.cte_bits);
445 } else {
446 encoding = CTF_FP_DATA(
447 dtd->dtd_u.dtu_enc.cte_format,
448 dtd->dtd_u.dtu_enc.cte_offset,
449 dtd->dtd_u.dtu_enc.cte_bits);
450 }
451 memcpy(t, &encoding, sizeof (encoding));
452 t += sizeof (encoding);
453 break;
454
455 case CTF_K_ARRAY:
456 if (fp->ctf_version == CTF_VERSION_2) {
457 struct ctf_array_v2 cta;
458
459 cta.cta_contents =
460 (uint16_t)dtd->dtd_u.dtu_arr.ctr_contents;
461 cta.cta_index =
462 (uint16_t)dtd->dtd_u.dtu_arr.ctr_index;
463 cta.cta_nelems = dtd->dtd_u.dtu_arr.ctr_nelems;
464
465 memcpy(t, &cta, sizeof (cta));
466 t += sizeof (cta);
467 } else {
468 struct ctf_array_v3 cta;
469
470 cta.cta_contents =
471 dtd->dtd_u.dtu_arr.ctr_contents;
472 cta.cta_index = dtd->dtd_u.dtu_arr.ctr_index;
473 cta.cta_nelems = dtd->dtd_u.dtu_arr.ctr_nelems;
474
475 memcpy(t, &cta, sizeof (cta));
476 t += sizeof (cta);
477 }
478 break;
479
480 case CTF_K_FUNCTION: {
481 char *argv = (char *)(uintptr_t)t;
482 uint_t argc;
483
484 if (fp->ctf_version == CTF_VERSION_2) {
485 ushort_t arg;
486
487 for (argc = 0; argc < vlen;
488 argc++, argv += sizeof(arg)) {
489 arg =
490 (ushort_t)dtd->dtd_u.dtu_argv[argc];
491 memcpy(argv, &arg, sizeof(arg));
492 }
493 } else {
494 uint_t arg;
495
496 for (argc = 0; argc < vlen;
497 argc++, argv += sizeof(arg)) {
498 arg = (uint_t)dtd->dtd_u.dtu_argv[argc];
499 memcpy(argv, &arg, sizeof(arg));
500 }
501 }
502
503 t = (uchar_t *)argv;
504 break;
505 }
506
507 case CTF_K_STRUCT:
508 case CTF_K_UNION:
509 if (dtd->dtd_data.ctt_size < LCTF_LSTRUCT_THRESH(fp))
510 t = ctf_copy_smembers(fp, dtd, (uint_t)(s - s0),
511 t);
512 else
513 t = ctf_copy_lmembers(fp, dtd, (uint_t)(s - s0),
514 t);
515 s = ctf_copy_membnames(dtd, s);
516 break;
517
518 case CTF_K_ENUM:
519 t = ctf_copy_emembers(dtd, (uint_t)(s - s0), t);
520 s = ctf_copy_membnames(dtd, s);
521 break;
522 }
523 }
524
525 /*
526 * Finally, we are ready to ctf_bufopen() the new container. If this
527 * is successful, we then switch nfp and fp and free the old container.
528 */
529 ctf_data_protect(buf, size);
530 cts.cts_name = _CTF_SECTION;
531 cts.cts_type = SHT_PROGBITS;
532 cts.cts_flags = 0;
533 cts.cts_data = buf;
534 cts.cts_size = size;
535 cts.cts_entsize = 1;
536 cts.cts_offset = 0;
537
538 if ((nfp = ctf_bufopen(&cts, NULL, NULL, &err)) == NULL) {
539 ctf_data_free(buf, size);
540 return (ctf_set_errno(fp, err));
541 }
542
543 (void) ctf_setmodel(nfp, ctf_getmodel(fp));
544 (void) ctf_import(nfp, fp->ctf_parent);
545
546 nfp->ctf_refcnt = fp->ctf_refcnt;
547 nfp->ctf_flags |= fp->ctf_flags & ~LCTF_DIRTY;
548 nfp->ctf_data.cts_data = NULL; /* force ctf_data_free() on close */
549 nfp->ctf_dthash = fp->ctf_dthash;
550 nfp->ctf_dthashlen = fp->ctf_dthashlen;
551 nfp->ctf_dtdefs = fp->ctf_dtdefs;
552 nfp->ctf_dtstrlen = fp->ctf_dtstrlen;
553 nfp->ctf_dtnextid = fp->ctf_dtnextid;
554 nfp->ctf_dtoldid = fp->ctf_dtnextid - 1;
555 nfp->ctf_specific = fp->ctf_specific;
556
557 fp->ctf_dthash = NULL;
558 fp->ctf_dthashlen = 0;
559 memset(&fp->ctf_dtdefs, 0, sizeof (ctf_list_t));
560
561 memcpy(&ofp, fp, sizeof (ctf_file_t));
562 memcpy(fp, nfp, sizeof (ctf_file_t));
563 memcpy(nfp, &ofp, sizeof (ctf_file_t));
564
565 /*
566 * Initialize the ctf_lookup_by_name top-level dictionary. We keep an
567 * array of type name prefixes and the corresponding ctf_hash to use.
568 * NOTE: This code must be kept in sync with the code in ctf_bufopen().
569 */
570 fp->ctf_lookups[0].ctl_hash = &fp->ctf_structs;
571 fp->ctf_lookups[1].ctl_hash = &fp->ctf_unions;
572 fp->ctf_lookups[2].ctl_hash = &fp->ctf_enums;
573 fp->ctf_lookups[3].ctl_hash = &fp->ctf_names;
574
575 nfp->ctf_refcnt = 1; /* force nfp to be freed */
576 ctf_close(nfp);
577
578 return (0);
579 }
580
581 void
582 ctf_dtd_insert(ctf_file_t *fp, ctf_dtdef_t *dtd)
583 {
584 ulong_t h = dtd->dtd_type & (fp->ctf_dthashlen - 1);
585
586 dtd->dtd_hash = fp->ctf_dthash[h];
587 fp->ctf_dthash[h] = dtd;
588 ctf_list_append(&fp->ctf_dtdefs, dtd);
589 }
590
591 void
592 ctf_dtd_delete(ctf_file_t *fp, ctf_dtdef_t *dtd)
593 {
594 ulong_t h = dtd->dtd_type & (fp->ctf_dthashlen - 1);
595 ctf_dtdef_t *p, **q = &fp->ctf_dthash[h];
596 ctf_dmdef_t *dmd, *nmd;
597 size_t len;
598 int kind, i;
599
600 for (p = *q; p != NULL; p = p->dtd_hash) {
601 if (p != dtd)
602 q = &p->dtd_hash;
603 else
604 break;
605 }
606
607 if (p != NULL)
608 *q = p->dtd_hash;
609
610 kind = LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info);
611 switch (kind) {
612 case CTF_K_STRUCT:
613 case CTF_K_UNION:
614 case CTF_K_ENUM:
615 for (dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
616 dmd != NULL; dmd = nmd) {
617 if (dmd->dmd_name != NULL) {
618 len = strlen(dmd->dmd_name) + 1;
619 ctf_free(dmd->dmd_name, len);
620 fp->ctf_dtstrlen -= len;
621 }
622 if (kind != CTF_K_ENUM)
623 ctf_ref_dec(fp, dmd->dmd_type);
624 nmd = ctf_list_next(dmd);
625 ctf_free(dmd, sizeof (ctf_dmdef_t));
626 }
627 break;
628 case CTF_K_FUNCTION:
629 ctf_ref_dec(fp, dtd->dtd_data.ctt_type);
630 for (i = 0; i < LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info); i++)
631 if (dtd->dtd_u.dtu_argv[i] != 0)
632 ctf_ref_dec(fp, dtd->dtd_u.dtu_argv[i]);
633 ctf_free(dtd->dtd_u.dtu_argv, sizeof (ctf_id_t) *
634 LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info));
635 break;
636 case CTF_K_ARRAY:
637 ctf_ref_dec(fp, dtd->dtd_u.dtu_arr.ctr_contents);
638 ctf_ref_dec(fp, dtd->dtd_u.dtu_arr.ctr_index);
639 break;
640 case CTF_K_TYPEDEF:
641 ctf_ref_dec(fp, dtd->dtd_data.ctt_type);
642 break;
643 case CTF_K_POINTER:
644 case CTF_K_VOLATILE:
645 case CTF_K_CONST:
646 case CTF_K_RESTRICT:
647 ctf_ref_dec(fp, dtd->dtd_data.ctt_type);
648 break;
649 }
650
651 if (dtd->dtd_name) {
652 len = strlen(dtd->dtd_name) + 1;
653 ctf_free(dtd->dtd_name, len);
654 fp->ctf_dtstrlen -= len;
655 }
656
657 ctf_list_delete(&fp->ctf_dtdefs, dtd);
658 ctf_free(dtd, sizeof (ctf_dtdef_t));
659 }
660
661 ctf_dtdef_t *
662 ctf_dtd_lookup(ctf_file_t *fp, ctf_id_t type)
663 {
664 ulong_t h = type & (fp->ctf_dthashlen - 1);
665 ctf_dtdef_t *dtd;
666
667 if (fp->ctf_dthash == NULL)
668 return (NULL);
669
670 for (dtd = fp->ctf_dthash[h]; dtd != NULL; dtd = dtd->dtd_hash) {
671 if (dtd->dtd_type == type)
672 break;
673 }
674
675 return (dtd);
676 }
677
678 /*
679 * Discard all of the dynamic type definitions that have been added to the
680 * container since the last call to ctf_update(). We locate such types by
681 * scanning the list and deleting elements that have type IDs greater than
682 * ctf_dtoldid, which is set by ctf_update(), above. Note that to work properly
683 * with our reference counting schemes, we must delete the dynamic list in
684 * reverse.
685 */
686 int
687 ctf_discard(ctf_file_t *fp)
688 {
689 ctf_dtdef_t *dtd, *ntd;
690
691 if (!(fp->ctf_flags & LCTF_RDWR))
692 return (ctf_set_errno(fp, ECTF_RDONLY));
693
694 if (!(fp->ctf_flags & LCTF_DIRTY))
695 return (0); /* no update required */
696
697 for (dtd = ctf_list_prev(&fp->ctf_dtdefs); dtd != NULL; dtd = ntd) {
698 ntd = ctf_list_prev(dtd);
699 if (LCTF_TYPE_TO_INDEX(fp, dtd->dtd_type) <= fp->ctf_dtoldid)
700 continue; /* skip types that have been committed */
701
702 ctf_dtd_delete(fp, dtd);
703 }
704
705 fp->ctf_dtnextid = fp->ctf_dtoldid + 1;
706 fp->ctf_flags &= ~LCTF_DIRTY;
707
708 return (0);
709 }
710
711 static ctf_id_t
712 ctf_add_generic(ctf_file_t *fp, uint_t flag, const char *name, ctf_dtdef_t **rp)
713 {
714 ctf_dtdef_t *dtd;
715 ctf_id_t type;
716 char *s = NULL;
717
718 if (flag != CTF_ADD_NONROOT && flag != CTF_ADD_ROOT)
719 return (ctf_set_errno(fp, EINVAL));
720
721 if (!(fp->ctf_flags & LCTF_RDWR))
722 return (ctf_set_errno(fp, ECTF_RDONLY));
723
724 if (LCTF_INDEX_TO_TYPE(fp, fp->ctf_dtnextid, 1) > LCTF_MAX_TYPE(fp)) {
725 ctf_dprintf("type id overflow %lu\n", fp->ctf_dtnextid);
726 return (ctf_set_errno(fp, ECTF_FULL));
727 }
728
729 if ((dtd = ctf_alloc(sizeof (ctf_dtdef_t))) == NULL)
730 return (ctf_set_errno(fp, EAGAIN));
731
732 if (name != NULL && *name != '\0' && (s = ctf_strdup(name)) == NULL) {
733 ctf_free(dtd, sizeof (ctf_dtdef_t));
734 return (ctf_set_errno(fp, EAGAIN));
735 }
736
737 type = fp->ctf_dtnextid++;
738 type = LCTF_INDEX_TO_TYPE(fp, type, (fp->ctf_flags & LCTF_CHILD));
739
740 memset(dtd, 0, sizeof (ctf_dtdef_t));
741 dtd->dtd_name = s;
742 dtd->dtd_type = type;
743
744 if (s != NULL)
745 fp->ctf_dtstrlen += strlen(s) + 1;
746
747 ctf_dtd_insert(fp, dtd);
748 fp->ctf_flags |= LCTF_DIRTY;
749
750 *rp = dtd;
751 return (type);
752 }
753
754 /*
755 * When encoding integer sizes, we want to convert a byte count in the range
756 * 1-8 to the closest power of 2 (e.g. 3->4, 5->8, etc). The clp2() function
757 * is a clever implementation from "Hacker's Delight" by Henry Warren, Jr.
758 */
759 static size_t
760 clp2(size_t x)
761 {
762 x--;
763
764 x |= (x >> 1);
765 x |= (x >> 2);
766 x |= (x >> 4);
767 x |= (x >> 8);
768 x |= (x >> 16);
769
770 return (x + 1);
771 }
772
773 static ctf_id_t
774 ctf_add_encoded(ctf_file_t *fp, uint_t flag,
775 const char *name, const ctf_encoding_t *ep, uint_t kind)
776 {
777 ctf_dtdef_t *dtd;
778 ctf_id_t type;
779
780 if (ep == NULL)
781 return (ctf_set_errno(fp, EINVAL));
782
783 if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
784 return (CTF_ERR); /* errno is set for us */
785
786 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, kind, flag, 0);
787 dtd->dtd_data.ctt_size = clp2(P2ROUNDUP(ep->cte_bits, NBBY) / NBBY);
788 dtd->dtd_u.dtu_enc = *ep;
789
790 return (type);
791 }
792
793 static ctf_id_t
794 ctf_add_reftype(ctf_file_t *fp, uint_t flag, ctf_id_t ref, uint_t kind)
795 {
796 ctf_dtdef_t *dtd;
797 ctf_id_t type;
798
799 if (ref == CTF_ERR || ref < 0 || ref > LCTF_MAX_TYPE(fp))
800 return (ctf_set_errno(fp, EINVAL));
801
802 if ((type = ctf_add_generic(fp, flag, NULL, &dtd)) == CTF_ERR)
803 return (CTF_ERR); /* errno is set for us */
804
805 ctf_ref_inc(fp, ref);
806
807 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, kind, flag, 0);
808 dtd->dtd_data.ctt_type = (uint_t)ref;
809
810 return (type);
811 }
812
813 ctf_id_t
814 ctf_add_integer(ctf_file_t *fp, uint_t flag,
815 const char *name, const ctf_encoding_t *ep)
816 {
817 return (ctf_add_encoded(fp, flag, name, ep, CTF_K_INTEGER));
818 }
819
820 ctf_id_t
821 ctf_add_float(ctf_file_t *fp, uint_t flag,
822 const char *name, const ctf_encoding_t *ep)
823 {
824 return (ctf_add_encoded(fp, flag, name, ep, CTF_K_FLOAT));
825 }
826
827 ctf_id_t
828 ctf_add_pointer(ctf_file_t *fp, uint_t flag, ctf_id_t ref)
829 {
830 return (ctf_add_reftype(fp, flag, ref, CTF_K_POINTER));
831 }
832
833 ctf_id_t
834 ctf_add_array(ctf_file_t *fp, uint_t flag, const ctf_arinfo_t *arp)
835 {
836 ctf_dtdef_t *dtd;
837 ctf_id_t type;
838 ctf_file_t *fpd;
839
840 if (arp == NULL)
841 return (ctf_set_errno(fp, EINVAL));
842
843 fpd = fp;
844 if (ctf_lookup_by_id(&fpd, arp->ctr_contents) == NULL &&
845 ctf_dtd_lookup(fp, arp->ctr_contents) == NULL)
846 return (ctf_set_errno(fp, ECTF_BADID));
847
848 fpd = fp;
849 if (ctf_lookup_by_id(&fpd, arp->ctr_index) == NULL &&
850 ctf_dtd_lookup(fp, arp->ctr_index) == NULL)
851 return (ctf_set_errno(fp, ECTF_BADID));
852
853 if ((type = ctf_add_generic(fp, flag, NULL, &dtd)) == CTF_ERR)
854 return (CTF_ERR); /* errno is set for us */
855
856 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_ARRAY, flag, 0);
857 dtd->dtd_data.ctt_size = 0;
858 dtd->dtd_u.dtu_arr = *arp;
859 ctf_ref_inc(fp, arp->ctr_contents);
860 ctf_ref_inc(fp, arp->ctr_index);
861
862 return (type);
863 }
864
865 int
866 ctf_set_array(ctf_file_t *fp, ctf_id_t type, const ctf_arinfo_t *arp)
867 {
868 ctf_file_t *fpd;
869 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, type);
870
871 if (!(fp->ctf_flags & LCTF_RDWR))
872 return (ctf_set_errno(fp, ECTF_RDONLY));
873
874 if (dtd == NULL ||
875 LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info) != CTF_K_ARRAY)
876 return (ctf_set_errno(fp, ECTF_BADID));
877
878 fpd = fp;
879 if (ctf_lookup_by_id(&fpd, arp->ctr_contents) == NULL &&
880 ctf_dtd_lookup(fp, arp->ctr_contents) == NULL)
881 return (ctf_set_errno(fp, ECTF_BADID));
882
883 fpd = fp;
884 if (ctf_lookup_by_id(&fpd, arp->ctr_index) == NULL &&
885 ctf_dtd_lookup(fp, arp->ctr_index) == NULL)
886 return (ctf_set_errno(fp, ECTF_BADID));
887
888 ctf_ref_dec(fp, dtd->dtd_u.dtu_arr.ctr_contents);
889 ctf_ref_dec(fp, dtd->dtd_u.dtu_arr.ctr_index);
890 fp->ctf_flags |= LCTF_DIRTY;
891 dtd->dtd_u.dtu_arr = *arp;
892 ctf_ref_inc(fp, arp->ctr_contents);
893 ctf_ref_inc(fp, arp->ctr_index);
894
895 return (0);
896 }
897
898 ctf_id_t
899 ctf_add_function(ctf_file_t *fp, uint_t flag,
900 const ctf_funcinfo_t *ctc, const ctf_id_t *argv)
901 {
902 ctf_dtdef_t *dtd;
903 ctf_id_t type;
904 uint_t vlen;
905 int i;
906 ctf_id_t *vdat = NULL;
907 ctf_file_t *fpd;
908
909 if (ctc == NULL || (ctc->ctc_flags & ~CTF_FUNC_VARARG) != 0 ||
910 (ctc->ctc_argc != 0 && argv == NULL))
911 return (ctf_set_errno(fp, EINVAL));
912
913 vlen = ctc->ctc_argc;
914 if (ctc->ctc_flags & CTF_FUNC_VARARG)
915 vlen++; /* add trailing zero to indicate varargs (see below) */
916
917 if (vlen > LCTF_MAX_VLEN(fp))
918 return (ctf_set_errno(fp, EOVERFLOW));
919
920 fpd = fp;
921 if (ctf_lookup_by_id(&fpd, ctc->ctc_return) == NULL &&
922 ctf_dtd_lookup(fp, ctc->ctc_return) == NULL)
923 return (ctf_set_errno(fp, ECTF_BADID));
924
925 for (i = 0; i < ctc->ctc_argc; i++) {
926 fpd = fp;
927 if (ctf_lookup_by_id(&fpd, argv[i]) == NULL &&
928 ctf_dtd_lookup(fp, argv[i]) == NULL)
929 return (ctf_set_errno(fp, ECTF_BADID));
930 }
931
932 if (vlen != 0 && (vdat = ctf_alloc(sizeof (ctf_id_t) * vlen)) == NULL)
933 return (ctf_set_errno(fp, EAGAIN));
934
935 if ((type = ctf_add_generic(fp, flag, NULL, &dtd)) == CTF_ERR) {
936 ctf_free(vdat, sizeof (ctf_id_t) * vlen);
937 return (CTF_ERR); /* errno is set for us */
938 }
939
940 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_FUNCTION, flag, vlen);
941 dtd->dtd_data.ctt_type = ctc->ctc_return;
942
943 ctf_ref_inc(fp, ctc->ctc_return);
944 for (i = 0; i < ctc->ctc_argc; i++)
945 ctf_ref_inc(fp, argv[i]);
946
947 memcpy(vdat, argv, sizeof (ctf_id_t) * ctc->ctc_argc);
948 if (ctc->ctc_flags & CTF_FUNC_VARARG)
949 vdat[vlen - 1] = 0; /* add trailing zero to indicate varargs */
950 dtd->dtd_u.dtu_argv = vdat;
951
952 return (type);
953 }
954
955 ctf_id_t
956 ctf_add_struct(ctf_file_t *fp, uint_t flag, const char *name)
957 {
958 ctf_hash_t *hp = &fp->ctf_structs;
959 ctf_helem_t *hep = NULL;
960 ctf_dtdef_t *dtd;
961 ctf_id_t type;
962
963 if (name != NULL)
964 hep = ctf_hash_lookup(hp, fp, name, strlen(name));
965
966 if (hep != NULL && ctf_type_kind(fp, hep->h_type) == CTF_K_FORWARD)
967 dtd = ctf_dtd_lookup(fp, type = hep->h_type);
968 else if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
969 return (CTF_ERR); /* errno is set for us */
970
971 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_STRUCT, flag, 0);
972 dtd->dtd_data.ctt_size = 0;
973
974 return (type);
975 }
976
977 ctf_id_t
978 ctf_add_union(ctf_file_t *fp, uint_t flag, const char *name)
979 {
980 ctf_hash_t *hp = &fp->ctf_unions;
981 ctf_helem_t *hep = NULL;
982 ctf_dtdef_t *dtd;
983 ctf_id_t type;
984
985 if (name != NULL)
986 hep = ctf_hash_lookup(hp, fp, name, strlen(name));
987
988 if (hep != NULL && ctf_type_kind(fp, hep->h_type) == CTF_K_FORWARD)
989 dtd = ctf_dtd_lookup(fp, type = hep->h_type);
990 else if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
991 return (CTF_ERR); /* errno is set for us */
992
993 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_UNION, flag, 0);
994 dtd->dtd_data.ctt_size = 0;
995
996 return (type);
997 }
998
999 ctf_id_t
1000 ctf_add_enum(ctf_file_t *fp, uint_t flag, const char *name)
1001 {
1002 ctf_hash_t *hp = &fp->ctf_enums;
1003 ctf_helem_t *hep = NULL;
1004 ctf_dtdef_t *dtd;
1005 ctf_id_t type;
1006
1007 if (name != NULL)
1008 hep = ctf_hash_lookup(hp, fp, name, strlen(name));
1009
1010 if (hep != NULL && ctf_type_kind(fp, hep->h_type) == CTF_K_FORWARD)
1011 dtd = ctf_dtd_lookup(fp, type = hep->h_type);
1012 else if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
1013 return (CTF_ERR); /* errno is set for us */
1014
1015 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_ENUM, flag, 0);
1016 dtd->dtd_data.ctt_size = fp->ctf_dmodel->ctd_int;
1017
1018 return (type);
1019 }
1020
1021 ctf_id_t
1022 ctf_add_forward(ctf_file_t *fp, uint_t flag, const char *name, uint_t kind)
1023 {
1024 ctf_hash_t *hp;
1025 ctf_helem_t *hep;
1026 ctf_dtdef_t *dtd;
1027 ctf_id_t type;
1028
1029 switch (kind) {
1030 case CTF_K_STRUCT:
1031 hp = &fp->ctf_structs;
1032 break;
1033 case CTF_K_UNION:
1034 hp = &fp->ctf_unions;
1035 break;
1036 case CTF_K_ENUM:
1037 hp = &fp->ctf_enums;
1038 break;
1039 default:
1040 return (ctf_set_errno(fp, ECTF_NOTSUE));
1041 }
1042
1043 /*
1044 * If the type is already defined or exists as a forward tag, just
1045 * return the ctf_id_t of the existing definition.
1046 */
1047 if (name != NULL && (hep = ctf_hash_lookup(hp,
1048 fp, name, strlen(name))) != NULL)
1049 return (hep->h_type);
1050
1051 if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
1052 return (CTF_ERR); /* errno is set for us */
1053
1054 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_FORWARD, flag, 0);
1055 dtd->dtd_data.ctt_type = kind;
1056
1057 return (type);
1058 }
1059
1060 ctf_id_t
1061 ctf_add_typedef(ctf_file_t *fp, uint_t flag, const char *name, ctf_id_t ref)
1062 {
1063 ctf_dtdef_t *dtd;
1064 ctf_id_t type;
1065 ctf_file_t *fpd;
1066
1067 fpd = fp;
1068 if (ref == CTF_ERR || (ctf_lookup_by_id(&fpd, ref) == NULL &&
1069 ctf_dtd_lookup(fp, ref) == NULL))
1070 return (ctf_set_errno(fp, EINVAL));
1071
1072 if ((type = ctf_add_generic(fp, flag, name, &dtd)) == CTF_ERR)
1073 return (CTF_ERR); /* errno is set for us */
1074
1075 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, CTF_K_TYPEDEF, flag, 0);
1076 dtd->dtd_data.ctt_type = ref;
1077 ctf_ref_inc(fp, ref);
1078
1079 return (type);
1080 }
1081
1082 ctf_id_t
1083 ctf_add_volatile(ctf_file_t *fp, uint_t flag, ctf_id_t ref)
1084 {
1085 return (ctf_add_reftype(fp, flag, ref, CTF_K_VOLATILE));
1086 }
1087
1088 ctf_id_t
1089 ctf_add_const(ctf_file_t *fp, uint_t flag, ctf_id_t ref)
1090 {
1091 return (ctf_add_reftype(fp, flag, ref, CTF_K_CONST));
1092 }
1093
1094 ctf_id_t
1095 ctf_add_restrict(ctf_file_t *fp, uint_t flag, ctf_id_t ref)
1096 {
1097 return (ctf_add_reftype(fp, flag, ref, CTF_K_RESTRICT));
1098 }
1099
1100 int
1101 ctf_add_enumerator(ctf_file_t *fp, ctf_id_t enid, const char *name, int value)
1102 {
1103 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, enid);
1104 ctf_dmdef_t *dmd;
1105
1106 uint_t kind, vlen, root;
1107 char *s;
1108
1109 if (name == NULL)
1110 return (ctf_set_errno(fp, EINVAL));
1111
1112 if (!(fp->ctf_flags & LCTF_RDWR))
1113 return (ctf_set_errno(fp, ECTF_RDONLY));
1114
1115 if (dtd == NULL)
1116 return (ctf_set_errno(fp, ECTF_BADID));
1117
1118 kind = LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info);
1119 root = LCTF_INFO_ROOT(fp, dtd->dtd_data.ctt_info);
1120 vlen = LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info);
1121
1122 if (kind != CTF_K_ENUM)
1123 return (ctf_set_errno(fp, ECTF_NOTENUM));
1124
1125 if (vlen > LCTF_MAX_VLEN(fp))
1126 return (ctf_set_errno(fp, ECTF_DTFULL));
1127
1128 for (dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
1129 dmd != NULL; dmd = ctf_list_next(dmd)) {
1130 if (strcmp(dmd->dmd_name, name) == 0)
1131 return (ctf_set_errno(fp, ECTF_DUPMEMBER));
1132 }
1133
1134 if ((dmd = ctf_alloc(sizeof (ctf_dmdef_t))) == NULL)
1135 return (ctf_set_errno(fp, EAGAIN));
1136
1137 if ((s = ctf_strdup(name)) == NULL) {
1138 ctf_free(dmd, sizeof (ctf_dmdef_t));
1139 return (ctf_set_errno(fp, EAGAIN));
1140 }
1141
1142 dmd->dmd_name = s;
1143 dmd->dmd_type = CTF_ERR;
1144 dmd->dmd_offset = 0;
1145 dmd->dmd_value = value;
1146
1147 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, kind, root, vlen + 1);
1148 ctf_list_append(&dtd->dtd_u.dtu_members, dmd);
1149
1150 fp->ctf_dtstrlen += strlen(s) + 1;
1151 fp->ctf_flags |= LCTF_DIRTY;
1152
1153 return (0);
1154 }
1155
1156 int
1157 ctf_add_member(ctf_file_t *fp, ctf_id_t souid, const char *name, ctf_id_t type)
1158 {
1159 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, souid);
1160 ctf_dmdef_t *dmd;
1161
1162 ssize_t msize, malign, ssize;
1163 uint_t kind, vlen, root;
1164 char *s = NULL;
1165
1166 if (!(fp->ctf_flags & LCTF_RDWR))
1167 return (ctf_set_errno(fp, ECTF_RDONLY));
1168
1169 if (dtd == NULL)
1170 return (ctf_set_errno(fp, ECTF_BADID));
1171
1172 kind = LCTF_INFO_KIND(fp, dtd->dtd_data.ctt_info);
1173 root = LCTF_INFO_ROOT(fp, dtd->dtd_data.ctt_info);
1174 vlen = LCTF_INFO_VLEN(fp, dtd->dtd_data.ctt_info);
1175
1176 if (kind != CTF_K_STRUCT && kind != CTF_K_UNION)
1177 return (ctf_set_errno(fp, ECTF_NOTSOU));
1178
1179 if (vlen > LCTF_MAX_VLEN(fp))
1180 return (ctf_set_errno(fp, ECTF_DTFULL));
1181
1182 if (name != NULL) {
1183 for (dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
1184 dmd != NULL; dmd = ctf_list_next(dmd)) {
1185 if (dmd->dmd_name != NULL &&
1186 strcmp(dmd->dmd_name, name) == 0)
1187 return (ctf_set_errno(fp, ECTF_DUPMEMBER));
1188 }
1189 }
1190
1191 if ((msize = ctf_type_size(fp, type)) == CTF_ERR ||
1192 (malign = ctf_type_align(fp, type)) == CTF_ERR)
1193 return (CTF_ERR); /* errno is set for us */
1194
1195 if ((dmd = ctf_alloc(sizeof (ctf_dmdef_t))) == NULL)
1196 return (ctf_set_errno(fp, EAGAIN));
1197
1198 if (name != NULL && (s = ctf_strdup(name)) == NULL) {
1199 ctf_free(dmd, sizeof (ctf_dmdef_t));
1200 return (ctf_set_errno(fp, EAGAIN));
1201 }
1202
1203 dmd->dmd_name = s;
1204 dmd->dmd_type = type;
1205 dmd->dmd_value = -1;
1206
1207 if (kind == CTF_K_STRUCT && vlen != 0) {
1208 ctf_dmdef_t *lmd = ctf_list_prev(&dtd->dtd_u.dtu_members);
1209 ctf_id_t ltype = ctf_type_resolve(fp, lmd->dmd_type);
1210 size_t off = lmd->dmd_offset;
1211
1212 ctf_encoding_t linfo;
1213 ssize_t lsize;
1214
1215 if (ctf_type_encoding(fp, ltype, &linfo) != CTF_ERR)
1216 off += linfo.cte_bits;
1217 else if ((lsize = ctf_type_size(fp, ltype)) != CTF_ERR)
1218 off += lsize * NBBY;
1219
1220 /*
1221 * Round up the offset of the end of the last member to the
1222 * next byte boundary, convert 'off' to bytes, and then round
1223 * it up again to the next multiple of the alignment required
1224 * by the new member. Finally, convert back to bits and store
1225 * the result in dmd_offset. Technically we could do more
1226 * efficient packing if the new member is a bit-field, but
1227 * we're the "compiler" and ANSI says we can do as we choose.
1228 */
1229 off = roundup(off, NBBY) / NBBY;
1230 off = roundup(off, MAX(malign, 1));
1231 dmd->dmd_offset = off * NBBY;
1232 ssize = off + msize;
1233 } else {
1234 dmd->dmd_offset = 0;
1235 ssize = ctf_get_ctt_size(fp, &dtd->dtd_data, NULL, NULL);
1236 ssize = MAX(ssize, msize);
1237 }
1238
1239 if (ssize > LCTF_MAX_SIZE(fp)) {
1240 dtd->dtd_data.ctt_size = LCTF_LSIZE_SENT(fp);
1241 dtd->dtd_data.ctt_lsizehi = CTF_SIZE_TO_LSIZE_HI(ssize);
1242 dtd->dtd_data.ctt_lsizelo = CTF_SIZE_TO_LSIZE_LO(ssize);
1243 } else
1244 dtd->dtd_data.ctt_size = ssize;
1245
1246 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(fp, kind, root, vlen + 1);
1247 ctf_list_append(&dtd->dtd_u.dtu_members, dmd);
1248
1249 if (s != NULL)
1250 fp->ctf_dtstrlen += strlen(s) + 1;
1251
1252 ctf_ref_inc(fp, type);
1253 fp->ctf_flags |= LCTF_DIRTY;
1254 return (0);
1255 }
1256
1257 /*
1258 * This removes a type from the dynamic section. This will fail if the type is
1259 * referenced by another type. Note that the CTF ID is never reused currently by
1260 * CTF. Note that if this container is a parent container then we just outright
1261 * refuse to remove the type. There currently is no notion of searching for the
1262 * ctf_dtdef_t in parent containers. If there is, then this constraint could
1263 * become finer grained.
1264 */
1265 int
1266 ctf_delete_type(ctf_file_t *fp, ctf_id_t type)
1267 {
1268 ctf_file_t *fpd;
1269 ctf_dtdef_t *dtd = ctf_dtd_lookup(fp, type);
1270
1271 if (!(fp->ctf_flags & LCTF_RDWR))
1272 return (ctf_set_errno(fp, ECTF_RDONLY));
1273
1274 /*
1275 * We want to give as useful an errno as possible. That means that we
1276 * want to distinguish between a type which does not exist and one for
1277 * which the type is not dynamic.
1278 */
1279 fpd = fp;
1280 if (ctf_lookup_by_id(&fpd, type) == NULL &&
1281 ctf_dtd_lookup(fp, type) == NULL)
1282 return (CTF_ERR); /* errno is set for us */
1283
1284 if (dtd == NULL)
1285 return (ctf_set_errno(fp, ECTF_NOTDYN));
1286
1287 if (dtd->dtd_ref != 0 || fp->ctf_refcnt > 1)
1288 return (ctf_set_errno(fp, ECTF_REFERENCED));
1289
1290 ctf_dtd_delete(fp, dtd);
1291 fp->ctf_flags |= LCTF_DIRTY;
1292 return (0);
1293 }
1294
1295 static int
1296 enumcmp(const char *name, int value, void *arg)
1297 {
1298 ctf_bundle_t *ctb = arg;
1299 int bvalue;
1300
1301 return (ctf_enum_value(ctb->ctb_file, ctb->ctb_type,
1302 name, &bvalue) == CTF_ERR || value != bvalue);
1303 }
1304
1305 static int
1306 enumadd(const char *name, int value, void *arg)
1307 {
1308 ctf_bundle_t *ctb = arg;
1309
1310 return (ctf_add_enumerator(ctb->ctb_file, ctb->ctb_type,
1311 name, value) == CTF_ERR);
1312 }
1313
1314 static int
1315 membadd(const char *name, ctf_id_t type, ulong_t offset, void *arg)
1316 {
1317 ctf_bundle_t *ctb = arg;
1318 ctf_dmdef_t *dmd;
1319 char *s = NULL;
1320
1321 if ((dmd = ctf_alloc(sizeof (ctf_dmdef_t))) == NULL)
1322 return (ctf_set_errno(ctb->ctb_file, EAGAIN));
1323
1324 if (name != NULL && *name != '\0' && (s = ctf_strdup(name)) == NULL) {
1325 ctf_free(dmd, sizeof (ctf_dmdef_t));
1326 return (ctf_set_errno(ctb->ctb_file, EAGAIN));
1327 }
1328
1329 /*
1330 * For now, dmd_type is copied as the src_fp's type; it is reset to an
1331 * equivalent dst_fp type by a final loop in ctf_add_type(), below.
1332 */
1333 dmd->dmd_name = s;
1334 dmd->dmd_type = type;
1335 dmd->dmd_offset = offset;
1336 dmd->dmd_value = -1;
1337
1338 ctf_list_append(&ctb->ctb_dtd->dtd_u.dtu_members, dmd);
1339
1340 if (s != NULL)
1341 ctb->ctb_file->ctf_dtstrlen += strlen(s) + 1;
1342
1343 ctb->ctb_file->ctf_flags |= LCTF_DIRTY;
1344 return (0);
1345 }
1346
1347 static long
1348 soucmp(ctf_file_t *src_fp, ctf_id_t src_type, ctf_file_t *dst_fp,
1349 ctf_id_t dst_type)
1350 {
1351 const void *src_tp, *dst_tp;
1352 const char *src_name, *dst_name;
1353 ssize_t src_sz, dst_sz, src_inc, dst_inc;
1354 uint_t dst_kind, dst_vlen, src_kind, src_vlen, n;
1355
1356 if ((src_type = ctf_type_resolve(src_fp, src_type)) == CTF_ERR)
1357 return (CTF_ERR);
1358 if ((dst_type = ctf_type_resolve(dst_fp, dst_type)) == CTF_ERR)
1359 return (CTF_ERR);
1360
1361 if ((src_tp = ctf_lookup_by_id(&src_fp, src_type)) == NULL)
1362 return (CTF_ERR);
1363 if ((dst_tp = ctf_lookup_by_id(&dst_fp, dst_type)) == NULL)
1364 return (CTF_ERR);
1365
1366 ctf_get_ctt_info(src_fp, src_tp, &src_kind, &src_vlen, NULL);
1367 ctf_get_ctt_info(dst_fp, dst_tp, &dst_kind, &dst_vlen, NULL);
1368
1369 if (src_kind != dst_kind)
1370 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1371 if (src_kind != CTF_K_STRUCT && src_kind != CTF_K_UNION)
1372 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1373 if (src_vlen != dst_vlen)
1374 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1375
1376 (void) ctf_get_ctt_size(src_fp, src_tp, &src_sz, &src_inc);
1377 (void) ctf_get_ctt_size(dst_fp, dst_tp, &dst_sz, &dst_inc);
1378 if (src_sz != dst_sz)
1379 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1380
1381 const char *src_mp, *dst_mp;
1382 ulong_t src_offset, dst_offset;
1383
1384 src_mp = (const char *)src_tp + src_inc;
1385 dst_mp = (const char *)dst_tp + dst_inc;
1386 for (n = src_vlen; n != 0;
1387 n--, src_mp += src_inc, dst_mp += dst_inc) {
1388 ctf_get_ctm_info(src_fp, src_mp, src_sz, &src_inc, NULL,
1389 &src_offset, &src_name);
1390 ctf_get_ctm_info(dst_fp, dst_mp, dst_sz, &dst_inc, NULL,
1391 &dst_offset, &dst_name);
1392
1393 if (src_offset != dst_offset)
1394 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1395 if (strcmp(src_name, dst_name) != 0)
1396 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1397 }
1398
1399 return (0);
1400 }
1401
1402 /*
1403 * The ctf_add_type routine is used to copy a type from a source CTF container
1404 * to a dynamic destination container. This routine operates recursively by
1405 * following the source type's links and embedded member types. If the
1406 * destination container already contains a named type which has the same
1407 * attributes, then we succeed and return this type but no changes occur.
1408 */
1409 ctf_id_t
1410 ctf_add_type(ctf_file_t *dst_fp, ctf_file_t *src_fp, ctf_id_t src_type)
1411 {
1412 ctf_id_t dst_type = CTF_ERR;
1413 uint_t dst_kind = CTF_K_UNKNOWN;
1414
1415 const void *tp;
1416 const char *name;
1417 uint_t type, kind, flag, vlen;
1418
1419 ctf_bundle_t src, dst;
1420 ctf_encoding_t src_en, main_en, dst_en;
1421 ctf_arinfo_t src_ar, dst_ar;
1422
1423 ctf_dtdef_t *dtd;
1424 ctf_funcinfo_t ctc;
1425 ssize_t size;
1426
1427 ctf_hash_t *hp;
1428 ctf_helem_t *hep;
1429
1430 if (dst_fp == src_fp)
1431 return (src_type);
1432
1433 if (!(dst_fp->ctf_flags & LCTF_RDWR))
1434 return (ctf_set_errno(dst_fp, ECTF_RDONLY));
1435
1436 if ((tp = ctf_lookup_by_id(&src_fp, src_type)) == NULL)
1437 return (ctf_set_errno(dst_fp, ctf_errno(src_fp)));
1438
1439 name = ctf_type_rname(src_fp, tp);
1440
1441 ctf_get_ctt_info(src_fp, tp, &kind, &vlen, &flag);
1442
1443 switch (kind) {
1444 case CTF_K_STRUCT:
1445 hp = &dst_fp->ctf_structs;
1446 break;
1447 case CTF_K_UNION:
1448 hp = &dst_fp->ctf_unions;
1449 break;
1450 case CTF_K_ENUM:
1451 hp = &dst_fp->ctf_enums;
1452 break;
1453 default:
1454 hp = &dst_fp->ctf_names;
1455 break;
1456 }
1457
1458 /*
1459 * If the source type has a name and is a root type (visible at the
1460 * top-level scope), lookup the name in the destination container and
1461 * verify that it is of the same kind before we do anything else.
1462 */
1463 if ((flag & CTF_ADD_ROOT) && name[0] != '\0' &&
1464 (hep = ctf_hash_lookup(hp, dst_fp, name, strlen(name))) != NULL) {
1465 dst_type = (ctf_id_t)hep->h_type;
1466 dst_kind = ctf_type_kind(dst_fp, dst_type);
1467 }
1468
1469 /*
1470 * If an identically named dst_type exists, fail with ECTF_CONFLICT
1471 * unless dst_type is a forward declaration and src_type is a struct,
1472 * union, or enum (i.e. the definition of the previous forward decl).
1473 */
1474 if (dst_type != CTF_ERR && dst_kind != kind) {
1475 if (dst_kind != CTF_K_FORWARD || (kind != CTF_K_ENUM &&
1476 kind != CTF_K_STRUCT && kind != CTF_K_UNION))
1477 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1478 else
1479 dst_type = CTF_ERR;
1480 }
1481
1482 /*
1483 * If the non-empty name was not found in the appropriate hash, search
1484 * the list of pending dynamic definitions that are not yet committed.
1485 * If a matching name and kind are found, assume this is the type that
1486 * we are looking for. This is necessary to permit ctf_add_type() to
1487 * operate recursively on entities such as a struct that contains a
1488 * pointer member that refers to the same struct type.
1489 *
1490 * In the case of integer and floating point types, we match using the
1491 * type encoding as well - else we may incorrectly return a bitfield
1492 * type, for instance.
1493 */
1494 if (dst_type == CTF_ERR && name[0] != '\0') {
1495 for (dtd = ctf_list_prev(&dst_fp->ctf_dtdefs); dtd != NULL &&
1496 LCTF_TYPE_TO_INDEX(dst_fp, dtd->dtd_type) >
1497 dst_fp->ctf_dtoldid; dtd = ctf_list_prev(dtd)) {
1498 if (LCTF_INFO_KIND(dst_fp, dtd->dtd_data.ctt_info) !=
1499 kind || dtd->dtd_name == NULL ||
1500 strcmp(dtd->dtd_name, name) != 0)
1501 continue;
1502 if (kind == CTF_K_INTEGER || kind == CTF_K_FLOAT) {
1503 if (ctf_type_encoding(src_fp, src_type,
1504 &src_en) != 0)
1505 continue;
1506 if (memcmp(&src_en, &dtd->dtd_u.dtu_enc,
1507 sizeof (ctf_encoding_t)) != 0)
1508 continue;
1509 }
1510 return (dtd->dtd_type);
1511 }
1512 }
1513
1514 src.ctb_file = src_fp;
1515 src.ctb_type = src_type;
1516 src.ctb_dtd = NULL;
1517
1518 dst.ctb_file = dst_fp;
1519 dst.ctb_type = dst_type;
1520 dst.ctb_dtd = NULL;
1521
1522 /*
1523 * Now perform kind-specific processing. If dst_type is CTF_ERR, then
1524 * we add a new type with the same properties as src_type to dst_fp.
1525 * If dst_type is not CTF_ERR, then we verify that dst_type has the
1526 * same attributes as src_type. We recurse for embedded references.
1527 */
1528 switch (kind) {
1529 case CTF_K_INTEGER:
1530 case CTF_K_FLOAT:
1531 if (ctf_type_encoding(src_fp, src_type, &src_en) != 0)
1532 return (ctf_set_errno(dst_fp, ctf_errno(src_fp)));
1533
1534 /*
1535 * This could be a bitfield, and the CTF library assumes
1536 * intrinsics will appear before bitfields. Therefore,
1537 * try to copy over the intrinsic prior to copying the
1538 * bitfield.
1539 */
1540 if (dst_type == CTF_ERR && name[0] != '\0' &&
1541 (hep = ctf_hash_lookup(&src_fp->ctf_names, src_fp, name,
1542 strlen(name))) != NULL &&
1543 src_type != (ctf_id_t)hep->h_type) {
1544 if (ctf_type_encoding(src_fp, (ctf_id_t)hep->h_type,
1545 &main_en) != 0) {
1546 return (ctf_set_errno(dst_fp,
1547 ctf_errno(src_fp)));
1548 }
1549 if (memcmp(&src_en, &main_en, sizeof (ctf_encoding_t)) &&
1550 ctf_add_type(dst_fp, src_fp,
1551 (ctf_id_t)hep->h_type) == CTF_ERR)
1552 return (CTF_ERR); /* errno is set for us */
1553 }
1554
1555 if (dst_type != CTF_ERR) {
1556 if (ctf_type_encoding(dst_fp, dst_type, &dst_en) != 0)
1557 return (CTF_ERR); /* errno is set for us */
1558
1559 if (memcmp(&src_en, &dst_en, sizeof (ctf_encoding_t)))
1560 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1561
1562 } else if (kind == CTF_K_INTEGER) {
1563 dst_type = ctf_add_integer(dst_fp, flag, name, &src_en);
1564 } else
1565 dst_type = ctf_add_float(dst_fp, flag, name, &src_en);
1566 break;
1567
1568 case CTF_K_POINTER:
1569 case CTF_K_VOLATILE:
1570 case CTF_K_CONST:
1571 case CTF_K_RESTRICT:
1572 src_type = ctf_type_reference(src_fp, src_type);
1573 src_type = ctf_add_type(dst_fp, src_fp, src_type);
1574
1575 if (src_type == CTF_ERR)
1576 return (CTF_ERR); /* errno is set for us */
1577
1578 dst_type = ctf_add_reftype(dst_fp, flag, src_type, kind);
1579 break;
1580
1581 case CTF_K_ARRAY:
1582 if (ctf_array_info(src_fp, src_type, &src_ar) == CTF_ERR)
1583 return (ctf_set_errno(dst_fp, ctf_errno(src_fp)));
1584
1585 src_ar.ctr_contents =
1586 ctf_add_type(dst_fp, src_fp, src_ar.ctr_contents);
1587 src_ar.ctr_index =
1588 ctf_add_type(dst_fp, src_fp, src_ar.ctr_index);
1589 src_ar.ctr_nelems = src_ar.ctr_nelems;
1590
1591 if (src_ar.ctr_contents == CTF_ERR ||
1592 src_ar.ctr_index == CTF_ERR)
1593 return (CTF_ERR); /* errno is set for us */
1594
1595 if (dst_type != CTF_ERR) {
1596 if (ctf_array_info(dst_fp, dst_type, &dst_ar) != 0)
1597 return (CTF_ERR); /* errno is set for us */
1598
1599 if (memcmp(&src_ar, &dst_ar, sizeof (ctf_arinfo_t)))
1600 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1601 } else
1602 dst_type = ctf_add_array(dst_fp, flag, &src_ar);
1603 break;
1604
1605 case CTF_K_FUNCTION:
1606 ctf_get_ctt_index(src_fp, tp, NULL, &type, NULL);
1607 ctc.ctc_return = ctf_add_type(dst_fp, src_fp, type);
1608 ctc.ctc_argc = 0;
1609 ctc.ctc_flags = 0;
1610
1611 if (ctc.ctc_return == CTF_ERR)
1612 return (CTF_ERR); /* errno is set for us */
1613
1614 dst_type = ctf_add_function(dst_fp, flag, &ctc, NULL);
1615 break;
1616
1617 case CTF_K_STRUCT:
1618 case CTF_K_UNION: {
1619 ctf_dmdef_t *dmd;
1620 int errs = 0;
1621
1622 if (dst_type != CTF_ERR && dst_kind != CTF_K_FORWARD) {
1623 /*
1624 * Compare the sizes and fields of the two types.
1625 * The field comparisons only check the names and
1626 * offsets, so this is not perfect but is good enough
1627 * for scenarios that we care about.
1628 */
1629 if (soucmp(src_fp, src_type, dst_fp, dst_type) != 0)
1630 return (CTF_ERR); /* errno is set for us */
1631 break;
1632 }
1633
1634 /*
1635 * Unlike the other cases, copying structs and unions is done
1636 * manually so as to avoid repeated lookups in ctf_add_member
1637 * and to ensure the exact same member offsets as in src_type.
1638 */
1639 dst_type = ctf_add_generic(dst_fp, flag, name, &dtd);
1640 if (dst_type == CTF_ERR)
1641 return (CTF_ERR); /* errno is set for us */
1642
1643 dst.ctb_type = dst_type;
1644 dst.ctb_dtd = dtd;
1645
1646 if (ctf_member_iter(src_fp, src_type, membadd, &dst) != 0)
1647 errs++; /* increment errs and fail at bottom of case */
1648
1649 if ((size = ctf_type_size(src_fp, src_type)) >
1650 LCTF_MAX_SIZE(src_fp)) {
1651 dtd->dtd_data.ctt_size = LCTF_LSIZE_SENT(dst_fp);
1652 dtd->dtd_data.ctt_lsizehi = CTF_SIZE_TO_LSIZE_HI(size);
1653 dtd->dtd_data.ctt_lsizelo = CTF_SIZE_TO_LSIZE_LO(size);
1654 } else
1655 dtd->dtd_data.ctt_size = size;
1656
1657 dtd->dtd_data.ctt_info = LCTF_TYPE_INFO(dst_fp, kind, flag,
1658 vlen);
1659
1660 /*
1661 * Make a final pass through the members changing each dmd_type
1662 * (a src_fp type) to an equivalent type in dst_fp. We pass
1663 * through all members, leaving any that fail set to CTF_ERR.
1664 */
1665 for (dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
1666 dmd != NULL; dmd = ctf_list_next(dmd)) {
1667 if ((dmd->dmd_type = ctf_add_type(dst_fp, src_fp,
1668 dmd->dmd_type)) == CTF_ERR)
1669 errs++;
1670 }
1671
1672 if (errs)
1673 return (CTF_ERR); /* errno is set for us */
1674
1675 /*
1676 * Now that we know that we can't fail, we go through and bump
1677 * all the reference counts on the member types.
1678 */
1679 for (dmd = ctf_list_next(&dtd->dtd_u.dtu_members);
1680 dmd != NULL; dmd = ctf_list_next(dmd))
1681 ctf_ref_inc(dst_fp, dmd->dmd_type);
1682 break;
1683 }
1684
1685 case CTF_K_ENUM:
1686 if (dst_type != CTF_ERR && dst_kind != CTF_K_FORWARD) {
1687 if (ctf_enum_iter(src_fp, src_type, enumcmp, &dst) ||
1688 ctf_enum_iter(dst_fp, dst_type, enumcmp, &src))
1689 return (ctf_set_errno(dst_fp, ECTF_CONFLICT));
1690 } else {
1691 dst_type = ctf_add_enum(dst_fp, flag, name);
1692 if ((dst.ctb_type = dst_type) == CTF_ERR ||
1693 ctf_enum_iter(src_fp, src_type, enumadd, &dst))
1694 return (CTF_ERR); /* errno is set for us */
1695 }
1696 break;
1697
1698 case CTF_K_FORWARD:
1699 if (dst_type == CTF_ERR) {
1700 dst_type = ctf_add_forward(dst_fp,
1701 flag, name, CTF_K_STRUCT); /* assume STRUCT */
1702 }
1703 break;
1704
1705 case CTF_K_TYPEDEF:
1706 src_type = ctf_type_reference(src_fp, src_type);
1707 src_type = ctf_add_type(dst_fp, src_fp, src_type);
1708
1709 if (src_type == CTF_ERR)
1710 return (CTF_ERR); /* errno is set for us */
1711
1712 /*
1713 * If dst_type is not CTF_ERR at this point, we should check if
1714 * ctf_type_reference(dst_fp, dst_type) != src_type and if so
1715 * fail with ECTF_CONFLICT. However, this causes problems with
1716 * <sys/types.h> typedefs that vary based on things like if
1717 * _ILP32x then pid_t is int otherwise long. We therefore omit
1718 * this check and assume that if the identically named typedef
1719 * already exists in dst_fp, it is correct or equivalent.
1720 */
1721 if (dst_type == CTF_ERR) {
1722 dst_type = ctf_add_typedef(dst_fp, flag,
1723 name, src_type);
1724 }
1725 break;
1726
1727 default:
1728 return (ctf_set_errno(dst_fp, ECTF_CORRUPT));
1729 }
1730
1731 return (dst_type);
1732 }
1733