Branch data Line data Source code
1 : : /* Generate CTF.
2 : : Copyright (C) 2019-2024 Free Software Foundation, Inc.
3 : :
4 : : This file is part of GCC.
5 : :
6 : : GCC is free software; you can redistribute it and/or modify it under
7 : : the terms of the GNU General Public License as published by the Free
8 : : Software Foundation; either version 3, or (at your option) any later
9 : : version.
10 : :
11 : : GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 : : WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 : : FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 : : for more details.
15 : :
16 : : You should have received a copy of the GNU General Public License
17 : : along with GCC; see the file COPYING3. If not see
18 : : <http://www.gnu.org/licenses/>. */
19 : :
20 : : #include "config.h"
21 : : #include "system.h"
22 : : #include "coretypes.h"
23 : : #include "target.h"
24 : : #include "toplev.h"
25 : : #include "ctfc.h"
26 : : #include "diagnostic-core.h"
27 : :
28 : : /* A CTF container object - one per translation unit. */
29 : :
30 : : ctf_container_ref tu_ctfc;
31 : :
32 : : ctf_container_ref
33 : 2644 : ctf_get_tu_ctfc (void)
34 : : {
35 : 2644 : return tu_ctfc;
36 : : }
37 : :
38 : : /* If the next ctf type id is still set to the init value, no ctf records to
39 : : report. */
40 : : bool
41 : 339 : ctfc_is_empty_container (ctf_container_ref ctfc)
42 : : {
43 : 339 : return ((ctfc)->ctfc_nextid == CTF_INIT_TYPEID);
44 : : }
45 : :
46 : : /* Get the total number of CTF types in the container. */
47 : :
48 : : unsigned int
49 : 260 : ctfc_get_num_ctf_types (ctf_container_ref ctfc)
50 : : {
51 : 260 : return ctfc->ctfc_types->elements ();
52 : : }
53 : :
54 : : /* Get the total number of CTF variables in the container. */
55 : :
56 : 260 : unsigned int ctfc_get_num_ctf_vars (ctf_container_ref ctfc)
57 : : {
58 : 260 : return ctfc->ctfc_vars->elements ();
59 : : }
60 : :
61 : : /* Get reference to the CTF string table or the CTF auxilliary
62 : : string table. */
63 : :
64 : : ctf_strtable_t *
65 : 2806 : ctfc_get_strtab (ctf_container_ref ctfc, int aux)
66 : : {
67 : 2806 : return aux ? &(ctfc)->ctfc_aux_strtable : &(ctfc->ctfc_strtable);
68 : : }
69 : :
70 : : /* Get the length of the specified string table of the CTF container. */
71 : :
72 : : size_t
73 : 398 : ctfc_get_strtab_len (ctf_container_ref ctfc, int aux)
74 : : {
75 : 398 : ctf_strtable_t * strtab = ctfc_get_strtab (ctfc, aux);
76 : 398 : return strtab->ctstab_len;
77 : : }
78 : :
79 : : /* Get the number of bytes to represent the variable length portion of all CTF
80 : : types in the CTF container. */
81 : :
82 : 260 : size_t ctfc_get_num_vlen_bytes (ctf_container_ref ctfc)
83 : : {
84 : 260 : return ctfc->ctfc_num_vlen_bytes;
85 : : }
86 : :
87 : : /* Return which member of the union is used in CTFTYPE. Used for garbage
88 : : collection. */
89 : :
90 : : enum ctf_dtu_d_union_enum
91 : 0 : ctf_dtu_d_union_selector (ctf_dtdef_ref ctftype)
92 : : {
93 : 0 : uint32_t kind = CTF_V2_INFO_KIND (ctftype->dtd_data.ctti_info);
94 : 0 : switch (kind)
95 : : {
96 : : case CTF_K_UNKNOWN:
97 : : case CTF_K_INTEGER:
98 : : case CTF_K_FLOAT:
99 : : return CTF_DTU_D_ENCODING;
100 : : case CTF_K_STRUCT:
101 : : case CTF_K_UNION:
102 : : case CTF_K_ENUM:
103 : : return CTF_DTU_D_MEMBERS;
104 : : case CTF_K_ARRAY:
105 : : return CTF_DTU_D_ARRAY;
106 : : case CTF_K_FUNCTION:
107 : : return CTF_DTU_D_ARGUMENTS;
108 : : case CTF_K_SLICE:
109 : : return CTF_DTU_D_SLICE;
110 : : default:
111 : : /* The largest member as default. */
112 : : return CTF_DTU_D_ARRAY;
113 : : }
114 : : }
115 : :
116 : : /* Insert CTF type into the CTF container. */
117 : :
118 : : static void
119 : 1400 : ctf_dtd_insert (ctf_container_ref ctfc, ctf_dtdef_ref dtd)
120 : : {
121 : 1400 : bool existed = false;
122 : 1400 : ctf_dtdef_ref entry = dtd;
123 : :
124 : 1400 : ctf_dtdef_ref * item = ctfc->ctfc_types->find_slot (entry, INSERT);
125 : 1400 : if (*item == NULL)
126 : 1400 : *item = dtd;
127 : : else
128 : : existed = true;
129 : : /* Duplicate CTF type records not expected to be inserted. */
130 : 1400 : gcc_assert (!existed);
131 : 1400 : }
132 : :
133 : : /* Lookup CTF type given a DWARF die for the type. */
134 : :
135 : : ctf_dtdef_ref
136 : 4491 : ctf_dtd_lookup (const ctf_container_ref ctfc, const dw_die_ref type)
137 : : {
138 : 4491 : ctf_dtdef_t entry;
139 : 4491 : entry.dtd_key = type;
140 : :
141 : 4491 : ctf_dtdef_ref * slot = ctfc->ctfc_types->find_slot (&entry, NO_INSERT);
142 : :
143 : 4491 : if (slot)
144 : 1708 : return (ctf_dtdef_ref)*slot;
145 : :
146 : : return NULL;
147 : : }
148 : :
149 : : /* Insert CTF variable into the CTF container. */
150 : :
151 : : static void
152 : 255 : ctf_dvd_insert (ctf_container_ref ctfc, ctf_dvdef_ref dvd)
153 : : {
154 : 255 : bool existed = false;
155 : 255 : ctf_dvdef_ref entry = dvd;
156 : :
157 : 255 : ctf_dvdef_ref * item = ctfc->ctfc_vars->find_slot (entry, INSERT);
158 : 255 : if (*item == NULL)
159 : 255 : *item = dvd;
160 : : else
161 : : existed = true;
162 : : /* Duplicate variable records not expected to be inserted. */
163 : 255 : gcc_assert (!existed);
164 : 255 : }
165 : :
166 : : /* Lookup CTF variable given a DWARF die for the decl. */
167 : :
168 : : ctf_dvdef_ref
169 : 346 : ctf_dvd_lookup (const ctf_container_ref ctfc, dw_die_ref die)
170 : : {
171 : 346 : ctf_dvdef_t entry;
172 : 346 : entry.dvd_key = die;
173 : :
174 : 346 : ctf_dvdef_ref * slot = ctfc->ctfc_vars->find_slot (&entry, NO_INSERT);
175 : :
176 : 346 : if (slot)
177 : 91 : return (ctf_dvdef_ref)*slot;
178 : :
179 : : return NULL;
180 : : }
181 : :
182 : : /* Insert a dummy CTF variable into the list of variables to be ignored. */
183 : :
184 : : static void
185 : 2 : ctf_dvd_ignore_insert (ctf_container_ref ctfc, ctf_dvdef_ref dvd)
186 : : {
187 : 2 : bool existed = false;
188 : 2 : ctf_dvdef_ref entry = dvd;
189 : :
190 : 2 : ctf_dvdef_ref * item = ctfc->ctfc_ignore_vars->find_slot (entry, INSERT);
191 : 2 : if (*item == NULL)
192 : 2 : *item = dvd;
193 : : else
194 : : existed = true;
195 : : /* Duplicate variable records not expected to be inserted. */
196 : 2 : gcc_assert (!existed);
197 : 2 : }
198 : :
199 : : /* Lookup the dummy CTF variable given the DWARF die for the non-defining
200 : : decl to be ignored. */
201 : :
202 : : bool
203 : 510 : ctf_dvd_ignore_lookup (const ctf_container_ref ctfc, dw_die_ref die)
204 : : {
205 : 510 : ctf_dvdef_t entry;
206 : 510 : entry.dvd_key = die;
207 : :
208 : 510 : ctf_dvdef_ref * slot = ctfc->ctfc_ignore_vars->find_slot (&entry, NO_INSERT);
209 : :
210 : 510 : if (slot)
211 : 2 : return true;
212 : :
213 : : return false;
214 : : }
215 : :
216 : : /* Append member definition to the list. Member list is a singly-linked list
217 : : with list start pointing to the head. */
218 : :
219 : : static void
220 : 245 : ctf_dmd_list_append (ctf_dmdef_t ** dmd, ctf_dmdef_t * elem)
221 : : {
222 : 245 : ctf_dmdef_t * tail = (dmd && *dmd) ? *dmd : NULL;
223 : : if (tail)
224 : : {
225 : 216 : while (tail->dmd_next)
226 : : tail = tail->dmd_next;
227 : :
228 : 136 : tail->dmd_next = elem;
229 : : }
230 : : else
231 : 109 : *dmd = elem;
232 : :
233 : 245 : elem->dmd_next = NULL;
234 : 245 : }
235 : :
236 : : /* Append function argument to the list. Member list is a singly-linked list
237 : : with list start pointing to the head. */
238 : :
239 : : static void
240 : 127 : ctf_farg_list_append (ctf_func_arg_t ** farg, ctf_func_arg_t * elem)
241 : : {
242 : 127 : ctf_func_arg_t * tail = (farg && *farg) ? *farg : NULL;
243 : : if (tail)
244 : : {
245 : 49 : while (tail->farg_next)
246 : : tail = tail->farg_next;
247 : :
248 : 42 : tail->farg_next = elem;
249 : : }
250 : : else
251 : 85 : *farg = elem;
252 : :
253 : 127 : elem->farg_next = NULL;
254 : 127 : }
255 : :
256 : : /* Append str to the CTF string table. */
257 : :
258 : : static void
259 : 2742 : ctfc_strtable_append_str (ctf_strtable_t * str_table, const char * str)
260 : : {
261 : 2742 : ctf_string_t * ctf_string = ggc_cleared_alloc<ctf_string_t> ();
262 : : /* Keep a reference to the input STR. */
263 : 2742 : ctf_string->cts_str = str;
264 : 2742 : ctf_string->cts_next = NULL;
265 : :
266 : 2742 : if (!str_table->ctstab_head)
267 : 678 : str_table->ctstab_head = ctf_string;
268 : :
269 : : /* Append to the end of the list. */
270 : 2742 : if (str_table->ctstab_tail)
271 : 2064 : str_table->ctstab_tail->cts_next = ctf_string;
272 : :
273 : 2742 : str_table->ctstab_tail = ctf_string;
274 : 2742 : }
275 : :
276 : : /* Wrapper function to add str to the CTF string table. No de-duplication of
277 : : CTF strings is done by the compiler. */
278 : :
279 : : static const char *
280 : 3086 : ctfc_strtable_add_str (ctf_strtable_t * str_table, const char * name,
281 : : uint32_t * name_offset)
282 : : {
283 : 3086 : size_t len;
284 : 3086 : char * ctf_string;
285 : : /* Return value is the offset to the string in the string table. */
286 : 3086 : uint32_t str_offset = str_table->ctstab_len;
287 : :
288 : : /* Add empty string only once at the beginning of the string table. Also, do
289 : : not add null strings, return the offset to the empty string for them. */
290 : 3086 : if ((!name || (name != NULL && !strcmp (name, ""))) && str_offset)
291 : : {
292 : 344 : ctf_string = CONST_CAST (char *, str_table->ctstab_estr);
293 : 344 : str_offset = 0;
294 : : }
295 : : else
296 : : {
297 : 678 : gcc_assert (name);
298 : : /* Add null-terminated strings to the string table. */
299 : 2742 : len = strlen (name) + 1;
300 : 2742 : ctf_string = CONST_CAST (char *, ggc_strdup (name));
301 : :
302 : 2742 : ctfc_strtable_append_str (str_table, ctf_string);
303 : : /* Add string to the string table. Keep number of strings updated. */
304 : 2742 : str_table->ctstab_num++;
305 : : /* Keep the number of bytes contained in the string table updated. */
306 : 2742 : str_table->ctstab_len += len;
307 : : }
308 : :
309 : 3086 : *name_offset = str_offset;
310 : :
311 : 3086 : return (const char *) ctf_string;
312 : :
313 : : }
314 : :
315 : : /* Add string to the appropriate string table in the CTF container. */
316 : :
317 : : const char *
318 : 2408 : ctf_add_string (ctf_container_ref ctfc, const char * name,
319 : : uint32_t * name_offset, int aux_str = CTF_STRTAB)
320 : : {
321 : : /* Get the CTF string table or the CTF auxilliary string table,
322 : : as applicable. */
323 : 2408 : ctf_strtable_t *str_table = ctfc_get_strtab (ctfc, aux_str);
324 : 2408 : return ctfc_strtable_add_str (str_table, name, name_offset);
325 : : }
326 : :
327 : : /* Add the compilation unit (CU) name string to the CTF string table. The
328 : : CU name has a prepended pwd string if it is a relative path. Also set the
329 : : CU name offset in the CTF container. */
330 : :
331 : : void
332 : 339 : ctf_add_cuname (ctf_container_ref ctfc, const char * filename)
333 : : {
334 : 339 : char * cuname = NULL;
335 : :
336 : : /* (filename at this point of compilation cannot be null). */
337 : :
338 : 339 : if (!IS_DIR_SEPARATOR (filename[0]))
339 : : {
340 : : /* Filename is a relative path. */
341 : 0 : const char * cu_pwd = get_src_pwd ();
342 : 0 : const int cu_pwd_len = strlen (cu_pwd);
343 : :
344 : : /* Add a DIR_SEPARATOR char before the filename. */
345 : 0 : const int len = cu_pwd_len + 2 + strlen (filename);
346 : :
347 : 0 : cuname = (char *) ggc_alloc_atomic (len);
348 : 0 : memset (cuname, 0, len);
349 : :
350 : 0 : strcpy (cuname, cu_pwd);
351 : 0 : cuname[cu_pwd_len] = DIR_SEPARATOR;
352 : 0 : cuname[cu_pwd_len+1] = 0;
353 : 0 : strcat (cuname, filename);
354 : : }
355 : : else
356 : : /* Filename is an absolute path. */
357 : 339 : cuname = CONST_CAST (char *, ggc_strdup (filename));
358 : :
359 : 339 : ctf_add_string (ctfc, cuname, &(ctfc->ctfc_cuname_offset));
360 : : /* Add 1 as CTF strings in the CTF string table are null-terminated
361 : : strings. */
362 : 339 : ctfc->ctfc_strlen += strlen (cuname) + 1;
363 : :
364 : : /* Mark cuname for garbage collection. */
365 : 339 : cuname = NULL;
366 : 339 : }
367 : :
368 : : /* Functions to create CTF types.
369 : :
370 : : These functions perform the task of adding CTF types to the CTF container.
371 : : No de-duplication is done by them; the onus is on the calling function to do
372 : : so. The caller must first do a lookup via ctf_dtd_lookup or
373 : : ctf_dvd_lookup, as applicable, to ascertain that the CTF type or the CTF
374 : : variable respectively does not already exist, and then add it. */
375 : :
376 : : static ctf_id_t
377 : 1400 : ctf_add_generic (ctf_container_ref ctfc, uint32_t flag, const char * name,
378 : : ctf_dtdef_ref * rp, dw_die_ref die)
379 : : {
380 : 1400 : ctf_dtdef_ref dtd;
381 : 1400 : ctf_id_t type;
382 : :
383 : 1400 : gcc_assert (flag == CTF_ADD_NONROOT || flag == CTF_ADD_ROOT);
384 : :
385 : 1400 : dtd = ggc_cleared_alloc<ctf_dtdef_t> ();
386 : :
387 : 1400 : type = ctfc->ctfc_nextid++;
388 : 1400 : gcc_assert (type < CTF_MAX_TYPE); /* CTF type ID overflow. */
389 : :
390 : : /* Buffer the strings in the CTF string table. */
391 : 1400 : dtd->dtd_name = ctf_add_string (ctfc, name, &(dtd->dtd_data.ctti_name));
392 : 1400 : dtd->dtd_type = type;
393 : 1400 : dtd->dtd_key = die;
394 : :
395 : 1400 : if ((name != NULL) && strcmp (name, ""))
396 : 1084 : ctfc->ctfc_strlen += strlen (name) + 1;
397 : :
398 : 1400 : ctf_dtd_insert (ctfc, dtd);
399 : :
400 : 1400 : *rp = dtd;
401 : 1400 : return type;
402 : : }
403 : :
404 : : static ctf_id_t
405 : 571 : ctf_add_encoded (ctf_container_ref ctfc, uint32_t flag, const char * name,
406 : : const ctf_encoding_t * ep, uint32_t kind, dw_die_ref die)
407 : : {
408 : 571 : ctf_dtdef_ref dtd;
409 : 571 : ctf_id_t type;
410 : :
411 : 571 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
412 : :
413 : 571 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (kind, flag, 0);
414 : :
415 : 571 : uint32_t roundup_nbytes = (ROUND_UP (ep->cte_bits, BITS_PER_UNIT)
416 : : / BITS_PER_UNIT);
417 : :
418 : : /* FIXME, stay close to what libctf does. But by getting next power of two,
419 : : aren't we conveying less precise information. E.g. floating point mode
420 : : XF has a size of 12 bytes. */
421 : 1009 : dtd->dtd_data.ctti_size = roundup_nbytes ? (1 << ceil_log2 (roundup_nbytes))
422 : : : roundup_nbytes;
423 : 571 : dtd->dtd_u.dtu_enc = *ep;
424 : :
425 : 571 : ctfc->ctfc_num_stypes++;
426 : :
427 : 571 : return type;
428 : : }
429 : :
430 : : ctf_id_t
431 : 176 : ctf_add_reftype (ctf_container_ref ctfc, uint32_t flag, ctf_id_t ref,
432 : : uint32_t kind, dw_die_ref die)
433 : : {
434 : 176 : ctf_dtdef_ref dtd;
435 : 176 : ctf_id_t type;
436 : :
437 : 176 : gcc_assert (ref <= CTF_MAX_TYPE);
438 : :
439 : 176 : type = ctf_add_generic (ctfc, flag, NULL, &dtd, die);
440 : 176 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (kind, flag, 0);
441 : : /* Caller of this API must guarantee that a CTF type with id = ref already
442 : : exists. This will also be validated for us at link-time. */
443 : 176 : dtd->dtd_data.ctti_type = (uint32_t) ref;
444 : :
445 : 176 : ctfc->ctfc_num_stypes++;
446 : :
447 : 176 : return type;
448 : : }
449 : :
450 : : ctf_id_t
451 : 10 : ctf_add_forward (ctf_container_ref ctfc, uint32_t flag, const char * name,
452 : : uint32_t kind, dw_die_ref die)
453 : : {
454 : 10 : ctf_dtdef_ref dtd;
455 : 10 : ctf_id_t type = 0;
456 : :
457 : 10 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
458 : :
459 : 10 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_FORWARD, flag, 0);
460 : 10 : dtd->dtd_data.ctti_type = kind;
461 : :
462 : 10 : ctfc->ctfc_num_stypes++;
463 : :
464 : 10 : return type;
465 : : }
466 : :
467 : : ctf_id_t
468 : 55 : ctf_add_typedef (ctf_container_ref ctfc, uint32_t flag, const char * name,
469 : : ctf_id_t ref, dw_die_ref die)
470 : : {
471 : 55 : ctf_dtdef_ref dtd;
472 : 55 : ctf_id_t type;
473 : :
474 : 55 : gcc_assert (ref <= CTF_MAX_TYPE);
475 : : /* Nameless Typedefs are not expected. */
476 : 55 : gcc_assert ((name != NULL) && strcmp (name, ""));
477 : :
478 : 55 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
479 : 55 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_TYPEDEF, flag, 0);
480 : : /* Caller of this API must guarantee that a CTF type with id = ref already
481 : : exists. This will also be validated for us at link-time. */
482 : 55 : dtd->dtd_data.ctti_type = (uint32_t) ref;
483 : :
484 : 55 : gcc_assert (dtd->dtd_type != dtd->dtd_data.ctti_type);
485 : :
486 : 55 : ctfc->ctfc_num_stypes++;
487 : :
488 : 55 : return type;
489 : : }
490 : :
491 : : ctf_id_t
492 : 22 : ctf_add_slice (ctf_container_ref ctfc, uint32_t flag, ctf_id_t ref,
493 : : uint32_t bit_offset, uint32_t bit_size, dw_die_ref die)
494 : : {
495 : 22 : ctf_dtdef_ref dtd;
496 : 22 : ctf_id_t type;
497 : 22 : uint32_t roundup_nbytes;
498 : :
499 : 22 : gcc_assert ((bit_size <= 255) && (bit_offset <= 255));
500 : :
501 : 22 : gcc_assert (ref <= CTF_MAX_TYPE);
502 : :
503 : 22 : type = ctf_add_generic (ctfc, flag, NULL, &dtd, die);
504 : :
505 : 22 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_SLICE, flag, 0);
506 : :
507 : 22 : roundup_nbytes = (ROUND_UP (bit_size, BITS_PER_UNIT) / BITS_PER_UNIT);
508 : : /* FIXME, stay close to what libctf does. But by getting next power of two,
509 : : aren't we conveying less precise information, especially for bitfields.
510 : : For example, cte_bits = 33, roundup_nbytes = 5, ctti_size = 8 in the
511 : : implementation below. */
512 : 33 : dtd->dtd_data.ctti_size = roundup_nbytes ? (1 << ceil_log2 (roundup_nbytes))
513 : : : 0;
514 : :
515 : : /* Caller of this API must guarantee that a CTF type with id = ref already
516 : : exists. This will also be validated for us at link-time. */
517 : 22 : dtd->dtd_u.dtu_slice.cts_type = (uint32_t) ref;
518 : 22 : dtd->dtd_u.dtu_slice.cts_bits = bit_size;
519 : 22 : dtd->dtd_u.dtu_slice.cts_offset = bit_offset;
520 : :
521 : 22 : ctfc->ctfc_num_stypes++;
522 : :
523 : 22 : return type;
524 : : }
525 : :
526 : : ctf_id_t
527 : 34 : ctf_add_float (ctf_container_ref ctfc, uint32_t flag,
528 : : const char * name, const ctf_encoding_t * ep, dw_die_ref die)
529 : : {
530 : 34 : return (ctf_add_encoded (ctfc, flag, name, ep, CTF_K_FLOAT, die));
531 : : }
532 : :
533 : : ctf_id_t
534 : 527 : ctf_add_integer (ctf_container_ref ctfc, uint32_t flag,
535 : : const char * name, const ctf_encoding_t * ep, dw_die_ref die)
536 : : {
537 : 527 : return (ctf_add_encoded (ctfc, flag, name, ep, CTF_K_INTEGER, die));
538 : : }
539 : :
540 : : ctf_id_t
541 : 10 : ctf_add_unknown (ctf_container_ref ctfc, uint32_t flag,
542 : : const char * name, const ctf_encoding_t * ep, dw_die_ref die)
543 : : {
544 : 10 : return (ctf_add_encoded (ctfc, flag, name, ep, CTF_K_UNKNOWN, die));
545 : : }
546 : :
547 : : ctf_id_t
548 : 116 : ctf_add_pointer (ctf_container_ref ctfc, uint32_t flag, ctf_id_t ref,
549 : : dw_die_ref die)
550 : : {
551 : 116 : return (ctf_add_reftype (ctfc, flag, ref, CTF_K_POINTER, die));
552 : : }
553 : :
554 : : ctf_id_t
555 : 87 : ctf_add_array (ctf_container_ref ctfc, uint32_t flag, const ctf_arinfo_t * arp,
556 : : dw_die_ref die)
557 : : {
558 : 87 : ctf_dtdef_ref dtd;
559 : 87 : ctf_id_t type;
560 : :
561 : 87 : gcc_assert (arp);
562 : :
563 : : /* Caller of this API must make sure CTF type for arp->ctr_contents and
564 : : arp->ctr_index are already added. This will also be validated for us at
565 : : link-time. */
566 : :
567 : 87 : type = ctf_add_generic (ctfc, flag, NULL, &dtd, die);
568 : :
569 : 87 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_ARRAY, flag, 0);
570 : 87 : dtd->dtd_data.ctti_size = 0;
571 : 87 : dtd->dtd_u.dtu_arr = *arp;
572 : :
573 : 87 : ctfc->ctfc_num_stypes++;
574 : :
575 : 87 : return type;
576 : : }
577 : :
578 : : ctf_id_t
579 : 14 : ctf_add_enum (ctf_container_ref ctfc, uint32_t flag, const char * name,
580 : : HOST_WIDE_INT size, bool eunsigned, dw_die_ref die)
581 : : {
582 : 14 : ctf_dtdef_ref dtd;
583 : 14 : ctf_id_t type;
584 : :
585 : : /* In the compiler, no need to handle the case of promoting forwards to
586 : : enums. This comment is simply to note a divergence from libctf. */
587 : :
588 : : /* The compiler does, however, update any previously existing forward types
589 : : to non-root. CTF does not allow existence of two root types with the same
590 : : name. */
591 : 14 : ctf_dtdef_ref enum_fwd_type = ctf_dtd_lookup (ctfc, die);
592 : 14 : if (enum_fwd_type)
593 : : {
594 : 0 : enum_fwd_type->dtd_data.ctti_info
595 : 0 : = CTF_TYPE_INFO (CTF_K_FORWARD, CTF_ADD_NONROOT, 0);
596 : : }
597 : :
598 : 14 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
599 : :
600 : 14 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_ENUM, flag, 0);
601 : :
602 : : /* Size in bytes should always fit, of course.
603 : : TBD WARN - warn instead? */
604 : 14 : gcc_assert (size <= CTF_MAX_SIZE);
605 : :
606 : 14 : dtd->dtd_data.ctti_size = size;
607 : 14 : dtd->dtd_enum_unsigned = eunsigned;
608 : :
609 : 14 : ctfc->ctfc_num_stypes++;
610 : :
611 : 14 : return type;
612 : : }
613 : :
614 : : int
615 : 45 : ctf_add_enumerator (ctf_container_ref ctfc, ctf_id_t enid, const char * name,
616 : : HOST_WIDE_INT value, dw_die_ref die)
617 : : {
618 : 45 : ctf_dmdef_t * dmd;
619 : 45 : uint32_t kind, vlen, root;
620 : :
621 : : /* Callers of this API must make sure that CTF_K_ENUM with enid has been
622 : : addded. This will also be validated for us at link-time. */
623 : 45 : ctf_dtdef_ref dtd = ctf_dtd_lookup (ctfc, die);
624 : 45 : gcc_assert (dtd);
625 : 45 : gcc_assert (dtd->dtd_type == enid);
626 : 45 : gcc_assert (name);
627 : :
628 : 45 : kind = CTF_V2_INFO_KIND (dtd->dtd_data.ctti_info);
629 : 45 : root = CTF_V2_INFO_ISROOT (dtd->dtd_data.ctti_info);
630 : 45 : vlen = CTF_V2_INFO_VLEN (dtd->dtd_data.ctti_info);
631 : :
632 : 45 : gcc_assert (kind == CTF_K_ENUM && vlen < CTF_MAX_VLEN);
633 : :
634 : : /* Enum value is of type HOST_WIDE_INT in the compiler, CTF enumerators
635 : : values in ctf_enum_t is limited to int32_t, BTF supports signed and
636 : : unsigned enumerators values of 32 and 64 bits, for both debug formats
637 : : we use ctf_dmdef_t.dmd_value entry of HOST_WIDE_INT type. So check
638 : : CTF bounds and skip adding this enum value if out of bounds. */
639 : 45 : if (!btf_debuginfo_p() && ((value > INT_MAX) || (value < INT_MIN)))
640 : : {
641 : : /* FIXME - Note this TBD_CTF_REPRESENTATION_LIMIT. */
642 : : return (1);
643 : : }
644 : :
645 : 43 : dmd = ggc_cleared_alloc<ctf_dmdef_t> ();
646 : :
647 : : /* Buffer the strings in the CTF string table. */
648 : 43 : dmd->dmd_name = ctf_add_string (ctfc, name, &(dmd->dmd_name_offset));
649 : 43 : dmd->dmd_type = CTF_NULL_TYPEID;
650 : 43 : dmd->dmd_offset = 0;
651 : :
652 : 43 : dmd->dmd_value = value;
653 : :
654 : 43 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (kind, root, vlen + 1);
655 : 43 : ctf_dmd_list_append (&dtd->dtd_u.dtu_members, dmd);
656 : :
657 : 43 : if ((name != NULL) && strcmp (name, ""))
658 : 43 : ctfc->ctfc_strlen += strlen (name) + 1;
659 : :
660 : : return (0);
661 : : }
662 : :
663 : : int
664 : 202 : ctf_add_member_offset (ctf_container_ref ctfc, dw_die_ref sou,
665 : : const char * name, ctf_id_t type,
666 : : uint64_t bit_offset)
667 : : {
668 : 202 : ctf_dtdef_ref dtd = ctf_dtd_lookup (ctfc, sou);
669 : 202 : ctf_dmdef_t * dmd;
670 : :
671 : 202 : uint32_t kind, vlen, root;
672 : :
673 : : /* The type of the member being added must already exist. */
674 : 202 : gcc_assert (dtd);
675 : :
676 : 202 : kind = CTF_V2_INFO_KIND (dtd->dtd_data.ctti_info);
677 : 202 : root = CTF_V2_INFO_ISROOT (dtd->dtd_data.ctti_info);
678 : 202 : vlen = CTF_V2_INFO_VLEN (dtd->dtd_data.ctti_info);
679 : :
680 : 202 : gcc_assert (kind == CTF_K_STRUCT || kind == CTF_K_UNION);
681 : 202 : gcc_assert (vlen < CTF_MAX_VLEN);
682 : :
683 : 202 : dmd = ggc_cleared_alloc<ctf_dmdef_t> ();
684 : :
685 : : /* Buffer the strings in the CTF string table. */
686 : 202 : dmd->dmd_name = ctf_add_string (ctfc, name, &(dmd->dmd_name_offset));
687 : 202 : dmd->dmd_type = type;
688 : 202 : dmd->dmd_value = -1;
689 : :
690 : 202 : if (kind == CTF_K_STRUCT && vlen != 0)
691 : 92 : dmd->dmd_offset = bit_offset;
692 : : else
693 : 110 : dmd->dmd_offset = 0;
694 : :
695 : 202 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (kind, root, vlen + 1);
696 : 202 : ctf_dmd_list_append (&dtd->dtd_u.dtu_members, dmd);
697 : :
698 : 202 : if ((name != NULL) && strcmp (name, ""))
699 : 200 : ctfc->ctfc_strlen += strlen (name) + 1;
700 : :
701 : 202 : return 0;
702 : : }
703 : :
704 : : int
705 : 255 : ctf_add_variable (ctf_container_ref ctfc, const char * name, ctf_id_t ref,
706 : : dw_die_ref die, unsigned int external_vis,
707 : : dw_die_ref die_var_decl)
708 : : {
709 : 255 : ctf_dvdef_ref dvd, dvd_ignore;
710 : :
711 : 255 : gcc_assert (name);
712 : :
713 : 255 : if (name != NULL)
714 : : {
715 : 255 : dvd = ggc_cleared_alloc<ctf_dvdef_t> ();
716 : 255 : dvd->dvd_key = die;
717 : : /* Buffer the strings in the CTF string table. */
718 : 255 : dvd->dvd_name = ctf_add_string (ctfc, name, &(dvd->dvd_name_offset));
719 : 255 : dvd->dvd_visibility = external_vis;
720 : 255 : dvd->dvd_type = ref;
721 : :
722 : : /* If DW_AT_specification attribute exists, keep track of it as this is
723 : : the non-defining declaration corresponding to the variable. We will
724 : : skip emitting CTF variable for such incomplete, non-defining
725 : : declarations.
726 : : There could be some non-defining declarations, however, for which a
727 : : defining declaration does not show up in the same CU. For such
728 : : cases, the compiler continues to emit CTF variable record as
729 : : usual. */
730 : 255 : if (die_var_decl)
731 : : {
732 : 2 : dvd_ignore = ggc_cleared_alloc<ctf_dvdef_t> ();
733 : 2 : dvd_ignore->dvd_key = die_var_decl;
734 : : /* It's alright to leave other fields as zero. No valid CTF
735 : : variable will be added for these DW_TAG_variable DIEs. */
736 : 2 : ctf_dvd_ignore_insert (ctfc, dvd_ignore);
737 : : }
738 : :
739 : 255 : ctf_dvd_insert (ctfc, dvd);
740 : :
741 : 255 : if (strcmp (name, ""))
742 : 255 : ctfc->ctfc_strlen += strlen (name) + 1;
743 : : }
744 : :
745 : 255 : return 0;
746 : : }
747 : :
748 : : int
749 : 127 : ctf_add_function_arg (ctf_container_ref ctfc, dw_die_ref func,
750 : : const char * name, ctf_id_t type)
751 : : {
752 : 127 : ctf_dtdef_ref dtd = ctf_dtd_lookup (ctfc, func);
753 : 127 : ctf_func_arg_t * farg;
754 : 127 : uint32_t vlen;
755 : :
756 : : /* The function to which argument is being added must already exist. */
757 : 127 : gcc_assert (dtd);
758 : : /* The number of args must have been non-zero. */
759 : 127 : vlen = CTF_V2_INFO_VLEN (dtd->dtd_data.ctti_info);
760 : 127 : gcc_assert (vlen);
761 : :
762 : 127 : farg = ggc_cleared_alloc<ctf_func_arg_t> ();
763 : :
764 : : /* Buffer the strings in the auxilliary string table. CTF V3 format does not
765 : : require function argument names. Use auxilliary string table to keep
766 : : these strings to avoid unnecessary bloat in CTF section in CTF V3. */
767 : 127 : farg->farg_name = ctf_add_string (ctfc, name, &(farg->farg_name_offset),
768 : : CTF_AUX_STRTAB);
769 : 127 : farg->farg_type = type;
770 : :
771 : 127 : ctf_farg_list_append (&dtd->dtd_u.dtu_argv, farg);
772 : :
773 : : /* For aux_str, keep ctfc_aux_strlen updated for debugging. */
774 : 127 : if ((name != NULL) && strcmp (name, ""))
775 : 101 : ctfc->ctfc_aux_strlen += strlen (name) + 1;
776 : :
777 : 127 : return 0;
778 : : }
779 : :
780 : : ctf_id_t
781 : 368 : ctf_add_function (ctf_container_ref ctfc, uint32_t flag, const char * name,
782 : : const ctf_funcinfo_t * ctc, dw_die_ref die,
783 : : bool from_global_func, int linkage)
784 : : {
785 : 368 : ctf_dtdef_ref dtd;
786 : 368 : ctf_id_t type;
787 : 368 : uint32_t vlen;
788 : :
789 : 368 : gcc_assert (ctc);
790 : :
791 : 368 : vlen = ctc->ctc_argc;
792 : 368 : gcc_assert (vlen <= CTF_MAX_VLEN);
793 : :
794 : 368 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
795 : :
796 : 368 : dtd->from_global_func = from_global_func;
797 : 368 : dtd->linkage = linkage;
798 : 368 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (CTF_K_FUNCTION, flag, vlen);
799 : : /* Caller must make sure CTF types for ctc->ctc_return are already added. */
800 : 368 : dtd->dtd_data.ctti_type = (uint32_t) ctc->ctc_return;
801 : : /* Caller must make sure CTF types for function arguments are already added
802 : : via ctf_add_function_arg () API. */
803 : :
804 : 368 : ctfc->ctfc_num_stypes++;
805 : :
806 : 368 : return type;
807 : : }
808 : :
809 : : ctf_id_t
810 : 97 : ctf_add_sou (ctf_container_ref ctfc, uint32_t flag, const char * name,
811 : : uint32_t kind, size_t size, dw_die_ref die)
812 : : {
813 : 97 : ctf_dtdef_ref dtd;
814 : 97 : ctf_id_t type = 0;
815 : :
816 : 97 : gcc_assert ((kind == CTF_K_STRUCT) || (kind == CTF_K_UNION));
817 : :
818 : : /* In the compiler, no need to handle the case of promoting forwards to
819 : : structs. This comment is simply to note a divergence from libctf. */
820 : :
821 : : /* The compiler does, however, update any previously existing forward types
822 : : to non-root. CTF does not allow existence of two root types with the same
823 : : name. */
824 : 97 : ctf_dtdef_ref sou_fwd_type = ctf_dtd_lookup (ctfc, die);
825 : 97 : if (sou_fwd_type)
826 : : {
827 : 0 : sou_fwd_type->dtd_data.ctti_info
828 : 0 : = CTF_TYPE_INFO (CTF_K_FORWARD, CTF_ADD_NONROOT, 0);
829 : : }
830 : :
831 : 97 : type = ctf_add_generic (ctfc, flag, name, &dtd, die);
832 : :
833 : 97 : dtd->dtd_data.ctti_info = CTF_TYPE_INFO (kind, flag, 0);
834 : :
835 : 97 : if (size > CTF_MAX_SIZE)
836 : : {
837 : 0 : dtd->dtd_data.ctti_size = CTF_LSIZE_SENT;
838 : 0 : dtd->dtd_data.ctti_lsizehi = CTF_SIZE_TO_LSIZE_HI (size);
839 : 0 : dtd->dtd_data.ctti_lsizelo = CTF_SIZE_TO_LSIZE_LO (size);
840 : 0 : ctfc->ctfc_num_types++;
841 : : }
842 : : else
843 : : {
844 : 97 : dtd->dtd_data.ctti_size = (uint32_t) size;
845 : 97 : ctfc->ctfc_num_stypes++;
846 : : }
847 : :
848 : 97 : return type;
849 : : }
850 : :
851 : : /* Given a TREE_TYPE node, return the CTF type ID for that type. */
852 : :
853 : : ctf_id_t
854 : 0 : ctf_lookup_tree_type (ctf_container_ref ctfc, const tree type)
855 : : {
856 : 0 : dw_die_ref die = lookup_type_die (type);
857 : 0 : if (die == NULL)
858 : : return CTF_NULL_TYPEID;
859 : :
860 : 0 : ctf_dtdef_ref dtd = ctf_dtd_lookup (ctfc, die);
861 : 0 : if (dtd == NULL)
862 : : return CTF_NULL_TYPEID;
863 : :
864 : 0 : return dtd->dtd_type;
865 : : }
866 : :
867 : : /* Check if CTF for TYPE has already been generated. Mainstay for
868 : : de-duplication. If CTF type already exists, returns TRUE and updates
869 : : the TYPE_ID for the caller. */
870 : :
871 : : bool
872 : 3947 : ctf_type_exists (ctf_container_ref ctfc, dw_die_ref type,
873 : : ctf_id_t * type_id)
874 : : {
875 : 3947 : bool exists = false;
876 : 3947 : ctf_dtdef_ref ctf_type_seen = ctf_dtd_lookup (ctfc, type);
877 : :
878 : 3947 : if (ctf_type_seen)
879 : : {
880 : 1275 : exists = true;
881 : : /* CTF type for this type exists. */
882 : 1275 : *type_id = ctf_type_seen->dtd_type;
883 : : }
884 : :
885 : 3947 : return exists;
886 : : }
887 : :
888 : : /* Location information for CTF Types and CTF Variables. CTF section does not
889 : : emit location information; at this time, location information is needed for
890 : : BTF CO-RE use-cases. */
891 : :
892 : : int
893 : 0 : ctfc_get_dtd_srcloc (ctf_dtdef_ref dtd, ctf_srcloc_ref loc)
894 : : {
895 : 0 : loc->ctsloc_file = ctf_get_die_loc_file (dtd->dtd_key);
896 : 0 : loc->ctsloc_line = ctf_get_die_loc_line (dtd->dtd_key);
897 : 0 : loc->ctsloc_col = ctf_get_die_loc_col (dtd->dtd_key);
898 : :
899 : 0 : if (loc->ctsloc_file == NULL)
900 : 0 : return 1;
901 : :
902 : : return 0;
903 : : }
904 : :
905 : : int
906 : 0 : ctfc_get_dvd_srcloc (ctf_dvdef_ref dvd, ctf_srcloc_ref loc)
907 : : {
908 : 0 : loc->ctsloc_file = ctf_get_die_loc_file (dvd->dvd_key);
909 : 0 : loc->ctsloc_line = ctf_get_die_loc_line (dvd->dvd_key);
910 : 0 : loc->ctsloc_col = ctf_get_die_loc_col (dvd->dvd_key);
911 : :
912 : 0 : if (loc->ctsloc_file == NULL)
913 : 0 : return 1;
914 : :
915 : : return 0;
916 : : }
917 : :
918 : : /* CTF container setup and teardown routines. */
919 : :
920 : : /* Initialize the CTF string table.
921 : : The first entry in the CTF string table (empty string) is added. */
922 : :
923 : : static void
924 : 678 : init_ctf_strtable (ctf_strtable_t * strtab)
925 : : {
926 : 678 : strtab->ctstab_head = NULL;
927 : 678 : strtab->ctstab_tail = NULL;
928 : 678 : strtab->ctstab_num = 0;
929 : 678 : strtab->ctstab_len = 0;
930 : :
931 : : /* The first entry in the CTF string table is an empty string. E.g., CTF
932 : : type records with no name (like CTF_K_CONST, CTF_K_VOLATILE etc) point to
933 : : this string. */
934 : 678 : uint32_t estr_offset = 0;
935 : 678 : strtab->ctstab_estr = ctfc_strtable_add_str (strtab, "", &estr_offset);
936 : 678 : }
937 : :
938 : : /* Initialize the string tables in the CTF container. */
939 : :
940 : : static void
941 : 339 : init_ctf_string_table (ctf_container_ref ctfc)
942 : : {
943 : 339 : init_ctf_strtable (&ctfc->ctfc_strtable);
944 : 339 : ctfc->ctfc_strlen++;
945 : :
946 : 339 : init_ctf_strtable (&ctfc->ctfc_aux_strtable);
947 : 339 : ctfc->ctfc_aux_strlen++;
948 : 339 : }
949 : :
950 : : /* Allocate a new CTF container with the desired flags. */
951 : :
952 : : static inline ctf_container_ref
953 : 339 : new_ctf_container (void)
954 : : {
955 : 339 : tu_ctfc = ggc_cleared_alloc<ctf_container_t> ();
956 : 339 : tu_ctfc->ctfc_types
957 : 339 : = hash_table<ctfc_dtd_hasher>::create_ggc (100);
958 : 339 : tu_ctfc->ctfc_vars
959 : 339 : = hash_table<ctfc_dvd_hasher>::create_ggc (100);
960 : 339 : tu_ctfc->ctfc_ignore_vars
961 : 339 : = hash_table<ctfc_dvd_hasher>::create_ggc (10);
962 : :
963 : 339 : return tu_ctfc;
964 : : }
965 : :
966 : : /* Initialize a CTF container per translation unit. */
967 : :
968 : : static void
969 : 339 : init_ctf_container (void)
970 : : {
971 : 339 : tu_ctfc = new_ctf_container ();
972 : :
973 : 339 : tu_ctfc->ctfc_magic = CTF_MAGIC;
974 : 339 : tu_ctfc->ctfc_version = CTF_VERSION;
975 : 339 : tu_ctfc->ctfc_flags = CTF_F_NEWFUNCINFO;
976 : 339 : tu_ctfc->ctfc_nextid = CTF_INIT_TYPEID;
977 : :
978 : 339 : init_ctf_string_table (tu_ctfc);
979 : 339 : }
980 : :
981 : : void
982 : 678 : ctfc_delete_strtab (ctf_strtable_t * strtab)
983 : : {
984 : 678 : ctf_string_t * str = NULL;
985 : 678 : ctf_string_t * next_str = NULL;
986 : :
987 : 678 : str = strtab->ctstab_head;
988 : 678 : next_str = str;
989 : 3420 : while (next_str != NULL)
990 : : {
991 : 2742 : next_str = str->cts_next;
992 : 2742 : ggc_free (str);
993 : 2742 : str = next_str;
994 : : }
995 : :
996 : 678 : strtab->ctstab_head = NULL;
997 : 678 : strtab->ctstab_tail = NULL;
998 : 678 : strtab->ctstab_estr = NULL;
999 : 678 : }
1000 : :
1001 : : /* Delete the CTF container's resources. */
1002 : :
1003 : : void
1004 : 339 : ctfc_delete_container (ctf_container_ref ctfc)
1005 : : {
1006 : 339 : if (ctfc)
1007 : : {
1008 : 339 : ctfc->ctfc_types->empty ();
1009 : 339 : ctfc->ctfc_types = NULL;
1010 : :
1011 : 339 : ctfc->ctfc_vars->empty ();
1012 : 339 : ctfc->ctfc_types = NULL;
1013 : :
1014 : 339 : ctfc->ctfc_ignore_vars->empty ();
1015 : 339 : ctfc->ctfc_ignore_vars = NULL;
1016 : :
1017 : 339 : ctfc_delete_strtab (&ctfc->ctfc_strtable);
1018 : 339 : ctfc_delete_strtab (&ctfc->ctfc_aux_strtable);
1019 : 339 : if (ctfc->ctfc_vars_list)
1020 : : {
1021 : 107 : ggc_free (ctfc->ctfc_vars_list);
1022 : 107 : ctfc->ctfc_vars_list = NULL;
1023 : : }
1024 : 339 : if (ctfc->ctfc_types_list)
1025 : : {
1026 : 339 : ggc_free (ctfc->ctfc_types_list);
1027 : 339 : ctfc->ctfc_types_list = NULL;
1028 : : }
1029 : 339 : if (ctfc->ctfc_gfuncs_list)
1030 : : {
1031 : 206 : ggc_free (ctfc->ctfc_gfuncs_list);
1032 : 206 : ctfc->ctfc_gfuncs_list = NULL;
1033 : : }
1034 : 339 : if (ctfc->ctfc_gobjts_list)
1035 : : {
1036 : 78 : ggc_free (ctfc->ctfc_gobjts_list);
1037 : 78 : ctfc->ctfc_gobjts_list = NULL;
1038 : : }
1039 : :
1040 : 339 : ctfc= NULL;
1041 : : }
1042 : 339 : }
1043 : :
1044 : : /* CTF routines interfacing to the compiler. */
1045 : :
1046 : : void
1047 : 339 : ctf_init (void)
1048 : : {
1049 : 339 : init_ctf_container ();
1050 : 339 : }
|