diff options
author | Eric Andersen <andersen@codepoet.org> | 2001-02-24 20:01:53 +0000 |
---|---|---|
committer | Eric Andersen <andersen@codepoet.org> | 2001-02-24 20:01:53 +0000 |
commit | 2bf658d5cd4460a0e0a8a8f3c8dc3b71be05d1ba (patch) | |
tree | 197b3919ea1f13ac6595f6ddb57b105be4c21333 | |
parent | afeb96547fabc8c63e883f7c24aab5638cafbd50 (diff) | |
download | busybox-w32-2bf658d5cd4460a0e0a8a8f3c8dc3b71be05d1ba.tar.gz busybox-w32-2bf658d5cd4460a0e0a8a8f3c8dc3b71be05d1ba.tar.bz2 busybox-w32-2bf658d5cd4460a0e0a8a8f3c8dc3b71be05d1ba.zip |
This patch, from Quinn Jensen <jensenq@lineo.com>, adds MIPS support
to busybox insmod. Thanks Quinn!!!
-Erik
-rw-r--r-- | insmod.c | 131 | ||||
-rw-r--r-- | modutils/insmod.c | 131 |
2 files changed, 254 insertions, 8 deletions
@@ -20,6 +20,12 @@ | |||
20 | * I've only tested the code on mpc8xx platforms in big-endian mode. | 20 | * I've only tested the code on mpc8xx platforms in big-endian mode. |
21 | * Did some cleanup and added BB_USE_xxx_ENTRIES... | 21 | * Did some cleanup and added BB_USE_xxx_ENTRIES... |
22 | * | 22 | * |
23 | * Quinn Jensen <jensenq@lineo.com> added MIPS support 23-Feb-2001. | ||
24 | * based on modutils-2.4.2 | ||
25 | * MIPS specific support for Elf loading and relocation. | ||
26 | * Copyright 1996, 1997 Linux International. | ||
27 | * Contributed by Ralf Baechle <ralf@gnu.ai.mit.edu> | ||
28 | * | ||
23 | * Based almost entirely on the Linux modutils-2.3.11 implementation. | 29 | * Based almost entirely on the Linux modutils-2.3.11 implementation. |
24 | * Copyright 1996, 1997 Linux International. | 30 | * Copyright 1996, 1997 Linux International. |
25 | * New implementation contributed by Richard Henderson <rth@tamu.edu> | 31 | * New implementation contributed by Richard Henderson <rth@tamu.edu> |
@@ -80,6 +86,10 @@ | |||
80 | #define BB_GOT_ENTRY_SIZE 4 | 86 | #define BB_GOT_ENTRY_SIZE 4 |
81 | #endif | 87 | #endif |
82 | 88 | ||
89 | #if defined(__mips__) | ||
90 | // neither used | ||
91 | #endif | ||
92 | |||
83 | //---------------------------------------------------------------------------- | 93 | //---------------------------------------------------------------------------- |
84 | //--------modutils module.h, lines 45-242 | 94 | //--------modutils module.h, lines 45-242 |
85 | //---------------------------------------------------------------------------- | 95 | //---------------------------------------------------------------------------- |
@@ -109,7 +119,7 @@ | |||
109 | #ifndef MODUTILS_MODULE_H | 119 | #ifndef MODUTILS_MODULE_H |
110 | static const int MODUTILS_MODULE_H = 1; | 120 | static const int MODUTILS_MODULE_H = 1; |
111 | 121 | ||
112 | #ident "$Id: insmod.c,v 1.49 2001/02/20 20:47:08 andersen Exp $" | 122 | #ident "$Id: insmod.c,v 1.50 2001/02/24 20:01:53 andersen Exp $" |
113 | 123 | ||
114 | /* This file contains the structures used by the 2.0 and 2.1 kernels. | 124 | /* This file contains the structures used by the 2.0 and 2.1 kernels. |
115 | We do not use the kernel headers directly because we do not wish | 125 | We do not use the kernel headers directly because we do not wish |
@@ -315,7 +325,7 @@ int delete_module(const char *); | |||
315 | #ifndef MODUTILS_OBJ_H | 325 | #ifndef MODUTILS_OBJ_H |
316 | static const int MODUTILS_OBJ_H = 1; | 326 | static const int MODUTILS_OBJ_H = 1; |
317 | 327 | ||
318 | #ident "$Id: insmod.c,v 1.49 2001/02/20 20:47:08 andersen Exp $" | 328 | #ident "$Id: insmod.c,v 1.50 2001/02/24 20:01:53 andersen Exp $" |
319 | 329 | ||
320 | /* The relocatable object is manipulated using elfin types. */ | 330 | /* The relocatable object is manipulated using elfin types. */ |
321 | 331 | ||
@@ -361,6 +371,18 @@ static const int MODUTILS_OBJ_H = 1; | |||
361 | #define Elf32_RelM Elf32_Rela | 371 | #define Elf32_RelM Elf32_Rela |
362 | #define ELFDATAM ELFDATA2MSB | 372 | #define ELFDATAM ELFDATA2MSB |
363 | 373 | ||
374 | #elif defined(__mips__) | ||
375 | |||
376 | #define MATCH_MACHINE(x) (x == EM_MIPS || x == EM_MIPS_RS3_LE) | ||
377 | #define SHT_RELM SHT_REL | ||
378 | #define Elf32_RelM Elf32_Rel | ||
379 | #ifdef __MIPSEB__ | ||
380 | #define ELFDATAM ELFDATA2MSB | ||
381 | #endif | ||
382 | #ifdef __MIPSEL__ | ||
383 | #define ELFDATAM ELFDATA2LSB | ||
384 | #endif | ||
385 | |||
364 | #elif defined(__i386__) | 386 | #elif defined(__i386__) |
365 | 387 | ||
366 | /* presumably we can use these for anything but the SH and ARM*/ | 388 | /* presumably we can use these for anything but the SH and ARM*/ |
@@ -594,6 +616,15 @@ struct arch_got_entry { | |||
594 | }; | 616 | }; |
595 | #endif | 617 | #endif |
596 | 618 | ||
619 | #if defined(__mips__) | ||
620 | struct mips_hi16 | ||
621 | { | ||
622 | struct mips_hi16 *next; | ||
623 | Elf32_Addr *addr; | ||
624 | Elf32_Addr value; | ||
625 | }; | ||
626 | #endif | ||
627 | |||
597 | struct arch_file { | 628 | struct arch_file { |
598 | struct obj_file root; | 629 | struct obj_file root; |
599 | #if defined(BB_USE_PLT_ENTRIES) | 630 | #if defined(BB_USE_PLT_ENTRIES) |
@@ -602,6 +633,9 @@ struct arch_file { | |||
602 | #if defined(BB_USE_GOT_ENTRIES) | 633 | #if defined(BB_USE_GOT_ENTRIES) |
603 | struct obj_section *got; | 634 | struct obj_section *got; |
604 | #endif | 635 | #endif |
636 | #if defined(__mips__) | ||
637 | struct mips_hi16 *mips_hi16_list; | ||
638 | #endif | ||
605 | }; | 639 | }; |
606 | 640 | ||
607 | struct arch_symbol { | 641 | struct arch_symbol { |
@@ -724,6 +758,9 @@ struct obj_file *arch_new_file(void) | |||
724 | #if defined(BB_USE_GOT_ENTRIES) | 758 | #if defined(BB_USE_GOT_ENTRIES) |
725 | f->got = NULL; | 759 | f->got = NULL; |
726 | #endif | 760 | #endif |
761 | #if defined(__mips__) | ||
762 | f->mips_hi16_list = NULL; | ||
763 | #endif | ||
727 | 764 | ||
728 | return &f->root; | 765 | return &f->root; |
729 | } | 766 | } |
@@ -783,6 +820,8 @@ arch_apply_relocation(struct obj_file *f, | |||
783 | case R_386_NONE: | 820 | case R_386_NONE: |
784 | #elif defined(__powerpc__) | 821 | #elif defined(__powerpc__) |
785 | case R_PPC_NONE: | 822 | case R_PPC_NONE: |
823 | #elif defined(__mips__) | ||
824 | case R_MIPS_NONE: | ||
786 | #endif | 825 | #endif |
787 | break; | 826 | break; |
788 | 827 | ||
@@ -794,6 +833,8 @@ arch_apply_relocation(struct obj_file *f, | |||
794 | case R_386_32: | 833 | case R_386_32: |
795 | #elif defined(__powerpc__) | 834 | #elif defined(__powerpc__) |
796 | case R_PPC_ADDR32: | 835 | case R_PPC_ADDR32: |
836 | #elif defined(__mips__) | ||
837 | case R_MIPS_32: | ||
797 | #endif | 838 | #endif |
798 | *loc += v; | 839 | *loc += v; |
799 | break; | 840 | break; |
@@ -812,6 +853,86 @@ arch_apply_relocation(struct obj_file *f, | |||
812 | break; | 853 | break; |
813 | #endif | 854 | #endif |
814 | 855 | ||
856 | #if defined(__mips__) | ||
857 | case R_MIPS_26: | ||
858 | if (v % 4) | ||
859 | ret = obj_reloc_dangerous; | ||
860 | if ((v & 0xf0000000) != ((dot + 4) & 0xf0000000)) | ||
861 | ret = obj_reloc_overflow; | ||
862 | *loc = | ||
863 | (*loc & ~0x03ffffff) | ((*loc + (v >> 2)) & | ||
864 | 0x03ffffff); | ||
865 | break; | ||
866 | |||
867 | case R_MIPS_HI16: | ||
868 | { | ||
869 | struct mips_hi16 *n; | ||
870 | |||
871 | /* We cannot relocate this one now because we don't know the value | ||
872 | of the carry we need to add. Save the information, and let LO16 | ||
873 | do the actual relocation. */ | ||
874 | n = (struct mips_hi16 *) xmalloc(sizeof *n); | ||
875 | n->addr = loc; | ||
876 | n->value = v; | ||
877 | n->next = ifile->mips_hi16_list; | ||
878 | ifile->mips_hi16_list = n; | ||
879 | break; | ||
880 | } | ||
881 | |||
882 | case R_MIPS_LO16: | ||
883 | { | ||
884 | unsigned long insnlo = *loc; | ||
885 | Elf32_Addr val, vallo; | ||
886 | |||
887 | /* Sign extend the addend we extract from the lo insn. */ | ||
888 | vallo = ((insnlo & 0xffff) ^ 0x8000) - 0x8000; | ||
889 | |||
890 | if (ifile->mips_hi16_list != NULL) { | ||
891 | struct mips_hi16 *l; | ||
892 | |||
893 | l = ifile->mips_hi16_list; | ||
894 | while (l != NULL) { | ||
895 | struct mips_hi16 *next; | ||
896 | unsigned long insn; | ||
897 | |||
898 | /* The value for the HI16 had best be the same. */ | ||
899 | assert(v == l->value); | ||
900 | |||
901 | /* Do the HI16 relocation. Note that we actually don't | ||
902 | need to know anything about the LO16 itself, except where | ||
903 | to find the low 16 bits of the addend needed by the LO16. */ | ||
904 | insn = *l->addr; | ||
905 | val = | ||
906 | ((insn & 0xffff) << 16) + | ||
907 | vallo; | ||
908 | val += v; | ||
909 | |||
910 | /* Account for the sign extension that will happen in the | ||
911 | low bits. */ | ||
912 | val = | ||
913 | ((val >> 16) + | ||
914 | ((val & 0x8000) != | ||
915 | 0)) & 0xffff; | ||
916 | |||
917 | insn = (insn & ~0xffff) | val; | ||
918 | *l->addr = insn; | ||
919 | |||
920 | next = l->next; | ||
921 | free(l); | ||
922 | l = next; | ||
923 | } | ||
924 | |||
925 | ifile->mips_hi16_list = NULL; | ||
926 | } | ||
927 | |||
928 | /* Ok, we're done with the HI16 relocs. Now deal with the LO16. */ | ||
929 | val = v + vallo; | ||
930 | insnlo = (insnlo & ~0xffff) | (val & 0xffff); | ||
931 | *loc = insnlo; | ||
932 | break; | ||
933 | } | ||
934 | #endif | ||
935 | |||
815 | #if defined(__arm__) | 936 | #if defined(__arm__) |
816 | #elif defined(__sh__) | 937 | #elif defined(__sh__) |
817 | case R_SH_REL32: | 938 | case R_SH_REL32: |
@@ -977,6 +1098,7 @@ arch_apply_relocation(struct obj_file *f, | |||
977 | 1098 | ||
978 | int arch_create_got(struct obj_file *f) | 1099 | int arch_create_got(struct obj_file *f) |
979 | { | 1100 | { |
1101 | #if defined(BB_USE_GOT_ENTRIES) || defined(BB_USE_PLT_ENTRIES) | ||
980 | struct arch_file *ifile = (struct arch_file *) f; | 1102 | struct arch_file *ifile = (struct arch_file *) f; |
981 | int i; | 1103 | int i; |
982 | #if defined(BB_USE_GOT_ENTRIES) | 1104 | #if defined(BB_USE_GOT_ENTRIES) |
@@ -1098,6 +1220,7 @@ int arch_create_got(struct obj_file *f) | |||
1098 | BB_PLT_ENTRY_SIZE, | 1220 | BB_PLT_ENTRY_SIZE, |
1099 | plt_offset); | 1221 | plt_offset); |
1100 | #endif | 1222 | #endif |
1223 | #endif | ||
1101 | return 1; | 1224 | return 1; |
1102 | } | 1225 | } |
1103 | 1226 | ||
@@ -2772,7 +2895,7 @@ int obj_create_image(struct obj_file *f, char *image) | |||
2772 | for (sec = f->load_order; sec; sec = sec->load_next) { | 2895 | for (sec = f->load_order; sec; sec = sec->load_next) { |
2773 | char *secimg; | 2896 | char *secimg; |
2774 | 2897 | ||
2775 | if (sec->header.sh_size == 0) | 2898 | if (sec->contents == 0 || sec->header.sh_size == 0) |
2776 | continue; | 2899 | continue; |
2777 | 2900 | ||
2778 | secimg = image + (sec->header.sh_addr - base); | 2901 | secimg = image + (sec->header.sh_addr - base); |
@@ -2857,7 +2980,7 @@ struct obj_file *obj_load(FILE * fp) | |||
2857 | sec->header = section_headers[i]; | 2980 | sec->header = section_headers[i]; |
2858 | sec->idx = i; | 2981 | sec->idx = i; |
2859 | 2982 | ||
2860 | switch (sec->header.sh_type) { | 2983 | if(sec->header.sh_size) switch (sec->header.sh_type) { |
2861 | case SHT_NULL: | 2984 | case SHT_NULL: |
2862 | case SHT_NOTE: | 2985 | case SHT_NOTE: |
2863 | case SHT_NOBITS: | 2986 | case SHT_NOBITS: |
diff --git a/modutils/insmod.c b/modutils/insmod.c index 7af135902..50f272edb 100644 --- a/modutils/insmod.c +++ b/modutils/insmod.c | |||
@@ -20,6 +20,12 @@ | |||
20 | * I've only tested the code on mpc8xx platforms in big-endian mode. | 20 | * I've only tested the code on mpc8xx platforms in big-endian mode. |
21 | * Did some cleanup and added BB_USE_xxx_ENTRIES... | 21 | * Did some cleanup and added BB_USE_xxx_ENTRIES... |
22 | * | 22 | * |
23 | * Quinn Jensen <jensenq@lineo.com> added MIPS support 23-Feb-2001. | ||
24 | * based on modutils-2.4.2 | ||
25 | * MIPS specific support for Elf loading and relocation. | ||
26 | * Copyright 1996, 1997 Linux International. | ||
27 | * Contributed by Ralf Baechle <ralf@gnu.ai.mit.edu> | ||
28 | * | ||
23 | * Based almost entirely on the Linux modutils-2.3.11 implementation. | 29 | * Based almost entirely on the Linux modutils-2.3.11 implementation. |
24 | * Copyright 1996, 1997 Linux International. | 30 | * Copyright 1996, 1997 Linux International. |
25 | * New implementation contributed by Richard Henderson <rth@tamu.edu> | 31 | * New implementation contributed by Richard Henderson <rth@tamu.edu> |
@@ -80,6 +86,10 @@ | |||
80 | #define BB_GOT_ENTRY_SIZE 4 | 86 | #define BB_GOT_ENTRY_SIZE 4 |
81 | #endif | 87 | #endif |
82 | 88 | ||
89 | #if defined(__mips__) | ||
90 | // neither used | ||
91 | #endif | ||
92 | |||
83 | //---------------------------------------------------------------------------- | 93 | //---------------------------------------------------------------------------- |
84 | //--------modutils module.h, lines 45-242 | 94 | //--------modutils module.h, lines 45-242 |
85 | //---------------------------------------------------------------------------- | 95 | //---------------------------------------------------------------------------- |
@@ -109,7 +119,7 @@ | |||
109 | #ifndef MODUTILS_MODULE_H | 119 | #ifndef MODUTILS_MODULE_H |
110 | static const int MODUTILS_MODULE_H = 1; | 120 | static const int MODUTILS_MODULE_H = 1; |
111 | 121 | ||
112 | #ident "$Id: insmod.c,v 1.49 2001/02/20 20:47:08 andersen Exp $" | 122 | #ident "$Id: insmod.c,v 1.50 2001/02/24 20:01:53 andersen Exp $" |
113 | 123 | ||
114 | /* This file contains the structures used by the 2.0 and 2.1 kernels. | 124 | /* This file contains the structures used by the 2.0 and 2.1 kernels. |
115 | We do not use the kernel headers directly because we do not wish | 125 | We do not use the kernel headers directly because we do not wish |
@@ -315,7 +325,7 @@ int delete_module(const char *); | |||
315 | #ifndef MODUTILS_OBJ_H | 325 | #ifndef MODUTILS_OBJ_H |
316 | static const int MODUTILS_OBJ_H = 1; | 326 | static const int MODUTILS_OBJ_H = 1; |
317 | 327 | ||
318 | #ident "$Id: insmod.c,v 1.49 2001/02/20 20:47:08 andersen Exp $" | 328 | #ident "$Id: insmod.c,v 1.50 2001/02/24 20:01:53 andersen Exp $" |
319 | 329 | ||
320 | /* The relocatable object is manipulated using elfin types. */ | 330 | /* The relocatable object is manipulated using elfin types. */ |
321 | 331 | ||
@@ -361,6 +371,18 @@ static const int MODUTILS_OBJ_H = 1; | |||
361 | #define Elf32_RelM Elf32_Rela | 371 | #define Elf32_RelM Elf32_Rela |
362 | #define ELFDATAM ELFDATA2MSB | 372 | #define ELFDATAM ELFDATA2MSB |
363 | 373 | ||
374 | #elif defined(__mips__) | ||
375 | |||
376 | #define MATCH_MACHINE(x) (x == EM_MIPS || x == EM_MIPS_RS3_LE) | ||
377 | #define SHT_RELM SHT_REL | ||
378 | #define Elf32_RelM Elf32_Rel | ||
379 | #ifdef __MIPSEB__ | ||
380 | #define ELFDATAM ELFDATA2MSB | ||
381 | #endif | ||
382 | #ifdef __MIPSEL__ | ||
383 | #define ELFDATAM ELFDATA2LSB | ||
384 | #endif | ||
385 | |||
364 | #elif defined(__i386__) | 386 | #elif defined(__i386__) |
365 | 387 | ||
366 | /* presumably we can use these for anything but the SH and ARM*/ | 388 | /* presumably we can use these for anything but the SH and ARM*/ |
@@ -594,6 +616,15 @@ struct arch_got_entry { | |||
594 | }; | 616 | }; |
595 | #endif | 617 | #endif |
596 | 618 | ||
619 | #if defined(__mips__) | ||
620 | struct mips_hi16 | ||
621 | { | ||
622 | struct mips_hi16 *next; | ||
623 | Elf32_Addr *addr; | ||
624 | Elf32_Addr value; | ||
625 | }; | ||
626 | #endif | ||
627 | |||
597 | struct arch_file { | 628 | struct arch_file { |
598 | struct obj_file root; | 629 | struct obj_file root; |
599 | #if defined(BB_USE_PLT_ENTRIES) | 630 | #if defined(BB_USE_PLT_ENTRIES) |
@@ -602,6 +633,9 @@ struct arch_file { | |||
602 | #if defined(BB_USE_GOT_ENTRIES) | 633 | #if defined(BB_USE_GOT_ENTRIES) |
603 | struct obj_section *got; | 634 | struct obj_section *got; |
604 | #endif | 635 | #endif |
636 | #if defined(__mips__) | ||
637 | struct mips_hi16 *mips_hi16_list; | ||
638 | #endif | ||
605 | }; | 639 | }; |
606 | 640 | ||
607 | struct arch_symbol { | 641 | struct arch_symbol { |
@@ -724,6 +758,9 @@ struct obj_file *arch_new_file(void) | |||
724 | #if defined(BB_USE_GOT_ENTRIES) | 758 | #if defined(BB_USE_GOT_ENTRIES) |
725 | f->got = NULL; | 759 | f->got = NULL; |
726 | #endif | 760 | #endif |
761 | #if defined(__mips__) | ||
762 | f->mips_hi16_list = NULL; | ||
763 | #endif | ||
727 | 764 | ||
728 | return &f->root; | 765 | return &f->root; |
729 | } | 766 | } |
@@ -783,6 +820,8 @@ arch_apply_relocation(struct obj_file *f, | |||
783 | case R_386_NONE: | 820 | case R_386_NONE: |
784 | #elif defined(__powerpc__) | 821 | #elif defined(__powerpc__) |
785 | case R_PPC_NONE: | 822 | case R_PPC_NONE: |
823 | #elif defined(__mips__) | ||
824 | case R_MIPS_NONE: | ||
786 | #endif | 825 | #endif |
787 | break; | 826 | break; |
788 | 827 | ||
@@ -794,6 +833,8 @@ arch_apply_relocation(struct obj_file *f, | |||
794 | case R_386_32: | 833 | case R_386_32: |
795 | #elif defined(__powerpc__) | 834 | #elif defined(__powerpc__) |
796 | case R_PPC_ADDR32: | 835 | case R_PPC_ADDR32: |
836 | #elif defined(__mips__) | ||
837 | case R_MIPS_32: | ||
797 | #endif | 838 | #endif |
798 | *loc += v; | 839 | *loc += v; |
799 | break; | 840 | break; |
@@ -812,6 +853,86 @@ arch_apply_relocation(struct obj_file *f, | |||
812 | break; | 853 | break; |
813 | #endif | 854 | #endif |
814 | 855 | ||
856 | #if defined(__mips__) | ||
857 | case R_MIPS_26: | ||
858 | if (v % 4) | ||
859 | ret = obj_reloc_dangerous; | ||
860 | if ((v & 0xf0000000) != ((dot + 4) & 0xf0000000)) | ||
861 | ret = obj_reloc_overflow; | ||
862 | *loc = | ||
863 | (*loc & ~0x03ffffff) | ((*loc + (v >> 2)) & | ||
864 | 0x03ffffff); | ||
865 | break; | ||
866 | |||
867 | case R_MIPS_HI16: | ||
868 | { | ||
869 | struct mips_hi16 *n; | ||
870 | |||
871 | /* We cannot relocate this one now because we don't know the value | ||
872 | of the carry we need to add. Save the information, and let LO16 | ||
873 | do the actual relocation. */ | ||
874 | n = (struct mips_hi16 *) xmalloc(sizeof *n); | ||
875 | n->addr = loc; | ||
876 | n->value = v; | ||
877 | n->next = ifile->mips_hi16_list; | ||
878 | ifile->mips_hi16_list = n; | ||
879 | break; | ||
880 | } | ||
881 | |||
882 | case R_MIPS_LO16: | ||
883 | { | ||
884 | unsigned long insnlo = *loc; | ||
885 | Elf32_Addr val, vallo; | ||
886 | |||
887 | /* Sign extend the addend we extract from the lo insn. */ | ||
888 | vallo = ((insnlo & 0xffff) ^ 0x8000) - 0x8000; | ||
889 | |||
890 | if (ifile->mips_hi16_list != NULL) { | ||
891 | struct mips_hi16 *l; | ||
892 | |||
893 | l = ifile->mips_hi16_list; | ||
894 | while (l != NULL) { | ||
895 | struct mips_hi16 *next; | ||
896 | unsigned long insn; | ||
897 | |||
898 | /* The value for the HI16 had best be the same. */ | ||
899 | assert(v == l->value); | ||
900 | |||
901 | /* Do the HI16 relocation. Note that we actually don't | ||
902 | need to know anything about the LO16 itself, except where | ||
903 | to find the low 16 bits of the addend needed by the LO16. */ | ||
904 | insn = *l->addr; | ||
905 | val = | ||
906 | ((insn & 0xffff) << 16) + | ||
907 | vallo; | ||
908 | val += v; | ||
909 | |||
910 | /* Account for the sign extension that will happen in the | ||
911 | low bits. */ | ||
912 | val = | ||
913 | ((val >> 16) + | ||
914 | ((val & 0x8000) != | ||
915 | 0)) & 0xffff; | ||
916 | |||
917 | insn = (insn & ~0xffff) | val; | ||
918 | *l->addr = insn; | ||
919 | |||
920 | next = l->next; | ||
921 | free(l); | ||
922 | l = next; | ||
923 | } | ||
924 | |||
925 | ifile->mips_hi16_list = NULL; | ||
926 | } | ||
927 | |||
928 | /* Ok, we're done with the HI16 relocs. Now deal with the LO16. */ | ||
929 | val = v + vallo; | ||
930 | insnlo = (insnlo & ~0xffff) | (val & 0xffff); | ||
931 | *loc = insnlo; | ||
932 | break; | ||
933 | } | ||
934 | #endif | ||
935 | |||
815 | #if defined(__arm__) | 936 | #if defined(__arm__) |
816 | #elif defined(__sh__) | 937 | #elif defined(__sh__) |
817 | case R_SH_REL32: | 938 | case R_SH_REL32: |
@@ -977,6 +1098,7 @@ arch_apply_relocation(struct obj_file *f, | |||
977 | 1098 | ||
978 | int arch_create_got(struct obj_file *f) | 1099 | int arch_create_got(struct obj_file *f) |
979 | { | 1100 | { |
1101 | #if defined(BB_USE_GOT_ENTRIES) || defined(BB_USE_PLT_ENTRIES) | ||
980 | struct arch_file *ifile = (struct arch_file *) f; | 1102 | struct arch_file *ifile = (struct arch_file *) f; |
981 | int i; | 1103 | int i; |
982 | #if defined(BB_USE_GOT_ENTRIES) | 1104 | #if defined(BB_USE_GOT_ENTRIES) |
@@ -1098,6 +1220,7 @@ int arch_create_got(struct obj_file *f) | |||
1098 | BB_PLT_ENTRY_SIZE, | 1220 | BB_PLT_ENTRY_SIZE, |
1099 | plt_offset); | 1221 | plt_offset); |
1100 | #endif | 1222 | #endif |
1223 | #endif | ||
1101 | return 1; | 1224 | return 1; |
1102 | } | 1225 | } |
1103 | 1226 | ||
@@ -2772,7 +2895,7 @@ int obj_create_image(struct obj_file *f, char *image) | |||
2772 | for (sec = f->load_order; sec; sec = sec->load_next) { | 2895 | for (sec = f->load_order; sec; sec = sec->load_next) { |
2773 | char *secimg; | 2896 | char *secimg; |
2774 | 2897 | ||
2775 | if (sec->header.sh_size == 0) | 2898 | if (sec->contents == 0 || sec->header.sh_size == 0) |
2776 | continue; | 2899 | continue; |
2777 | 2900 | ||
2778 | secimg = image + (sec->header.sh_addr - base); | 2901 | secimg = image + (sec->header.sh_addr - base); |
@@ -2857,7 +2980,7 @@ struct obj_file *obj_load(FILE * fp) | |||
2857 | sec->header = section_headers[i]; | 2980 | sec->header = section_headers[i]; |
2858 | sec->idx = i; | 2981 | sec->idx = i; |
2859 | 2982 | ||
2860 | switch (sec->header.sh_type) { | 2983 | if(sec->header.sh_size) switch (sec->header.sh_type) { |
2861 | case SHT_NULL: | 2984 | case SHT_NULL: |
2862 | case SHT_NOTE: | 2985 | case SHT_NOTE: |
2863 | case SHT_NOBITS: | 2986 | case SHT_NOBITS: |