1 /* $NetBSD: libdwarf_loc.c,v 1.4 2022/05/01 17:20:47 jkoshy Exp $ */
2
3 /*-
4 * Copyright (c) 2007 John Birrell (jb@freebsd.org)
5 * Copyright (c) 2014 Kai Wang
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
28 */
29
30 #include "_libdwarf.h"
31
32 __RCSID("$NetBSD: libdwarf_loc.c,v 1.4 2022/05/01 17:20:47 jkoshy Exp $");
33 ELFTC_VCSID("Id: libdwarf_loc.c 3070 2014-06-23 03:08:33Z kaiwang27");
34
35 /*
36 * Given an array of bytes of length 'len' representing a
37 * DWARF expression, compute the number of operations based
38 * on there being one byte describing the operation and
39 * zero or more bytes of operands as defined in the standard
40 * for each operation type. Also, if lbuf is non-null, store
41 * the opcode and oprand in it.
42 */
43 static int
_dwarf_loc_fill_loc(Dwarf_Debug dbg,Dwarf_Locdesc * lbuf,uint8_t pointer_size,uint8_t offset_size,uint8_t version,uint8_t * p,int len)44 _dwarf_loc_fill_loc(Dwarf_Debug dbg, Dwarf_Locdesc *lbuf, uint8_t pointer_size,
45 uint8_t offset_size, uint8_t version, uint8_t *p, int len)
46 {
47 int count;
48 uint64_t operand1;
49 uint64_t operand2;
50 uint8_t *ps, *pe, s;
51
52 count = 0;
53 ps = p;
54 pe = p + len;
55
56 /*
57 * Process each byte. If an error occurs, then the
58 * count will be set to -1.
59 */
60 while (p < pe) {
61
62 operand1 = 0;
63 operand2 = 0;
64
65 if (lbuf != NULL) {
66 lbuf->ld_s[count].lr_atom = *p;
67 lbuf->ld_s[count].lr_offset = p - ps;
68 }
69
70 switch (*p++) {
71 /* Operations with no operands. */
72 case DW_OP_deref:
73 case DW_OP_reg0:
74 case DW_OP_reg1:
75 case DW_OP_reg2:
76 case DW_OP_reg3:
77 case DW_OP_reg4:
78 case DW_OP_reg5:
79 case DW_OP_reg6:
80 case DW_OP_reg7:
81 case DW_OP_reg8:
82 case DW_OP_reg9:
83 case DW_OP_reg10:
84 case DW_OP_reg11:
85 case DW_OP_reg12:
86 case DW_OP_reg13:
87 case DW_OP_reg14:
88 case DW_OP_reg15:
89 case DW_OP_reg16:
90 case DW_OP_reg17:
91 case DW_OP_reg18:
92 case DW_OP_reg19:
93 case DW_OP_reg20:
94 case DW_OP_reg21:
95 case DW_OP_reg22:
96 case DW_OP_reg23:
97 case DW_OP_reg24:
98 case DW_OP_reg25:
99 case DW_OP_reg26:
100 case DW_OP_reg27:
101 case DW_OP_reg28:
102 case DW_OP_reg29:
103 case DW_OP_reg30:
104 case DW_OP_reg31:
105
106 case DW_OP_lit0:
107 case DW_OP_lit1:
108 case DW_OP_lit2:
109 case DW_OP_lit3:
110 case DW_OP_lit4:
111 case DW_OP_lit5:
112 case DW_OP_lit6:
113 case DW_OP_lit7:
114 case DW_OP_lit8:
115 case DW_OP_lit9:
116 case DW_OP_lit10:
117 case DW_OP_lit11:
118 case DW_OP_lit12:
119 case DW_OP_lit13:
120 case DW_OP_lit14:
121 case DW_OP_lit15:
122 case DW_OP_lit16:
123 case DW_OP_lit17:
124 case DW_OP_lit18:
125 case DW_OP_lit19:
126 case DW_OP_lit20:
127 case DW_OP_lit21:
128 case DW_OP_lit22:
129 case DW_OP_lit23:
130 case DW_OP_lit24:
131 case DW_OP_lit25:
132 case DW_OP_lit26:
133 case DW_OP_lit27:
134 case DW_OP_lit28:
135 case DW_OP_lit29:
136 case DW_OP_lit30:
137 case DW_OP_lit31:
138
139 case DW_OP_dup:
140 case DW_OP_drop:
141
142 case DW_OP_over:
143
144 case DW_OP_swap:
145 case DW_OP_rot:
146 case DW_OP_xderef:
147
148 case DW_OP_abs:
149 case DW_OP_and:
150 case DW_OP_div:
151 case DW_OP_minus:
152 case DW_OP_mod:
153 case DW_OP_mul:
154 case DW_OP_neg:
155 case DW_OP_not:
156 case DW_OP_or:
157 case DW_OP_plus:
158
159 case DW_OP_shl:
160 case DW_OP_shr:
161 case DW_OP_shra:
162 case DW_OP_xor:
163
164 case DW_OP_eq:
165 case DW_OP_ge:
166 case DW_OP_gt:
167 case DW_OP_le:
168 case DW_OP_lt:
169 case DW_OP_ne:
170
171 case DW_OP_nop:
172 case DW_OP_push_object_address:
173 case DW_OP_form_tls_address:
174 case DW_OP_call_frame_cfa:
175 case DW_OP_stack_value:
176 case DW_OP_GNU_push_tls_address:
177 case DW_OP_GNU_uninit:
178 break;
179
180 /* Operations with 1-byte operands. */
181 case DW_OP_const1u:
182 case DW_OP_pick:
183 case DW_OP_deref_size:
184 case DW_OP_xderef_size:
185 operand1 = *p++;
186 break;
187
188 case DW_OP_const1s:
189 operand1 = (int8_t) *p++;
190 break;
191
192 /* Operations with 2-byte operands. */
193 case DW_OP_call2:
194 case DW_OP_const2u:
195 case DW_OP_bra:
196 case DW_OP_skip:
197 operand1 = dbg->decode(&p, 2);
198 break;
199
200 case DW_OP_const2s:
201 operand1 = (int16_t) dbg->decode(&p, 2);
202 break;
203
204 /* Operations with 4-byte operands. */
205 case DW_OP_call4:
206 case DW_OP_const4u:
207 case DW_OP_GNU_parameter_ref:
208 operand1 = dbg->decode(&p, 4);
209 break;
210
211 case DW_OP_const4s:
212 operand1 = (int32_t) dbg->decode(&p, 4);
213 break;
214
215 /* Operations with 8-byte operands. */
216 case DW_OP_const8u:
217 case DW_OP_const8s:
218 operand1 = dbg->decode(&p, 8);
219 break;
220
221 /* Operations with an unsigned LEB128 operand. */
222 case DW_OP_constu:
223 case DW_OP_plus_uconst:
224 case DW_OP_regx:
225 case DW_OP_piece:
226 case DW_OP_GNU_deref_type:
227 case DW_OP_GNU_convert:
228 case DW_OP_GNU_reinterpret:
229 operand1 = _dwarf_decode_uleb128(&p);
230 break;
231
232 /* Operations with a signed LEB128 operand. */
233 case DW_OP_consts:
234 case DW_OP_breg0:
235 case DW_OP_breg1:
236 case DW_OP_breg2:
237 case DW_OP_breg3:
238 case DW_OP_breg4:
239 case DW_OP_breg5:
240 case DW_OP_breg6:
241 case DW_OP_breg7:
242 case DW_OP_breg8:
243 case DW_OP_breg9:
244 case DW_OP_breg10:
245 case DW_OP_breg11:
246 case DW_OP_breg12:
247 case DW_OP_breg13:
248 case DW_OP_breg14:
249 case DW_OP_breg15:
250 case DW_OP_breg16:
251 case DW_OP_breg17:
252 case DW_OP_breg18:
253 case DW_OP_breg19:
254 case DW_OP_breg20:
255 case DW_OP_breg21:
256 case DW_OP_breg22:
257 case DW_OP_breg23:
258 case DW_OP_breg24:
259 case DW_OP_breg25:
260 case DW_OP_breg26:
261 case DW_OP_breg27:
262 case DW_OP_breg28:
263 case DW_OP_breg29:
264 case DW_OP_breg30:
265 case DW_OP_breg31:
266 case DW_OP_fbreg:
267 operand1 = _dwarf_decode_sleb128(&p);
268 break;
269
270 /*
271 * Oeration with two unsigned LEB128 operands.
272 */
273 case DW_OP_bit_piece:
274 case DW_OP_GNU_regval_type:
275 operand1 = _dwarf_decode_uleb128(&p);
276 operand2 = _dwarf_decode_uleb128(&p);
277 break;
278
279 /*
280 * Operations with an unsigned LEB128 operand
281 * followed by a signed LEB128 operand.
282 */
283 case DW_OP_bregx:
284 operand1 = _dwarf_decode_uleb128(&p);
285 operand2 = _dwarf_decode_sleb128(&p);
286 break;
287
288 /*
289 * Operation with an unsigned LEB128 operand
290 * representing the size of a block, followed
291 * by the block content.
292 *
293 * Store the size of the block in the operand1
294 * and a pointer to the block in the operand2.
295 */
296 case DW_OP_implicit_value:
297 case DW_OP_GNU_entry_value:
298 operand1 = _dwarf_decode_uleb128(&p);
299 operand2 = (Dwarf_Unsigned) (uintptr_t) p;
300 p += operand1;
301 break;
302
303 /* Target address size operand. */
304 case DW_OP_addr:
305 case DW_OP_GNU_addr_index:
306 case DW_OP_GNU_const_index:
307 operand1 = dbg->decode(&p, pointer_size);
308 break;
309
310 /* Offset size operand. */
311 case DW_OP_call_ref:
312 operand1 = dbg->decode(&p, offset_size);
313 break;
314
315 /*
316 * The first byte is address byte length, followed by
317 * the address value. If the length is 0, the address
318 * size is the same as target pointer size.
319 */
320 case DW_OP_GNU_encoded_addr:
321 s = *p++;
322 if (s == 0)
323 s = pointer_size;
324 operand1 = dbg->decode(&p, s);
325 break;
326
327 /*
328 * Operand1: DIE offset (size depending on DWARF version)
329 * DWARF2: pointer size
330 * DWARF{3,4}: offset size
331 *
332 * Operand2: SLEB128
333 */
334 case DW_OP_GNU_implicit_pointer:
335 if (version == 2)
336 operand1 = dbg->decode(&p, pointer_size);
337 else
338 operand1 = dbg->decode(&p, offset_size);
339 operand2 = _dwarf_decode_sleb128(&p);
340 break;
341
342 /*
343 * Operand1: DIE offset (ULEB128)
344 * Operand2: pointer to a block. The block's first byte
345 * is its size.
346 */
347 case DW_OP_GNU_const_type:
348 operand1 = _dwarf_decode_uleb128(&p);
349 operand2 = (Dwarf_Unsigned) (uintptr_t) p;
350 s = *p++;
351 p += s;
352 break;
353
354 /* All other operations cause an error. */
355 default:
356 count = -1;
357 goto done;
358 }
359
360 if (lbuf != NULL) {
361 lbuf->ld_s[count].lr_number = operand1;
362 lbuf->ld_s[count].lr_number2 = operand2;
363 }
364
365 count++;
366 }
367
368 done:
369 return (count);
370 }
371
372 int
_dwarf_loc_expr_add_atom(Dwarf_Debug dbg,uint8_t * out,uint8_t * end,Dwarf_Small atom,Dwarf_Unsigned operand1,Dwarf_Unsigned operand2,int * length,Dwarf_Error * error)373 _dwarf_loc_expr_add_atom(Dwarf_Debug dbg, uint8_t *out, uint8_t *end,
374 Dwarf_Small atom, Dwarf_Unsigned operand1, Dwarf_Unsigned operand2,
375 int *length, Dwarf_Error *error)
376 {
377 uint8_t buf[64];
378 uint8_t *p, *pe;
379 uint64_t offset;
380 int len;
381
382 if (out != NULL && end != NULL) {
383 p = out;
384 pe = end;
385 } else {
386 p = out = buf;
387 pe = &buf[sizeof(buf)];
388 }
389
390 switch (atom) {
391 /* Operations with no operands. */
392 case DW_OP_deref:
393 case DW_OP_reg0:
394 case DW_OP_reg1:
395 case DW_OP_reg2:
396 case DW_OP_reg3:
397 case DW_OP_reg4:
398 case DW_OP_reg5:
399 case DW_OP_reg6:
400 case DW_OP_reg7:
401 case DW_OP_reg8:
402 case DW_OP_reg9:
403 case DW_OP_reg10:
404 case DW_OP_reg11:
405 case DW_OP_reg12:
406 case DW_OP_reg13:
407 case DW_OP_reg14:
408 case DW_OP_reg15:
409 case DW_OP_reg16:
410 case DW_OP_reg17:
411 case DW_OP_reg18:
412 case DW_OP_reg19:
413 case DW_OP_reg20:
414 case DW_OP_reg21:
415 case DW_OP_reg22:
416 case DW_OP_reg23:
417 case DW_OP_reg24:
418 case DW_OP_reg25:
419 case DW_OP_reg26:
420 case DW_OP_reg27:
421 case DW_OP_reg28:
422 case DW_OP_reg29:
423 case DW_OP_reg30:
424 case DW_OP_reg31:
425
426 case DW_OP_lit0:
427 case DW_OP_lit1:
428 case DW_OP_lit2:
429 case DW_OP_lit3:
430 case DW_OP_lit4:
431 case DW_OP_lit5:
432 case DW_OP_lit6:
433 case DW_OP_lit7:
434 case DW_OP_lit8:
435 case DW_OP_lit9:
436 case DW_OP_lit10:
437 case DW_OP_lit11:
438 case DW_OP_lit12:
439 case DW_OP_lit13:
440 case DW_OP_lit14:
441 case DW_OP_lit15:
442 case DW_OP_lit16:
443 case DW_OP_lit17:
444 case DW_OP_lit18:
445 case DW_OP_lit19:
446 case DW_OP_lit20:
447 case DW_OP_lit21:
448 case DW_OP_lit22:
449 case DW_OP_lit23:
450 case DW_OP_lit24:
451 case DW_OP_lit25:
452 case DW_OP_lit26:
453 case DW_OP_lit27:
454 case DW_OP_lit28:
455 case DW_OP_lit29:
456 case DW_OP_lit30:
457 case DW_OP_lit31:
458
459 case DW_OP_dup:
460 case DW_OP_drop:
461
462 case DW_OP_over:
463
464 case DW_OP_swap:
465 case DW_OP_rot:
466 case DW_OP_xderef:
467
468 case DW_OP_abs:
469 case DW_OP_and:
470 case DW_OP_div:
471 case DW_OP_minus:
472 case DW_OP_mod:
473 case DW_OP_mul:
474 case DW_OP_neg:
475 case DW_OP_not:
476 case DW_OP_or:
477 case DW_OP_plus:
478
479 case DW_OP_shl:
480 case DW_OP_shr:
481 case DW_OP_shra:
482 case DW_OP_xor:
483
484 case DW_OP_eq:
485 case DW_OP_ge:
486 case DW_OP_gt:
487 case DW_OP_le:
488 case DW_OP_lt:
489 case DW_OP_ne:
490
491 case DW_OP_nop:
492 case DW_OP_GNU_push_tls_address:
493 *p++ = atom;
494 break;
495
496 /* Operations with 1-byte operands. */
497 case DW_OP_const1u:
498 case DW_OP_const1s:
499 case DW_OP_pick:
500 case DW_OP_deref_size:
501 case DW_OP_xderef_size:
502 *p++ = atom;
503 *p++ = (uint8_t) operand1;
504 break;
505
506 /* Operations with 2-byte operands. */
507 case DW_OP_const2u:
508 case DW_OP_const2s:
509 case DW_OP_bra:
510 case DW_OP_skip:
511 *p++ = atom;
512 offset = 0;
513 dbg->write(p, &offset, operand1, 2);
514 p += 2;
515 break;
516
517 /* Operations with 4-byte operands. */
518 case DW_OP_const4u:
519 case DW_OP_const4s:
520 *p++ = atom;
521 offset = 0;
522 dbg->write(p, &offset, operand1, 4);
523 p += 4;
524 break;
525
526 /* Operations with 8-byte operands. */
527 case DW_OP_const8u:
528 case DW_OP_const8s:
529 *p++ = atom;
530 offset = 0;
531 dbg->write(p, &offset, operand1, 8);
532 p += 8;
533 break;
534
535 /* Operations with an unsigned LEB128 operand. */
536 case DW_OP_constu:
537 case DW_OP_plus_uconst:
538 case DW_OP_regx:
539 case DW_OP_piece:
540 *p++ = atom;
541 len = _dwarf_write_uleb128(p, pe, operand1);
542 assert(len > 0);
543 p += len;
544 break;
545
546 /* Operations with a signed LEB128 operand. */
547 case DW_OP_consts:
548 case DW_OP_breg0:
549 case DW_OP_breg1:
550 case DW_OP_breg2:
551 case DW_OP_breg3:
552 case DW_OP_breg4:
553 case DW_OP_breg5:
554 case DW_OP_breg6:
555 case DW_OP_breg7:
556 case DW_OP_breg8:
557 case DW_OP_breg9:
558 case DW_OP_breg10:
559 case DW_OP_breg11:
560 case DW_OP_breg12:
561 case DW_OP_breg13:
562 case DW_OP_breg14:
563 case DW_OP_breg15:
564 case DW_OP_breg16:
565 case DW_OP_breg17:
566 case DW_OP_breg18:
567 case DW_OP_breg19:
568 case DW_OP_breg20:
569 case DW_OP_breg21:
570 case DW_OP_breg22:
571 case DW_OP_breg23:
572 case DW_OP_breg24:
573 case DW_OP_breg25:
574 case DW_OP_breg26:
575 case DW_OP_breg27:
576 case DW_OP_breg28:
577 case DW_OP_breg29:
578 case DW_OP_breg30:
579 case DW_OP_breg31:
580 case DW_OP_fbreg:
581 *p++ = atom;
582 len = _dwarf_write_sleb128(p, pe, operand1);
583 assert(len > 0);
584 p += len;
585 break;
586
587 /*
588 * Operations with an unsigned LEB128 operand
589 * followed by a signed LEB128 operand.
590 */
591 case DW_OP_bregx:
592 *p++ = atom;
593 len = _dwarf_write_uleb128(p, pe, operand1);
594 assert(len > 0);
595 p += len;
596 len = _dwarf_write_sleb128(p, pe, operand2);
597 assert(len > 0);
598 p += len;
599 break;
600
601 /* Target address size operand. */
602 case DW_OP_addr:
603 *p++ = atom;
604 offset = 0;
605 dbg->write(p, &offset, operand1, dbg->dbg_pointer_size);
606 p += dbg->dbg_pointer_size;
607 break;
608
609 /* All other operations cause an error. */
610 default:
611 DWARF_SET_ERROR(dbg, error, DW_DLE_LOC_EXPR_BAD);
612 return (DW_DLE_LOC_EXPR_BAD);
613 }
614
615 if (length)
616 *length = p - out;
617
618 return (DW_DLE_NONE);
619 }
620
621 int
_dwarf_loc_fill_locdesc(Dwarf_Debug dbg,Dwarf_Locdesc * llbuf,uint8_t * in,uint64_t in_len,uint8_t pointer_size,uint8_t offset_size,uint8_t version,Dwarf_Error * error)622 _dwarf_loc_fill_locdesc(Dwarf_Debug dbg, Dwarf_Locdesc *llbuf, uint8_t *in,
623 uint64_t in_len, uint8_t pointer_size, uint8_t offset_size,
624 uint8_t version, Dwarf_Error *error)
625 {
626 int num;
627
628 assert(llbuf != NULL);
629 assert(in != NULL);
630 assert(in_len > 0);
631
632 /* Compute the number of locations. */
633 if ((num = _dwarf_loc_fill_loc(dbg, NULL, pointer_size, offset_size,
634 version, in, in_len)) < 0) {
635 DWARF_SET_ERROR(dbg, error, DW_DLE_LOC_EXPR_BAD);
636 return (DW_DLE_LOC_EXPR_BAD);
637 }
638
639 llbuf->ld_cents = num;
640 if (num <= 0)
641 return (DW_DLE_NONE);
642
643 if ((llbuf->ld_s = calloc(num, sizeof(Dwarf_Loc))) == NULL) {
644 DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
645 return (DW_DLE_MEMORY);
646 }
647
648 (void) _dwarf_loc_fill_loc(dbg, llbuf, pointer_size, offset_size,
649 version, in, in_len);
650
651 return (DW_DLE_NONE);
652 }
653
654 int
_dwarf_loc_fill_locexpr(Dwarf_Debug dbg,Dwarf_Locdesc ** ret_llbuf,uint8_t * in,uint64_t in_len,uint8_t pointer_size,uint8_t offset_size,uint8_t version,Dwarf_Error * error)655 _dwarf_loc_fill_locexpr(Dwarf_Debug dbg, Dwarf_Locdesc **ret_llbuf, uint8_t *in,
656 uint64_t in_len, uint8_t pointer_size, uint8_t offset_size,
657 uint8_t version, Dwarf_Error *error)
658 {
659 Dwarf_Locdesc *llbuf;
660 int ret;
661
662 if ((llbuf = malloc(sizeof(Dwarf_Locdesc))) == NULL) {
663 DWARF_SET_ERROR(dbg, error, DW_DLE_MEMORY);
664 return (DW_DLE_MEMORY);
665 }
666 llbuf->ld_lopc = 0;
667 llbuf->ld_hipc = ~0ULL;
668 llbuf->ld_s = NULL;
669
670 ret = _dwarf_loc_fill_locdesc(dbg, llbuf, in, in_len, pointer_size,
671 offset_size, version, error);
672 if (ret != DW_DLE_NONE) {
673 free(llbuf);
674 return (ret);
675 }
676
677 *ret_llbuf = llbuf;
678
679 return (ret);
680 }
681
682 int
_dwarf_loc_add(Dwarf_Die die,Dwarf_Attribute at,Dwarf_Error * error)683 _dwarf_loc_add(Dwarf_Die die, Dwarf_Attribute at, Dwarf_Error *error)
684 {
685 Dwarf_Debug dbg;
686 Dwarf_CU cu;
687 int ret;
688
689 assert(at->at_ld == NULL);
690 assert(at->u[1].u8p != NULL);
691 assert(at->u[0].u64 > 0);
692
693 cu = die->die_cu;
694 assert(cu != NULL);
695
696 dbg = cu->cu_dbg;
697 assert(dbg != NULL);
698
699 ret = _dwarf_loc_fill_locexpr(dbg, &at->at_ld, at->u[1].u8p,
700 at->u[0].u64, cu->cu_pointer_size, cu->cu_length_size == 4 ? 4 : 8,
701 cu->cu_version, error);
702
703 return (ret);
704 }
705