aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEric Andersen <andersen@codepoet.org>2003-08-13 19:56:33 +0000
committerEric Andersen <andersen@codepoet.org>2003-08-13 19:56:33 +0000
commitbf83355dda609db2d028ecb740e1daa5cfbe15aa (patch)
treed7d26bee7bf6151cf291453a13acabcf958f1d02
parent4456f25e8fa584fa0a72e0a64961e384e5de587f (diff)
downloadbusybox-w32-bf83355dda609db2d028ecb740e1daa5cfbe15aa.tar.gz
busybox-w32-bf83355dda609db2d028ecb740e1daa5cfbe15aa.tar.bz2
busybox-w32-bf83355dda609db2d028ecb740e1daa5cfbe15aa.zip
Patch from Paul Mundt (lethal) adding sh64 insmod support for busybox
-rw-r--r--modutils/insmod.c82
1 files changed, 72 insertions, 10 deletions
diff --git a/modutils/insmod.c b/modutils/insmod.c
index 84617fa48..c5cab1997 100644
--- a/modutils/insmod.c
+++ b/modutils/insmod.c
@@ -2,7 +2,7 @@
2/* 2/*
3 * Mini insmod implementation for busybox 3 * Mini insmod implementation for busybox
4 * 4 *
5 * This version of insmod supports x86, ARM, SH3/4, powerpc, m68k, 5 * This version of insmod supports x86, ARM, SH3/4/5, powerpc, m68k,
6 * MIPS, and v850e. 6 * MIPS, and v850e.
7 * 7 *
8 * Copyright (C) 1999,2000 by Lineo, inc. and Erik Andersen 8 * Copyright (C) 1999,2000 by Lineo, inc. and Erik Andersen
@@ -19,6 +19,11 @@
19 * very minor changes required to also work with StrongArm and presumably 19 * very minor changes required to also work with StrongArm and presumably
20 * all ARM based systems. 20 * all ARM based systems.
21 * 21 *
22 * Paul Mundt <lethal@linux-sh.org> 08-Aug-2003.
23 * Integrated support for sh64 (SH-5), from preliminary modutils
24 * patches from Benedict Gaster <benedict.gaster@superh.com>.
25 * Currently limited to support for 32bit ABI.
26 *
22 * Magnus Damm <damm@opensource.se> 22-May-2002. 27 * Magnus Damm <damm@opensource.se> 22-May-2002.
23 * The plt and got code are now using the same structs. 28 * The plt and got code are now using the same structs.
24 * Added generic linked list code to fully support PowerPC. 29 * Added generic linked list code to fully support PowerPC.
@@ -182,17 +187,18 @@
182#define Elf32_RelM Elf32_Rela 187#define Elf32_RelM Elf32_Rela
183#define ELFCLASSM ELFCLASS32 188#define ELFCLASSM ELFCLASS32
184 189
185/* the SH changes have only been tested on the SH4 in =little endian= mode */ 190/* the SH changes have only been tested in =little endian= mode */
186/* I'm not sure about big endian, so let's warn: */ 191/* I'm not sure about big endian, so let's warn: */
187 192
188#if (defined(__SH4__) || defined(__SH3__)) && defined(__BIG_ENDIAN__) 193#if defined(__sh__) && defined(__BIG_ENDIAN__)
189#error insmod.c may require changes for use on big endian SH4/SH3 194#error insmod.c may require changes for use on big endian SH
190#endif 195#endif
191 196
192/* it may or may not work on the SH1/SH2... So let's error on those 197/* it may or may not work on the SH1/SH2... So let's error on those
193 also */ 198 also */
194#if (defined(__sh__) && (!(defined(__SH3__) || defined(__SH4__)))) 199#if ((!(defined(__SH3__) || defined(__SH4__) || defined(__SH5__)))) && \
195#error insmod.c may require changes for non-SH3/SH4 use 200 (defined(__sh__))
201#error insmod.c may require changes for SH1 or SH2 use
196#endif 202#endif
197#endif 203#endif
198 204
@@ -247,7 +253,7 @@
247#ifndef MODUTILS_MODULE_H 253#ifndef MODUTILS_MODULE_H
248static const int MODUTILS_MODULE_H = 1; 254static const int MODUTILS_MODULE_H = 1;
249 255
250#ident "$Id: insmod.c,v 1.99 2003/07/22 08:56:50 andersen Exp $" 256#ident "$Id: insmod.c,v 1.100 2003/08/13 19:56:33 andersen Exp $"
251 257
252/* This file contains the structures used by the 2.0 and 2.1 kernels. 258/* This file contains the structures used by the 2.0 and 2.1 kernels.
253 We do not use the kernel headers directly because we do not wish 259 We do not use the kernel headers directly because we do not wish
@@ -468,7 +474,7 @@ int delete_module(const char *);
468#ifndef MODUTILS_OBJ_H 474#ifndef MODUTILS_OBJ_H
469static const int MODUTILS_OBJ_H = 1; 475static const int MODUTILS_OBJ_H = 1;
470 476
471#ident "$Id: insmod.c,v 1.99 2003/07/22 08:56:50 andersen Exp $" 477#ident "$Id: insmod.c,v 1.100 2003/08/13 19:56:33 andersen Exp $"
472 478
473/* The relocatable object is manipulated using elfin types. */ 479/* The relocatable object is manipulated using elfin types. */
474 480
@@ -1201,7 +1207,51 @@ arch_apply_relocation(struct obj_file *f,
1201 *loc = v - got; 1207 *loc = v - got;
1202 break; 1208 break;
1203 1209
1204#endif 1210#if defined(__SH5__)
1211 case R_SH_IMM_MEDLOW16:
1212 case R_SH_IMM_LOW16:
1213 {
1214 Elf32_Addr word;
1215
1216 if (ELF32_R_TYPE(rel->r_info) == R_SH_IMM_MEDLOW16)
1217 v >>= 16;
1218
1219 /*
1220 * movi and shori have the format:
1221 *
1222 * | op | imm | reg | reserved |
1223 * 31..26 25..10 9.. 4 3 .. 0
1224 *
1225 * so we simply mask and or in imm.
1226 */
1227 word = *loc & ~0x3fffc00;
1228 word |= (v & 0xffff) << 10;
1229
1230 *loc = word;
1231
1232 break;
1233 }
1234
1235 case R_SH_IMM_MEDLOW16_PCREL:
1236 case R_SH_IMM_LOW16_PCREL:
1237 {
1238 Elf32_Addr word;
1239
1240 word = *loc & ~0x3fffc00;
1241
1242 v -= dot;
1243
1244 if (ELF32_R_TYPE(rel->r_info) == R_SH_IMM_MEDLOW16_PCREL)
1245 v >>= 16;
1246
1247 word |= (v & 0xffff) << 10;
1248
1249 *loc = word;
1250
1251 break;
1252 }
1253#endif /* __SH5__ */
1254#endif /* __sh__ */
1205 1255
1206 default: 1256 default:
1207 printf("Warning: unhandled reloc %d\n",(int)ELF32_R_TYPE(rel->r_info)); 1257 printf("Warning: unhandled reloc %d\n",(int)ELF32_R_TYPE(rel->r_info));
@@ -3470,14 +3520,26 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits)
3470 3520
3471 /* Insert all symbols into the hash table. */ 3521 /* Insert all symbols into the hash table. */
3472 for (j = 1, ++sym; j < nsym; ++j, ++sym) { 3522 for (j = 1, ++sym; j < nsym; ++j, ++sym) {
3523 ElfW(Addr) val = sym->st_value;
3473 const char *name; 3524 const char *name;
3474 if (sym->st_name) 3525 if (sym->st_name)
3475 name = strtab + sym->st_name; 3526 name = strtab + sym->st_name;
3476 else 3527 else
3477 name = f->sections[sym->st_shndx]->name; 3528 name = f->sections[sym->st_shndx]->name;
3478 3529
3530#if defined(__SH5__)
3531 /*
3532 * For sh64 it is possible that the target of a branch
3533 * requires a mode switch (32 to 16 and back again).
3534 *
3535 * This is implied by the lsb being set in the target
3536 * address for SHmedia mode and clear for SHcompact.
3537 */
3538 val |= sym->st_other & 4;
3539#endif
3540
3479 obj_add_symbol(f, name, j, sym->st_info, sym->st_shndx, 3541 obj_add_symbol(f, name, j, sym->st_info, sym->st_shndx,
3480 sym->st_value, sym->st_size); 3542 val, sym->st_size);
3481 } 3543 }
3482 } 3544 }
3483 break; 3545 break;