1/** 2 * @file debug_line.c 3 * DWARF 2 debug line info creation helper 4 * 5 * @remark Copyright 2007 OProfile authors 6 * @remark Read the file COPYING 7 * 8 * @author Philippe Elie 9 */ 10 11#include <stdint.h> 12#include <stdlib.h> 13#include <string.h> 14#include <stddef.h> 15#include <stdio.h> 16#include <bfd.h> 17#include <limits.h> 18 19#include "opjitconv.h" 20#include "jitdump.h" 21#include "opagent.h" 22#include "op_libiberty.h" 23#include "op_growable_buffer.h" 24 25/* 26 * Terminology comes from the TIS DWARF Debugging Information Format 27 * version 2.0 28 */ 29 30typedef uint32_t uword; 31typedef uint16_t uhalf; 32typedef int32_t sword; 33typedef int16_t shalf; 34typedef uint8_t ubyte; 35typedef int8_t sbyte; 36 37/* 38 * Many of the following enum are incomplete and define only the subset 39 * of DWARF we use. 40 */ 41enum lns_opcode { 42 DW_LNS_copy=1, 43 DW_LNS_advance_pc, 44 DW_LNS_advance_line, 45 DW_LNS_set_file, 46 DW_LNS_set_column, 47 DW_LNS_negate_stmt, 48 DW_LNS_set_basic_block, 49 DW_LNS_const_add_pc, 50 DW_LNS_fixed_advance_pc, 51 52 /* Adding new opcode needs an update of the standard_opcode_length 53 * array */ 54 55 DW_LNS_max_opcode, 56}; 57 58enum lne_opcode { 59 DW_LNE_end_sequence = 1, 60 DW_LNE_set_address, 61 DW_LNE_define_file 62}; 63 64enum dw_tag { 65 DW_TAG_compile_unit = 0x11, 66}; 67 68enum dw_at { 69 DW_AT_name = 0x03, 70 DW_AT_stmt_list = 0x10, 71 DW_AT_low_pc, 72 DW_AT_high_pc, 73 DW_AT_language, 74 DW_AT_compdir = 0x1b, 75 DW_AT_producer = 0x25, 76}; 77 78enum dw_children { 79 DW_CHILDREN_no, 80 DW_CHILDREN_yes 81}; 82 83enum dw_form { 84 DW_FORM_data4 = 0x06, 85}; 86 87struct debug_line_header { 88 // Not counting this field 89 uword total_length; 90 // version number (2 currently) 91 uhalf version; 92 // relative offset from next field to 93 // program statement 94 uword prolog_length; 95 ubyte minimum_instruction_length; 96 ubyte default_is_stmt; 97 // line_base - see DWARF 2 specs 98 sbyte line_base; 99 // line_range - see DWARF 2 specs 100 ubyte line_range; 101 // number of opcode + 1 102 ubyte opcode_base; 103 /* follow the array of opcode args nr: ubytes [nr_opcode_base] */ 104 /* follow the search directories index, zero terminated string 105 * terminated by an empty string. 106 */ 107 /* follow an array of { filename, LEB128, LEB128, LEB128 }, first is 108 * the directory index entry, 0 means current directory, then mtime 109 * and filesize, last entry is followed by en empty string. 110 */ 111 /* follow the first program statement */ 112} __attribute__((packed)); 113 114/* DWARF 2 spec talk only about one possible compilation unit header while 115 * binutils can handle two flavours of dwarf 2, 32 and 64 bits, this is not 116 * related to the used arch, an ELF 32 can hold more than 4 Go of debug 117 * information. For now we handle only DWARF 2 32 bits comp unit. It'll only 118 * become a problem if we generate more than 4GB of debug information. 119 */ 120struct compilation_unit_header { 121 uword total_length; 122 uhalf version; 123 uword debug_abbrev_offset; 124 ubyte pointer_size; 125} __attribute__((packed)); 126 127/* field filled at run time are marked with -1 */ 128static struct debug_line_header const default_debug_line_header = { 129 -1, 130 2, 131 -1, 132 1, /* could be better when min instruction size != 1 */ 133 1, /* we don't take care about basic block */ 134 -5, /* sensible value for line base ... */ 135 14, /* ... and line range are guessed statically */ 136 DW_LNS_max_opcode 137}; 138 139static ubyte const standard_opcode_length[DW_LNS_max_opcode - 1] = 140{ 141 0, 1, 1, 1, 1, 0, 0, 0, 1 142}; 143 144/* field filled at run time are marked with -1 */ 145static struct compilation_unit_header const default_comp_unit_header = { 146 -1, 147 2, 148 0, /* we reuse the same abbrev entries for all comp unit */ 149 -1 150}; 151 152 153static void emit_uword(struct growable_buffer * b, uword data) 154{ 155 add_data(b, &data, sizeof(uword)); 156} 157 158 159static void emit_string(struct growable_buffer * b, char const * s) 160{ 161 add_data(b, s, strlen(s) + 1); 162} 163 164 165static void emit_unsigned_LEB128(struct growable_buffer * b, 166 unsigned long data) 167{ 168 do { 169 ubyte cur = data & 0x7F; 170 data >>= 7; 171 if (data) 172 cur |= 0x80; 173 add_data(b, &cur, 1); 174 } while (data); 175} 176 177 178static void emit_signed_LEB128(struct growable_buffer * b, long data) 179{ 180 int more = 1; 181 int negative = data < 0; 182 int size = sizeof(long) * CHAR_BIT; 183 while (more) { 184 ubyte cur = data & 0x7F; 185 data >>= 7; 186 if (negative) 187 data |= - (1 << (size - 7)); 188 if ((data == 0 && !(cur & 0x40)) || 189 (data == -1l && (cur & 0x40))) 190 more = 0; 191 else 192 cur |= 0x80; 193 add_data(b, &cur, 1); 194 } 195} 196 197 198static void emit_extended_opcode(struct growable_buffer * b, ubyte opcode, 199 void * data, size_t data_len) 200{ 201 add_data(b, "", 1); 202 emit_unsigned_LEB128(b, data_len + 1); 203 add_data(b, &opcode, 1); 204 add_data(b, data, data_len); 205} 206 207 208static void emit_opcode(struct growable_buffer * b, ubyte opcode) 209{ 210 add_data(b, &opcode, 1); 211} 212 213 214static void emit_opcode_signed(struct growable_buffer * b, 215 ubyte opcode, long data) 216{ 217 add_data(b, &opcode, 1); 218 emit_signed_LEB128(b, data); 219} 220 221 222static void emit_opcode_unsigned(struct growable_buffer * b, ubyte opcode, 223 unsigned long data) 224{ 225 add_data(b, &opcode, 1); 226 emit_unsigned_LEB128(b, data); 227} 228 229 230static void emit_advance_pc(struct growable_buffer * b, unsigned long delta_pc) 231{ 232 emit_opcode_unsigned(b, DW_LNS_advance_pc, delta_pc); 233} 234 235 236static void emit_advance_lineno(struct growable_buffer * b, long delta_lineno) 237{ 238 emit_opcode_signed(b, DW_LNS_advance_line, delta_lineno); 239} 240 241 242static void emit_lne_end_of_sequence(struct growable_buffer * b) 243{ 244 emit_extended_opcode(b, DW_LNE_end_sequence, NULL, 0); 245} 246 247 248static void emit_set_file(struct growable_buffer * b, unsigned long index) 249{ 250 emit_opcode_unsigned(b, DW_LNS_set_file, index); 251} 252 253 254static void emit_lne_define_filename(struct growable_buffer * b, 255 char const * filename) 256{ 257 /* emit_extended_opcode() can't be used here, we have additional 258 * data to output and the len field will be miscalculated. */ 259 add_data(b, "", 1); 260 /* strlen(filename) + zero terminator + len field + 3 bytes for the dir 261 * entry, timestamp and filesize */ 262 emit_unsigned_LEB128(b, strlen(filename) + 5); 263 emit_opcode(b, DW_LNE_define_file); 264 emit_string(b, filename); 265 add_data(b, "\0\0\0", 3); 266} 267 268 269static void emit_lne_set_address(struct growable_buffer * b, 270 void const * address) 271{ 272 emit_extended_opcode(b, DW_LNE_set_address, &address, sizeof(address)); 273} 274 275 276static ubyte get_special_opcode(struct debug_line_info const * line, 277 unsigned int last_lineno, unsigned long last_vma) 278{ 279 unsigned int temp; 280 unsigned long delta_addr; 281 282 /* See TIS DWARF Debugging Information Format version 2.0 � 6.2.5.1 */ 283 284 temp = (line->lineno - last_lineno) - 285 default_debug_line_header.line_base; 286 if (temp >= default_debug_line_header.line_range) 287 return 0; 288 289 delta_addr = (line->vma - last_vma) / 290 default_debug_line_header.minimum_instruction_length; 291 /* This is not sufficient to ensure opcode will be in [0-256] but 292 * sufficient to ensure when summing with the delta lineno we will 293 * not overflow the unsigned long opcode */ 294 if (delta_addr <= 256 / default_debug_line_header.line_range) { 295 unsigned long opcode = temp + 296 (delta_addr * default_debug_line_header.line_range) + 297 default_debug_line_header.opcode_base; 298 299 return opcode <= 255 ? opcode : 0; 300 } 301 302 return 0; 303} 304 305 306static void emit_lineno_info(struct growable_buffer * b, 307 struct debug_line_info const * line, size_t nr_entry, 308 unsigned long code_addr) 309{ 310 size_t i; 311 312 /* 313 * Machine state at start of a statement program 314 * address = 0 315 * file = 1 316 * line = 1 317 * column = 0 318 * is_stmt = default_is_stmt as given in the debug_line_header 319 * basic block = 0 320 * end sequence = 0 321 */ 322 323 /* start state of the state machine we take care of */ 324 unsigned long last_vma = code_addr; 325 unsigned int last_lineno = 1; 326 char const * cur_filename = NULL; 327 unsigned long cur_file_index = 0; 328 329 /* FIXME: relocatable address? */ 330 emit_lne_set_address(b, (void const *)code_addr); 331 emit_advance_lineno(b, line[0].lineno - last_lineno); 332 last_lineno = line[0].lineno; 333 emit_lne_define_filename(b, line[0].filename); 334 cur_filename = line[0].filename; 335 emit_set_file(b, ++cur_file_index); 336 emit_opcode(b, DW_LNS_copy); 337 338 339 for (i = 0; i < nr_entry; i++) { 340 int need_copy = 0; 341 ubyte special_opcode; 342 343 if (!cur_filename || strcmp(cur_filename, line[i].filename)) { 344 emit_lne_define_filename(b, line[i].filename); 345 cur_filename = line[i].filename; 346 emit_set_file(b, ++cur_file_index); 347 need_copy = 1; 348 } 349 if ((special_opcode = get_special_opcode(&line[i], 350 last_lineno, last_vma)) != 0) { 351 last_lineno = line[i].lineno; 352 last_vma = line[i].vma; 353 emit_opcode(b, special_opcode); 354 } else { 355 if (last_lineno != line[i].lineno) { 356 emit_advance_lineno(b, 357 line[i].lineno - last_lineno); 358 last_lineno = line[i].lineno; 359 need_copy = 1; 360 } 361 if (last_vma != line[i].vma) { 362 emit_advance_pc(b, line[i].vma - last_vma); 363 last_vma = line[i].vma; 364 need_copy = 1; 365 } 366 if (need_copy) 367 emit_opcode(b, DW_LNS_copy); 368 } 369 } 370} 371 372 373static void add_debug_line(struct growable_buffer * b, 374 struct debug_line_info const * line, size_t nr_entry, 375 unsigned long code_addr) 376{ 377 struct debug_line_header * dbg_header; 378 size_t old_size; 379 380 old_size = b->size; 381 382 add_data(b, &default_debug_line_header, 383 sizeof(default_debug_line_header)); 384 add_data(b, &standard_opcode_length, sizeof(standard_opcode_length)); 385 386 // empty directory entry 387 add_data(b, "", 1); 388 389 // empty filename directory 390 add_data(b, "", 1); 391 392 dbg_header = b->p + old_size; 393 dbg_header->prolog_length = (b->size - old_size) - 394 offsetof(struct debug_line_header, minimum_instruction_length); 395 396 emit_lineno_info(b, line, nr_entry, code_addr); 397 398 emit_lne_end_of_sequence(b); 399 400 dbg_header = b->p + old_size; 401 dbg_header->total_length = (b->size - old_size) - 402 offsetof(struct debug_line_header, version); 403} 404 405 406static void add_compilation_unit(struct growable_buffer * b, 407 size_t offset_debug_line) 408{ 409 struct compilation_unit_header * comp_unit_header; 410 411 size_t old_size = b->size; 412 413 add_data(b, &default_comp_unit_header, 414 sizeof(default_comp_unit_header)); 415 416 emit_unsigned_LEB128(b, 1); 417 emit_uword(b, offset_debug_line); 418 419 comp_unit_header = b->p + old_size; 420 comp_unit_header->total_length = (b->size - old_size) - 421 offsetof(struct compilation_unit_header, version); 422 comp_unit_header->pointer_size = sizeof(void *); 423} 424 425 426static void create_debug_abbrev(struct growable_buffer * b) 427{ 428 emit_unsigned_LEB128(b, 1); 429 emit_unsigned_LEB128(b, DW_TAG_compile_unit); 430 emit_unsigned_LEB128(b, DW_CHILDREN_yes); 431 emit_unsigned_LEB128(b, DW_AT_stmt_list); 432 emit_unsigned_LEB128(b, DW_FORM_data4); 433 emit_unsigned_LEB128(b, 0); 434} 435 436static struct growable_buffer b_line; 437static struct growable_buffer b_debug_info; 438static struct growable_buffer b_debug_abbrev; 439 440int init_debug_line_info(bfd * abfd) 441{ 442 asection * line_section, * debug_info, * debug_abbrev; 443 struct jitentry_debug_line * debug_line; 444 445 init_buffer(&b_line); 446 init_buffer(&b_debug_info); 447 init_buffer(&b_debug_abbrev); 448 449 for (debug_line = jitentry_debug_line_list; 450 debug_line; 451 debug_line = debug_line->next) { 452 struct jr_code_debug_info const * rec = debug_line->data; 453 if (rec->nr_entry) { 454 size_t i; 455 void const * data = rec + 1; 456 struct debug_line_info * dbg_line = 457 xmalloc(rec->nr_entry * 458 sizeof(struct debug_line_info)); 459 for (i = 0; i < rec->nr_entry; ++i) { 460 dbg_line[i].vma = *(unsigned long *)data; 461 data += sizeof(unsigned long); 462 dbg_line[i].lineno = *(unsigned int *)data; 463 data += sizeof(unsigned int); 464 dbg_line[i].filename = data; 465 data += strlen(data) + 1; 466 } 467 468 add_compilation_unit(&b_debug_info, b_line.size); 469 add_debug_line(&b_line, dbg_line, 470 rec->nr_entry, rec->code_addr); 471 create_debug_abbrev(&b_debug_abbrev); 472 473 free(dbg_line); 474 } 475 } 476 477 line_section = create_section(abfd, ".debug_line", b_line.size, 0, 478 SEC_HAS_CONTENTS|SEC_READONLY|SEC_DEBUGGING); 479 if (!line_section) 480 return -1; 481 482 debug_info = create_section(abfd, ".debug_info", b_debug_info.size, 0, 483 SEC_HAS_CONTENTS|SEC_READONLY|SEC_DEBUGGING); 484 if (!debug_info) 485 return -1; 486 487 debug_abbrev = create_section(abfd, ".debug_abbrev", 488 b_debug_abbrev.size, 0, 489 SEC_HAS_CONTENTS|SEC_READONLY|SEC_DEBUGGING); 490 if (!debug_abbrev) 491 return -1; 492 493 return 0; 494} 495 496 497int finalize_debug_line_info(bfd * abfd) 498{ 499 asection * line_section, * debug_info, * debug_abbrev; 500 501 line_section = bfd_get_section_by_name(abfd, ".debug_line"); 502 if (!line_section) 503 return -1; 504 505 debug_info = bfd_get_section_by_name(abfd, ".debug_info"); 506 if (!debug_info) 507 return -1; 508 509 510 debug_abbrev = bfd_get_section_by_name(abfd, ".debug_abbrev"); 511 if (!debug_abbrev) 512 return -1; 513 514 fill_section_content(abfd, line_section, b_line.p, 0, b_line.size); 515 fill_section_content(abfd, debug_info, b_debug_info.p, 516 0, b_debug_info.size); 517 fill_section_content(abfd, debug_abbrev, b_debug_abbrev.p, 0, 518 b_debug_abbrev.size); 519 520 521 free_buffer(&b_line); 522 free_buffer(&b_debug_info); 523 free_buffer(&b_debug_abbrev); 524 525 return 0; 526} 527