diff options
Diffstat (limited to 'scripts/mod/modpost.c')
| -rw-r--r-- | scripts/mod/modpost.c | 38 |
1 files changed, 36 insertions, 2 deletions
diff --git a/scripts/mod/modpost.c b/scripts/mod/modpost.c index 40610984a1b5..066355673930 100644 --- a/scripts/mod/modpost.c +++ b/scripts/mod/modpost.c | |||
| @@ -623,7 +623,10 @@ static void handle_modversions(struct module *mod, struct elf_info *info, | |||
| 623 | 623 | ||
| 624 | switch (sym->st_shndx) { | 624 | switch (sym->st_shndx) { |
| 625 | case SHN_COMMON: | 625 | case SHN_COMMON: |
| 626 | warn("\"%s\" [%s] is COMMON symbol\n", symname, mod->name); | 626 | if (!strncmp(symname, "__gnu_lto_", sizeof("__gnu_lto_")-1)) { |
| 627 | /* Should warn here, but modpost runs before the linker */ | ||
| 628 | } else | ||
| 629 | warn("\"%s\" [%s] is COMMON symbol\n", symname, mod->name); | ||
| 627 | break; | 630 | break; |
| 628 | case SHN_UNDEF: | 631 | case SHN_UNDEF: |
| 629 | /* undefined symbol */ | 632 | /* undefined symbol */ |
| @@ -849,6 +852,7 @@ static const char *section_white_list[] = | |||
| 849 | ".xt.lit", /* xtensa */ | 852 | ".xt.lit", /* xtensa */ |
| 850 | ".arcextmap*", /* arc */ | 853 | ".arcextmap*", /* arc */ |
| 851 | ".gnu.linkonce.arcext*", /* arc : modules */ | 854 | ".gnu.linkonce.arcext*", /* arc : modules */ |
| 855 | ".gnu.lto*", | ||
| 852 | NULL | 856 | NULL |
| 853 | }; | 857 | }; |
| 854 | 858 | ||
| @@ -1455,6 +1459,10 @@ static void check_section_mismatch(const char *modname, struct elf_info *elf, | |||
| 1455 | to = find_elf_symbol(elf, r->r_addend, sym); | 1459 | to = find_elf_symbol(elf, r->r_addend, sym); |
| 1456 | tosym = sym_name(elf, to); | 1460 | tosym = sym_name(elf, to); |
| 1457 | 1461 | ||
| 1462 | if (!strncmp(fromsym, "reference___initcall", | ||
| 1463 | sizeof("reference___initcall")-1)) | ||
| 1464 | return; | ||
| 1465 | |||
| 1458 | /* check whitelist - we may ignore it */ | 1466 | /* check whitelist - we may ignore it */ |
| 1459 | if (secref_whitelist(mismatch, | 1467 | if (secref_whitelist(mismatch, |
| 1460 | fromsec, fromsym, tosec, tosym)) { | 1468 | fromsec, fromsym, tosec, tosym)) { |
| @@ -1502,6 +1510,16 @@ static int addend_386_rel(struct elf_info *elf, Elf_Shdr *sechdr, Elf_Rela *r) | |||
| 1502 | #define R_ARM_JUMP24 29 | 1510 | #define R_ARM_JUMP24 29 |
| 1503 | #endif | 1511 | #endif |
| 1504 | 1512 | ||
| 1513 | #ifndef R_ARM_THM_CALL | ||
| 1514 | #define R_ARM_THM_CALL 10 | ||
| 1515 | #endif | ||
| 1516 | #ifndef R_ARM_THM_JUMP24 | ||
| 1517 | #define R_ARM_THM_JUMP24 30 | ||
| 1518 | #endif | ||
| 1519 | #ifndef R_ARM_THM_JUMP19 | ||
| 1520 | #define R_ARM_THM_JUMP19 51 | ||
| 1521 | #endif | ||
| 1522 | |||
| 1505 | static int addend_arm_rel(struct elf_info *elf, Elf_Shdr *sechdr, Elf_Rela *r) | 1523 | static int addend_arm_rel(struct elf_info *elf, Elf_Shdr *sechdr, Elf_Rela *r) |
| 1506 | { | 1524 | { |
| 1507 | unsigned int r_typ = ELF_R_TYPE(r->r_info); | 1525 | unsigned int r_typ = ELF_R_TYPE(r->r_info); |
| @@ -1515,6 +1533,9 @@ static int addend_arm_rel(struct elf_info *elf, Elf_Shdr *sechdr, Elf_Rela *r) | |||
| 1515 | case R_ARM_PC24: | 1533 | case R_ARM_PC24: |
| 1516 | case R_ARM_CALL: | 1534 | case R_ARM_CALL: |
| 1517 | case R_ARM_JUMP24: | 1535 | case R_ARM_JUMP24: |
| 1536 | case R_ARM_THM_CALL: | ||
| 1537 | case R_ARM_THM_JUMP24: | ||
| 1538 | case R_ARM_THM_JUMP19: | ||
| 1518 | /* From ARM ABI: ((S + A) | T) - P */ | 1539 | /* From ARM ABI: ((S + A) | T) - P */ |
| 1519 | r->r_addend = (int)(long)(elf->hdr + | 1540 | r->r_addend = (int)(long)(elf->hdr + |
| 1520 | sechdr->sh_offset + | 1541 | sechdr->sh_offset + |
| @@ -1680,6 +1701,19 @@ static void check_sec_ref(struct module *mod, const char *modname, | |||
| 1680 | } | 1701 | } |
| 1681 | } | 1702 | } |
| 1682 | 1703 | ||
| 1704 | static char *remove_dot(char *s) | ||
| 1705 | { | ||
| 1706 | char *end; | ||
| 1707 | int n = strcspn(s, "."); | ||
| 1708 | |||
| 1709 | if (n > 0 && s[n] != 0) { | ||
| 1710 | strtoul(s + n + 1, &end, 10); | ||
| 1711 | if (end > s + n + 1 && (*end == '.' || *end == 0)) | ||
| 1712 | s[n] = 0; | ||
| 1713 | } | ||
| 1714 | return s; | ||
| 1715 | } | ||
| 1716 | |||
| 1683 | static void read_symbols(char *modname) | 1717 | static void read_symbols(char *modname) |
| 1684 | { | 1718 | { |
| 1685 | const char *symname; | 1719 | const char *symname; |
| @@ -1718,7 +1752,7 @@ static void read_symbols(char *modname) | |||
| 1718 | } | 1752 | } |
| 1719 | 1753 | ||
| 1720 | for (sym = info.symtab_start; sym < info.symtab_stop; sym++) { | 1754 | for (sym = info.symtab_start; sym < info.symtab_stop; sym++) { |
| 1721 | symname = info.strtab + sym->st_name; | 1755 | symname = remove_dot(info.strtab + sym->st_name); |
| 1722 | 1756 | ||
| 1723 | handle_modversions(mod, &info, sym, symname); | 1757 | handle_modversions(mod, &info, sym, symname); |
| 1724 | handle_moddevtable(mod, &info, sym, symname); | 1758 | handle_moddevtable(mod, &info, sym, symname); |
