History

kbuild: make better section mismatch reports on i386, arm and mips

On i386, ARM and MIPS, warn_sec_mismatch() sometimes fails to show usefull symbol name. This is because empty 'refsym' due to 0 r_addend value. This patch is to adjust r_addend value, consulting with apply_relocate() routine in kernel code. Without this patch: MODPOST vmlinux WARNING: init/built-in.o - Section mismatch: reference to .init.text: from .text between 'rest_init' (at offset 0xf4) and 'try_name' WARNING: mm/built-in.o - Section mismatch: reference to .init.text: from .text between 'kmem_cache_create' (at offset 0x18a39) and 'cache_reap' WARNING: mm/built-in.o - Section mismatch: reference to .init.text: from .text between 'kmem_cache_create' (at offset 0x18a6b) and 'cache_reap' With this patch: MODPOST vmlinux WARNING: mm/built-in.o - Section mismatch: reference to .init.text:set_up_list3s from .text between 'kmem_cache_create' (at offset 0x18a39) and 'cache_reap' WARNING: mm/built-in.o - Section mismatch: reference to .init.text:set_up_list3s from .text between 'kmem_cache_create' (at offset 0x18a6b) and 'cache_reap' Now modpost can detect "kernel_init" name (and whitelist it) and show "set_up_list3s" name.

Atsushi Nemoto committed 19 years ago

Commit f892b7d1 parent 25601202 files · +82 −0Browse files

Showing the changes to scripts (2 of 2 files). Show all

Unified · Split

2 files
  1. scripts/mod/modpost.c +79 −0
  2. scripts/mod/modpost.h +3 −0
