1 /* 2 * kallsyms.c: in-kernel printing of symbolic oopses and stack traces. 3 * 4 * Rewritten and vastly simplified by Rusty Russell for in-kernel 5 * module loader: 6 * Copyright 2002 Rusty Russell <rusty@rustcorp.com.au> IBM Corporation 7 * 8 * ChangeLog: 9 * 10 * (25/Aug/2004) Paulo Marques <pmarques@grupopie.com> 11 * Changed the compression method from stem compression to "table lookup" 12 * compression (see scripts/kallsyms.c for a more complete description) 13 */ 14 #include <linux/kallsyms.h> 15 #include <linux/module.h> 16 #include <linux/init.h> 17 #include <linux/seq_file.h> 18 #include <linux/fs.h> 19 #include <linux/kdb.h> 20 #include <linux/err.h> 21 #include <linux/proc_fs.h> 22 #include <linux/sched.h> /* for cond_resched */ 23 #include <linux/mm.h> 24 #include <linux/ctype.h> 25 #include <linux/slab.h> 26 #include <linux/compiler.h> 27 28 #include <asm/sections.h> 29 30 #ifdef CONFIG_KALLSYMS_ALL 31 #define all_var 1 32 #else 33 #define all_var 0 34 #endif 35 36 /* 37 * These will be re-linked against their real values 38 * during the second link stage. 39 */ 40 extern const unsigned long kallsyms_addresses[] __weak; 41 extern const int kallsyms_offsets[] __weak; 42 extern const u8 kallsyms_names[] __weak; 43 44 /* 45 * Tell the compiler that the count isn't in the small data section if the arch 46 * has one (eg: FRV). 47 */ 48 extern const unsigned long kallsyms_num_syms 49 __attribute__((weak, section(".rodata"))); 50 51 extern const unsigned long kallsyms_relative_base 52 __attribute__((weak, section(".rodata"))); 53 54 extern const u8 kallsyms_token_table[] __weak; 55 extern const u16 kallsyms_token_index[] __weak; 56 57 extern const unsigned long kallsyms_markers[] __weak; 58 59 static inline int is_kernel_inittext(unsigned long addr) 60 { 61 if (addr >= (unsigned long)_sinittext 62 && addr <= (unsigned long)_einittext) 63 return 1; 64 return 0; 65 } 66 67 static inline int is_kernel_text(unsigned long addr) 68 { 69 if ((addr >= (unsigned long)_stext && addr <= (unsigned long)_etext) || 70 arch_is_kernel_text(addr)) 71 return 1; 72 return in_gate_area_no_mm(addr); 73 } 74 75 static inline int is_kernel(unsigned long addr) 76 { 77 if (addr >= (unsigned long)_stext && addr <= (unsigned long)_end) 78 return 1; 79 return in_gate_area_no_mm(addr); 80 } 81 82 static int is_ksym_addr(unsigned long addr) 83 { 84 if (all_var) 85 return is_kernel(addr); 86 87 return is_kernel_text(addr) || is_kernel_inittext(addr); 88 } 89 90 /* 91 * Expand a compressed symbol data into the resulting uncompressed string, 92 * if uncompressed string is too long (>= maxlen), it will be truncated, 93 * given the offset to where the symbol is in the compressed stream. 94 */ 95 static unsigned int kallsyms_expand_symbol(unsigned int off, 96 char *result, size_t maxlen) 97 { 98 int len, skipped_first = 0; 99 const u8 *tptr, *data; 100 101 /* Get the compressed symbol length from the first symbol byte. */ 102 data = &kallsyms_names[off]; 103 len = *data; 104 data++; 105 106 /* 107 * Update the offset to return the offset for the next symbol on 108 * the compressed stream. 109 */ 110 off += len + 1; 111 112 /* 113 * For every byte on the compressed symbol data, copy the table 114 * entry for that byte. 115 */ 116 while (len) { 117 tptr = &kallsyms_token_table[kallsyms_token_index[*data]]; 118 data++; 119 len--; 120 121 while (*tptr) { 122 if (skipped_first) { 123 if (maxlen <= 1) 124 goto tail; 125 *result = *tptr; 126 result++; 127 maxlen--; 128 } else 129 skipped_first = 1; 130 tptr++; 131 } 132 } 133 134 tail: 135 if (maxlen) 136 *result = '\0'; 137 138 /* Return to offset to the next symbol. */ 139 return off; 140 } 141 142 /* 143 * Get symbol type information. This is encoded as a single char at the 144 * beginning of the symbol name. 145 */ 146 static char kallsyms_get_symbol_type(unsigned int off) 147 { 148 /* 149 * Get just the first code, look it up in the token table, 150 * and return the first char from this token. 151 */ 152 return kallsyms_token_table[kallsyms_token_index[kallsyms_names[off + 1]]]; 153 } 154 155 156 /* 157 * Find the offset on the compressed stream given and index in the 158 * kallsyms array. 159 */ 160 static unsigned int get_symbol_offset(unsigned long pos) 161 { 162 const u8 *name; 163 int i; 164 165 /* 166 * Use the closest marker we have. We have markers every 256 positions, 167 * so that should be close enough. 168 */ 169 name = &kallsyms_names[kallsyms_markers[pos >> 8]]; 170 171 /* 172 * Sequentially scan all the symbols up to the point we're searching 173 * for. Every symbol is stored in a [<len>][<len> bytes of data] format, 174 * so we just need to add the len to the current pointer for every 175 * symbol we wish to skip. 176 */ 177 for (i = 0; i < (pos & 0xFF); i++) 178 name = name + (*name) + 1; 179 180 return name - kallsyms_names; 181 } 182 183 static unsigned long kallsyms_sym_address(int idx) 184 { 185 if (!IS_ENABLED(CONFIG_KALLSYMS_BASE_RELATIVE)) 186 return kallsyms_addresses[idx]; 187 188 /* values are unsigned offsets if --absolute-percpu is not in effect */ 189 if (!IS_ENABLED(CONFIG_KALLSYMS_ABSOLUTE_PERCPU)) 190 return kallsyms_relative_base + (u32)kallsyms_offsets[idx]; 191 192 /* ...otherwise, positive offsets are absolute values */ 193 if (kallsyms_offsets[idx] >= 0) 194 return kallsyms_offsets[idx]; 195 196 /* ...and negative offsets are relative to kallsyms_relative_base - 1 */ 197 return kallsyms_relative_base - 1 - kallsyms_offsets[idx]; 198 } 199 200 /* Lookup the address for this symbol. Returns 0 if not found. */ 201 unsigned long kallsyms_lookup_name(const char *name) 202 { 203 char namebuf[KSYM_NAME_LEN]; 204 unsigned long i; 205 unsigned int off; 206 207 for (i = 0, off = 0; i < kallsyms_num_syms; i++) { 208 off = kallsyms_expand_symbol(off, namebuf, ARRAY_SIZE(namebuf)); 209 210 if (strcmp(namebuf, name) == 0) 211 return kallsyms_sym_address(i); 212 } 213 return module_kallsyms_lookup_name(name); 214 } 215 EXPORT_SYMBOL_GPL(kallsyms_lookup_name); 216 217 int kallsyms_on_each_symbol(int (*fn)(void *, const char *, struct module *, 218 unsigned long), 219 void *data) 220 { 221 char namebuf[KSYM_NAME_LEN]; 222 unsigned long i; 223 unsigned int off; 224 int ret; 225 226 for (i = 0, off = 0; i < kallsyms_num_syms; i++) { 227 off = kallsyms_expand_symbol(off, namebuf, ARRAY_SIZE(namebuf)); 228 ret = fn(data, namebuf, NULL, kallsyms_sym_address(i)); 229 if (ret != 0) 230 return ret; 231 } 232 return module_kallsyms_on_each_symbol(fn, data); 233 } 234 EXPORT_SYMBOL_GPL(kallsyms_on_each_symbol); 235 236 static unsigned long get_symbol_pos(unsigned long addr, 237 unsigned long *symbolsize, 238 unsigned long *offset) 239 { 240 unsigned long symbol_start = 0, symbol_end = 0; 241 unsigned long i, low, high, mid; 242 243 /* This kernel should never had been booted. */ 244 if (!IS_ENABLED(CONFIG_KALLSYMS_BASE_RELATIVE)) 245 BUG_ON(!kallsyms_addresses); 246 else 247 BUG_ON(!kallsyms_offsets); 248 249 /* Do a binary search on the sorted kallsyms_addresses array. */ 250 low = 0; 251 high = kallsyms_num_syms; 252 253 while (high - low > 1) { 254 mid = low + (high - low) / 2; 255 if (kallsyms_sym_address(mid) <= addr) 256 low = mid; 257 else 258 high = mid; 259 } 260 261 /* 262 * Search for the first aliased symbol. Aliased 263 * symbols are symbols with the same address. 264 */ 265 while (low && kallsyms_sym_address(low-1) == kallsyms_sym_address(low)) 266 --low; 267 268 symbol_start = kallsyms_sym_address(low); 269 270 /* Search for next non-aliased symbol. */ 271 for (i = low + 1; i < kallsyms_num_syms; i++) { 272 if (kallsyms_sym_address(i) > symbol_start) { 273 symbol_end = kallsyms_sym_address(i); 274 break; 275 } 276 } 277 278 /* If we found no next symbol, we use the end of the section. */ 279 if (!symbol_end) { 280 if (is_kernel_inittext(addr)) 281 symbol_end = (unsigned long)_einittext; 282 else if (all_var) 283 symbol_end = (unsigned long)_end; 284 else 285 symbol_end = (unsigned long)_etext; 286 } 287 288 if (symbolsize) 289 *symbolsize = symbol_end - symbol_start; 290 if (offset) 291 *offset = addr - symbol_start; 292 293 return low; 294 } 295 296 /* 297 * Lookup an address but don't bother to find any names. 298 */ 299 int kallsyms_lookup_size_offset(unsigned long addr, unsigned long *symbolsize, 300 unsigned long *offset) 301 { 302 char namebuf[KSYM_NAME_LEN]; 303 if (is_ksym_addr(addr)) 304 return !!get_symbol_pos(addr, symbolsize, offset); 305 306 return !!module_address_lookup(addr, symbolsize, offset, NULL, namebuf); 307 } 308 309 /* 310 * Lookup an address 311 * - modname is set to NULL if it's in the kernel. 312 * - We guarantee that the returned name is valid until we reschedule even if. 313 * It resides in a module. 314 * - We also guarantee that modname will be valid until rescheduled. 315 */ 316 const char *kallsyms_lookup(unsigned long addr, 317 unsigned long *symbolsize, 318 unsigned long *offset, 319 char **modname, char *namebuf) 320 { 321 namebuf[KSYM_NAME_LEN - 1] = 0; 322 namebuf[0] = 0; 323 324 if (is_ksym_addr(addr)) { 325 unsigned long pos; 326 327 pos = get_symbol_pos(addr, symbolsize, offset); 328 /* Grab name */ 329 kallsyms_expand_symbol(get_symbol_offset(pos), 330 namebuf, KSYM_NAME_LEN); 331 if (modname) 332 *modname = NULL; 333 return namebuf; 334 } 335 336 /* See if it's in a module. */ 337 return module_address_lookup(addr, symbolsize, offset, modname, 338 namebuf); 339 } 340 341 int lookup_symbol_name(unsigned long addr, char *symname) 342 { 343 symname[0] = '\0'; 344 symname[KSYM_NAME_LEN - 1] = '\0'; 345 346 if (is_ksym_addr(addr)) { 347 unsigned long pos; 348 349 pos = get_symbol_pos(addr, NULL, NULL); 350 /* Grab name */ 351 kallsyms_expand_symbol(get_symbol_offset(pos), 352 symname, KSYM_NAME_LEN); 353 return 0; 354 } 355 /* See if it's in a module. */ 356 return lookup_module_symbol_name(addr, symname); 357 } 358 359 int lookup_symbol_attrs(unsigned long addr, unsigned long *size, 360 unsigned long *offset, char *modname, char *name) 361 { 362 name[0] = '\0'; 363 name[KSYM_NAME_LEN - 1] = '\0'; 364 365 if (is_ksym_addr(addr)) { 366 unsigned long pos; 367 368 pos = get_symbol_pos(addr, size, offset); 369 /* Grab name */ 370 kallsyms_expand_symbol(get_symbol_offset(pos), 371 name, KSYM_NAME_LEN); 372 modname[0] = '\0'; 373 return 0; 374 } 375 /* See if it's in a module. */ 376 return lookup_module_symbol_attrs(addr, size, offset, modname, name); 377 } 378 379 /* Look up a kernel symbol and return it in a text buffer. */ 380 static int __sprint_symbol(char *buffer, unsigned long address, 381 int symbol_offset, int add_offset) 382 { 383 char *modname; 384 const char *name; 385 unsigned long offset, size; 386 int len; 387 388 address += symbol_offset; 389 name = kallsyms_lookup(address, &size, &offset, &modname, buffer); 390 if (!name) 391 return sprintf(buffer, "0x%lx", address - symbol_offset); 392 393 if (name != buffer) 394 strcpy(buffer, name); 395 len = strlen(buffer); 396 offset -= symbol_offset; 397 398 if (add_offset) 399 len += sprintf(buffer + len, "+%#lx/%#lx", offset, size); 400 401 if (modname) 402 len += sprintf(buffer + len, " [%s]", modname); 403 404 return len; 405 } 406 407 /** 408 * sprint_symbol - Look up a kernel symbol and return it in a text buffer 409 * @buffer: buffer to be stored 410 * @address: address to lookup 411 * 412 * This function looks up a kernel symbol with @address and stores its name, 413 * offset, size and module name to @buffer if possible. If no symbol was found, 414 * just saves its @address as is. 415 * 416 * This function returns the number of bytes stored in @buffer. 417 */ 418 int sprint_symbol(char *buffer, unsigned long address) 419 { 420 return __sprint_symbol(buffer, address, 0, 1); 421 } 422 EXPORT_SYMBOL_GPL(sprint_symbol); 423 424 /** 425 * sprint_symbol_no_offset - Look up a kernel symbol and return it in a text buffer 426 * @buffer: buffer to be stored 427 * @address: address to lookup 428 * 429 * This function looks up a kernel symbol with @address and stores its name 430 * and module name to @buffer if possible. If no symbol was found, just saves 431 * its @address as is. 432 * 433 * This function returns the number of bytes stored in @buffer. 434 */ 435 int sprint_symbol_no_offset(char *buffer, unsigned long address) 436 { 437 return __sprint_symbol(buffer, address, 0, 0); 438 } 439 EXPORT_SYMBOL_GPL(sprint_symbol_no_offset); 440 441 /** 442 * sprint_backtrace - Look up a backtrace symbol and return it in a text buffer 443 * @buffer: buffer to be stored 444 * @address: address to lookup 445 * 446 * This function is for stack backtrace and does the same thing as 447 * sprint_symbol() but with modified/decreased @address. If there is a 448 * tail-call to the function marked "noreturn", gcc optimized out code after 449 * the call so that the stack-saved return address could point outside of the 450 * caller. This function ensures that kallsyms will find the original caller 451 * by decreasing @address. 452 * 453 * This function returns the number of bytes stored in @buffer. 454 */ 455 int sprint_backtrace(char *buffer, unsigned long address) 456 { 457 return __sprint_symbol(buffer, address, -1, 1); 458 } 459 460 /* Look up a kernel symbol and print it to the kernel messages. */ 461 void __print_symbol(const char *fmt, unsigned long address) 462 { 463 char buffer[KSYM_SYMBOL_LEN]; 464 465 sprint_symbol(buffer, address); 466 467 printk(fmt, buffer); 468 } 469 EXPORT_SYMBOL(__print_symbol); 470 471 /* To avoid using get_symbol_offset for every symbol, we carry prefix along. */ 472 struct kallsym_iter { 473 loff_t pos; 474 unsigned long value; 475 unsigned int nameoff; /* If iterating in core kernel symbols. */ 476 char type; 477 char name[KSYM_NAME_LEN]; 478 char module_name[MODULE_NAME_LEN]; 479 int exported; 480 }; 481 482 static int get_ksymbol_mod(struct kallsym_iter *iter) 483 { 484 if (module_get_kallsym(iter->pos - kallsyms_num_syms, &iter->value, 485 &iter->type, iter->name, iter->module_name, 486 &iter->exported) < 0) 487 return 0; 488 return 1; 489 } 490 491 /* Returns space to next name. */ 492 static unsigned long get_ksymbol_core(struct kallsym_iter *iter) 493 { 494 unsigned off = iter->nameoff; 495 496 iter->module_name[0] = '\0'; 497 iter->value = kallsyms_sym_address(iter->pos); 498 499 iter->type = kallsyms_get_symbol_type(off); 500 501 off = kallsyms_expand_symbol(off, iter->name, ARRAY_SIZE(iter->name)); 502 503 return off - iter->nameoff; 504 } 505 506 static void reset_iter(struct kallsym_iter *iter, loff_t new_pos) 507 { 508 iter->name[0] = '\0'; 509 iter->nameoff = get_symbol_offset(new_pos); 510 iter->pos = new_pos; 511 } 512 513 /* Returns false if pos at or past end of file. */ 514 static int update_iter(struct kallsym_iter *iter, loff_t pos) 515 { 516 /* Module symbols can be accessed randomly. */ 517 if (pos >= kallsyms_num_syms) { 518 iter->pos = pos; 519 return get_ksymbol_mod(iter); 520 } 521 522 /* If we're not on the desired position, reset to new position. */ 523 if (pos != iter->pos) 524 reset_iter(iter, pos); 525 526 iter->nameoff += get_ksymbol_core(iter); 527 iter->pos++; 528 529 return 1; 530 } 531 532 static void *s_next(struct seq_file *m, void *p, loff_t *pos) 533 { 534 (*pos)++; 535 536 if (!update_iter(m->private, *pos)) 537 return NULL; 538 return p; 539 } 540 541 static void *s_start(struct seq_file *m, loff_t *pos) 542 { 543 if (!update_iter(m->private, *pos)) 544 return NULL; 545 return m->private; 546 } 547 548 static void s_stop(struct seq_file *m, void *p) 549 { 550 } 551 552 static int s_show(struct seq_file *m, void *p) 553 { 554 struct kallsym_iter *iter = m->private; 555 556 /* Some debugging symbols have no name. Ignore them. */ 557 if (!iter->name[0]) 558 return 0; 559 560 if (iter->module_name[0]) { 561 char type; 562 563 /* 564 * Label it "global" if it is exported, 565 * "local" if not exported. 566 */ 567 type = iter->exported ? toupper(iter->type) : 568 tolower(iter->type); 569 seq_printf(m, "%pK %c %s\t[%s]\n", (void *)iter->value, 570 type, iter->name, iter->module_name); 571 } else 572 seq_printf(m, "%pK %c %s\n", (void *)iter->value, 573 iter->type, iter->name); 574 return 0; 575 } 576 577 static const struct seq_operations kallsyms_op = { 578 .start = s_start, 579 .next = s_next, 580 .stop = s_stop, 581 .show = s_show 582 }; 583 584 static int kallsyms_open(struct inode *inode, struct file *file) 585 { 586 /* 587 * We keep iterator in m->private, since normal case is to 588 * s_start from where we left off, so we avoid doing 589 * using get_symbol_offset for every symbol. 590 */ 591 struct kallsym_iter *iter; 592 iter = __seq_open_private(file, &kallsyms_op, sizeof(*iter)); 593 if (!iter) 594 return -ENOMEM; 595 reset_iter(iter, 0); 596 597 return 0; 598 } 599 600 #ifdef CONFIG_KGDB_KDB 601 const char *kdb_walk_kallsyms(loff_t *pos) 602 { 603 static struct kallsym_iter kdb_walk_kallsyms_iter; 604 if (*pos == 0) { 605 memset(&kdb_walk_kallsyms_iter, 0, 606 sizeof(kdb_walk_kallsyms_iter)); 607 reset_iter(&kdb_walk_kallsyms_iter, 0); 608 } 609 while (1) { 610 if (!update_iter(&kdb_walk_kallsyms_iter, *pos)) 611 return NULL; 612 ++*pos; 613 /* Some debugging symbols have no name. Ignore them. */ 614 if (kdb_walk_kallsyms_iter.name[0]) 615 return kdb_walk_kallsyms_iter.name; 616 } 617 } 618 #endif /* CONFIG_KGDB_KDB */ 619 620 static const struct file_operations kallsyms_operations = { 621 .open = kallsyms_open, 622 .read = seq_read, 623 .llseek = seq_lseek, 624 .release = seq_release_private, 625 }; 626 627 static int __init kallsyms_init(void) 628 { 629 proc_create("kallsyms", 0444, NULL, &kallsyms_operations); 630 return 0; 631 } 632 device_initcall(kallsyms_init); 633