diff options
Diffstat (limited to 'arch/cris/kernel/module.c')
-rw-r--r-- | arch/cris/kernel/module.c | 39 |
1 files changed, 16 insertions, 23 deletions
diff --git a/arch/cris/kernel/module.c b/arch/cris/kernel/module.c index f1d3e784f30c..11b867df8617 100644 --- a/arch/cris/kernel/module.c +++ b/arch/cris/kernel/module.c | |||
@@ -32,7 +32,7 @@ void *module_alloc(unsigned long size) | |||
32 | { | 32 | { |
33 | if (size == 0) | 33 | if (size == 0) |
34 | return NULL; | 34 | return NULL; |
35 | return vmalloc(size); | 35 | return vmalloc_exec(size); |
36 | } | 36 | } |
37 | 37 | ||
38 | 38 | ||
@@ -59,26 +59,8 @@ int apply_relocate(Elf32_Shdr *sechdrs, | |||
59 | unsigned int relsec, | 59 | unsigned int relsec, |
60 | struct module *me) | 60 | struct module *me) |
61 | { | 61 | { |
62 | unsigned int i; | 62 | printk(KERN_ERR "module %s: REL relocation unsupported\n", me->name); |
63 | Elf32_Rel *rel = (void *)sechdrs[relsec].sh_addr; | 63 | return -ENOEXEC; |
64 | Elf32_Sym *sym; | ||
65 | uint32_t *location; | ||
66 | |||
67 | DEBUGP("Applying relocate section %u to %u\n", relsec, | ||
68 | sechdrs[relsec].sh_info); | ||
69 | for (i = 0; i < sechdrs[relsec].sh_size / sizeof(*rel); i++) { | ||
70 | /* This is where to make the change */ | ||
71 | location = (void *)sechdrs[sechdrs[relsec].sh_info].sh_offset | ||
72 | + rel[i].r_offset; | ||
73 | /* This is the symbol it is referring to. Note that all | ||
74 | undefined symbols have been resolved. */ | ||
75 | sym = (Elf32_Sym *)sechdrs[symindex].sh_addr | ||
76 | + ELF32_R_SYM(rel[i].r_info); | ||
77 | |||
78 | /* We add the value into the location given */ | ||
79 | *location += sym->st_value; | ||
80 | } | ||
81 | return 0; | ||
82 | } | 64 | } |
83 | 65 | ||
84 | int apply_relocate_add(Elf32_Shdr *sechdrs, | 66 | int apply_relocate_add(Elf32_Shdr *sechdrs, |
@@ -90,7 +72,7 @@ int apply_relocate_add(Elf32_Shdr *sechdrs, | |||
90 | unsigned int i; | 72 | unsigned int i; |
91 | Elf32_Rela *rela = (void *)sechdrs[relsec].sh_addr; | 73 | Elf32_Rela *rela = (void *)sechdrs[relsec].sh_addr; |
92 | 74 | ||
93 | DEBUGP ("Applying relocate section %u to %u\n", relsec, | 75 | DEBUGP ("Applying add relocate section %u to %u\n", relsec, |
94 | sechdrs[relsec].sh_info); | 76 | sechdrs[relsec].sh_info); |
95 | 77 | ||
96 | for (i = 0; i < sechdrs[relsec].sh_size / sizeof (*rela); i++) { | 78 | for (i = 0; i < sechdrs[relsec].sh_size / sizeof (*rela); i++) { |
@@ -103,7 +85,18 @@ int apply_relocate_add(Elf32_Shdr *sechdrs, | |||
103 | Elf32_Sym *sym | 85 | Elf32_Sym *sym |
104 | = ((Elf32_Sym *)sechdrs[symindex].sh_addr | 86 | = ((Elf32_Sym *)sechdrs[symindex].sh_addr |
105 | + ELF32_R_SYM (rela[i].r_info)); | 87 | + ELF32_R_SYM (rela[i].r_info)); |
106 | *loc = sym->st_value + rela[i].r_addend; | 88 | switch (ELF32_R_TYPE(rela[i].r_info)) { |
89 | case R_CRIS_32: | ||
90 | *loc = sym->st_value + rela[i].r_addend; | ||
91 | break; | ||
92 | case R_CRIS_32_PCREL: | ||
93 | *loc = sym->st_value - (unsigned)loc + rela[i].r_addend - 4; | ||
94 | break; | ||
95 | default: | ||
96 | printk(KERN_ERR "module %s: Unknown relocation: %u\n", | ||
97 | me->name, ELF32_R_TYPE(rela[i].r_info)); | ||
98 | return -ENOEXEC; | ||
99 | } | ||
107 | } | 100 | } |
108 | 101 | ||
109 | return 0; | 102 | return 0; |