scripts/mod/modpost.c+79−0
@@ -384,6 +384,7 @@ static int parse_elf(struct elf_info *info, const char *filename) · 383 unmodified lines
384 sechdrs[i].sh_size = TO_NATIVE(sechdrs[i].sh_size);384 sechdrs[i].sh_size = TO_NATIVE(sechdrs[i].sh_size);
385 sechdrs[i].sh_link = TO_NATIVE(sechdrs[i].sh_link);385 sechdrs[i].sh_link = TO_NATIVE(sechdrs[i].sh_link);
386 sechdrs[i].sh_name = TO_NATIVE(sechdrs[i].sh_name);386 sechdrs[i].sh_name = TO_NATIVE(sechdrs[i].sh_name);
387 sechdrs[i].sh_info = TO_NATIVE(sechdrs[i].sh_info);
387 }388 }
388 /* Find symbol table. */389 /* Find symbol table. */
389 for (i = 1; i < hdr->e_shnum; i++) {390 for (i = 1; i < hdr->e_shnum; i++) {
@@ -773,6 +774,8 @@ static Elf_Sym *find_elf_symbol(struct elf_info *elf, Elf_Addr addr, · 383 unmodified lines
773 for (sym = elf->symtab_start; sym < elf->symtab_stop; sym++) {774 for (sym = elf->symtab_start; sym < elf->symtab_stop; sym++) {
774 if (sym->st_shndx != relsym->st_shndx)775 if (sym->st_shndx != relsym->st_shndx)
775 continue;776 continue;
777 if (ELF_ST_TYPE(sym->st_info) == STT_SECTION)
778 continue;
776 if (sym->st_value == addr)779 if (sym->st_value == addr)
777 return sym;780 return sym;
778 }781 }
@@ -910,6 +913,68 @@ static void warn_sec_mismatch(const char *modname, const char *fromsec, · 131 unmodified lines
910 }913 }
911}914}
912 915
916static void addend_386_rel(struct elf_info *elf, int section, Elf_Rela *r)
917{
918 Elf_Shdr *sechdrs = elf->sechdrs;
919 unsigned int r_typ;
920 unsigned int *location;
921
922 r_typ = ELF_R_TYPE(r->r_info);
923 location = (void *)elf->hdr +
924 sechdrs[sechdrs[section].sh_info].sh_offset + r->r_offset;
925 switch (r_typ) {
926 case R_386_32:
927 r->r_addend = TO_NATIVE(*location);
928 break;
929 case R_386_PC32:
930 r->r_addend = TO_NATIVE(*location) + 4;
931 break;
932 }
933}
934
935static void addend_arm_rel(struct elf_info *elf, int section, Elf_Rela *r)
936{
937 Elf_Shdr *sechdrs = elf->sechdrs;
938 unsigned int r_typ;
939 unsigned int *location;
940
941 r_typ = ELF_R_TYPE(r->r_info);
942 location = (void *)elf->hdr +
943 sechdrs[sechdrs[section].sh_info].sh_offset + r->r_offset;
944 switch (r_typ) {
945 case R_ARM_ABS32:
946 r->r_addend = TO_NATIVE(*location);
947 break;
948 case R_ARM_PC24:
949 r->r_addend = ((TO_NATIVE(*location) & 0x00ffffff) << 2) + 8;
950 break;
951 }
952}
953
954static int addend_mips_rel(struct elf_info *elf, int section, Elf_Rela *r)
955{
956 Elf_Shdr *sechdrs = elf->sechdrs;
957 unsigned int r_typ;
958 unsigned int *location;
959 unsigned int inst;
960
961 r_typ = ELF_R_TYPE(r->r_info);
962 if (r_typ == R_MIPS_HI16)
963 return 1; /* skip this */
964 location = (void *)elf->hdr +
965 sechdrs[sechdrs[section].sh_info].sh_offset + r->r_offset;
966 inst = TO_NATIVE(*location);
967 switch (r_typ) {
968 case R_MIPS_LO16:
969 r->r_addend = ((inst & 0xffff) ^ 0x8000) - 0x8000;
970 break;
971 case R_MIPS_26:
972 r->r_addend = (inst & 0x03ffffff) << 2;
973 break;
974 }
975 return 0;
976}
977
913/**978/**
914 * A module includes a number of sections that are discarded979 * A module includes a number of sections that are discarded
915 * either when loaded or when used as built-in.980 * either when loaded or when used as built-in.
@@ -953,8 +1018,11 @@ static void check_sec_ref(struct module *mod, const char *modname, · 37 unmodified lines
953 r.r_offset = TO_NATIVE(rela->r_offset);1018 r.r_offset = TO_NATIVE(rela->r_offset);
954#if KERNEL_ELFCLASS == ELFCLASS641019#if KERNEL_ELFCLASS == ELFCLASS64
955 if (hdr->e_machine == EM_MIPS) {1020 if (hdr->e_machine == EM_MIPS) {
1021 unsigned int r_typ;
956 r_sym = ELF64_MIPS_R_SYM(rela->r_info);1022 r_sym = ELF64_MIPS_R_SYM(rela->r_info);
957 r_sym = TO_NATIVE(r_sym);1023 r_sym = TO_NATIVE(r_sym);
1024 r_typ = ELF64_MIPS_R_TYPE(rela->r_info);
1025 r.r_info = ELF64_R_INFO(r_sym, r_typ);
958 } else {1026 } else {
959 r.r_info = TO_NATIVE(rela->r_info);1027 r.r_info = TO_NATIVE(rela->r_info);
960 r_sym = ELF_R_SYM(r.r_info);1028 r_sym = ELF_R_SYM(r.r_info);
@@ -987,8 +1055,11 @@ static void check_sec_ref(struct module *mod, const char *modname, · 26 unmodified lines
987 r.r_offset = TO_NATIVE(rel->r_offset);1055 r.r_offset = TO_NATIVE(rel->r_offset);
988#if KERNEL_ELFCLASS == ELFCLASS641056#if KERNEL_ELFCLASS == ELFCLASS64
989 if (hdr->e_machine == EM_MIPS) {1057 if (hdr->e_machine == EM_MIPS) {
1058 unsigned int r_typ;
990 r_sym = ELF64_MIPS_R_SYM(rel->r_info);1059 r_sym = ELF64_MIPS_R_SYM(rel->r_info);
991 r_sym = TO_NATIVE(r_sym);1060 r_sym = TO_NATIVE(r_sym);
1061 r_typ = ELF64_MIPS_R_TYPE(rel->r_info);
1062 r.r_info = ELF64_R_INFO(r_sym, r_typ);
992 } else {1063 } else {
993 r.r_info = TO_NATIVE(rel->r_info);1064 r.r_info = TO_NATIVE(rel->r_info);
994 r_sym = ELF_R_SYM(r.r_info);1065 r_sym = ELF_R_SYM(r.r_info);
@@ -998,6 +1069,14 @@ static void check_sec_ref(struct module *mod, const char *modname, · 3 unmodified lines
998 r_sym = ELF_R_SYM(r.r_info);1069 r_sym = ELF_R_SYM(r.r_info);
999#endif1070#endif
1000 r.r_addend = 0;1071 r.r_addend = 0;
1072 if (hdr->e_machine == EM_386)
1073 addend_386_rel(elf, i, &r);
1074 else if (hdr->e_machine == EM_ARM)
1075 addend_arm_rel(elf, i, &r);
1076 else if (hdr->e_machine == EM_MIPS) {
1077 if (addend_mips_rel(elf, i, &r))
1078 continue;
1079 }
1001 sym = elf->symtab_start + r_sym;1080 sym = elf->symtab_start + r_sym;
1002 /* Skip special sections */1081 /* Skip special sections */
1003 if (sym->st_shndx >= SHN_LORESERVE)1082 if (sym->st_shndx >= SHN_LORESERVE)
scripts/mod/modpost.h+3−0
@@ -60,6 +60,9 @@ typedef union · 59 unmodified lines
60#define ELF64_MIPS_R_SYM(i) \60#define ELF64_MIPS_R_SYM(i) \
61 ((__extension__ (_Elf64_Mips_R_Info_union)(i)).r_info_fields.r_sym)61 ((__extension__ (_Elf64_Mips_R_Info_union)(i)).r_info_fields.r_sym)
62 62
63#define ELF64_MIPS_R_TYPE(i) \
64 ((__extension__ (_Elf64_Mips_R_Info_union)(i)).r_info_fields.r_type1)
65
63#if KERNEL_ELFDATA != HOST_ELFDATA66#if KERNEL_ELFDATA != HOST_ELFDATA
64 67
65static inline void __endian(const void *src, void *dest, unsigned int size)68static inline void __endian(const void *src, void *dest, unsigned int size)

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t