metadata.c (176487) | metadata.c (176489) |
---|---|
1/*- 2 * Copyright (c) 1998 Michael Smith <msmith@freebsd.org> 3 * Copyright (C) 2007-2008 Semihalf, Piotr Kruszynski <ppk@semihalf.com> 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: --- 12 unchanged lines hidden (view full) --- 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28#include <sys/cdefs.h> | 1/*- 2 * Copyright (c) 1998 Michael Smith <msmith@freebsd.org> 3 * Copyright (C) 2007-2008 Semihalf, Piotr Kruszynski <ppk@semihalf.com> 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: --- 12 unchanged lines hidden (view full) --- 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28#include <sys/cdefs.h> |
29__FBSDID("$FreeBSD: head/sys/boot/powerpc/uboot/metadata.c 176487 2008-02-23 19:08:25Z marcel $"); | 29__FBSDID("$FreeBSD: head/sys/boot/powerpc/uboot/metadata.c 176489 2008-02-23 19:43:29Z marcel $"); |
30 31#include <stand.h> 32#include <sys/param.h> 33#include <sys/reboot.h> 34#include <sys/linker.h> 35 36#include <machine/elf.h> 37#include <machine/metadata.h> 38#include <machine/bootinfo.h> 39 40#include "api_public.h" 41#include "bootstrap.h" 42#include "glue.h" 43 44/* 45 * Return a 'boothowto' value corresponding to the kernel arguments in 46 * (kargs) and any relevant environment variables. 47 */ | 30 31#include <stand.h> 32#include <sys/param.h> 33#include <sys/reboot.h> 34#include <sys/linker.h> 35 36#include <machine/elf.h> 37#include <machine/metadata.h> 38#include <machine/bootinfo.h> 39 40#include "api_public.h" 41#include "bootstrap.h" 42#include "glue.h" 43 44/* 45 * Return a 'boothowto' value corresponding to the kernel arguments in 46 * (kargs) and any relevant environment variables. 47 */ |
48static struct | 48static struct |
49{ | 49{ |
50 const char *ev; 51 int mask; | 50 const char *ev; 51 int mask; |
52} howto_names[] = { | 52} howto_names[] = { |
53 {"boot_askname", RB_ASKNAME}, 54 {"boot_cdrom", RB_CDROM}, 55 {"boot_ddb", RB_KDB}, 56 {"boot_dfltroot", RB_DFLTROOT}, 57 {"boot_gdb", RB_GDB}, 58 {"boot_multicons", RB_MULTIPLE}, 59 {"boot_mute", RB_MUTE}, 60 {"boot_pause", RB_PAUSE}, 61 {"boot_serial", RB_SERIAL}, 62 {"boot_single", RB_SINGLE}, 63 {"boot_verbose", RB_VERBOSE}, 64 {NULL, 0} | 53 {"boot_askname", RB_ASKNAME}, 54 {"boot_cdrom", RB_CDROM}, 55 {"boot_ddb", RB_KDB}, 56 {"boot_dfltroot", RB_DFLTROOT}, 57 {"boot_gdb", RB_GDB}, 58 {"boot_multicons", RB_MULTIPLE}, 59 {"boot_mute", RB_MUTE}, 60 {"boot_pause", RB_PAUSE}, 61 {"boot_serial", RB_SERIAL}, 62 {"boot_single", RB_SINGLE}, 63 {"boot_verbose", RB_VERBOSE}, 64 {NULL, 0} |
65}; 66 67static int 68md_getboothowto(char *kargs) 69{ | 65}; 66 67static int 68md_getboothowto(char *kargs) 69{ |
70 char *cp; 71 int howto; 72 int active; 73 int i; 74 75 /* Parse kargs */ 76 howto = 0; 77 if (kargs != NULL) { 78 cp = kargs; 79 active = 0; 80 while (*cp != 0) { 81 if (!active && (*cp == '-')) { 82 active = 1; 83 } else if (active) 84 switch (*cp) { 85 case 'a': 86 howto |= RB_ASKNAME; 87 break; 88 case 'C': 89 howto |= RB_CDROM; 90 break; 91 case 'd': 92 howto |= RB_KDB; 93 break; 94 case 'D': 95 howto |= RB_MULTIPLE; 96 break; 97 case 'm': 98 howto |= RB_MUTE; 99 break; 100 case 'g': 101 howto |= RB_GDB; 102 break; 103 case 'h': 104 howto |= RB_SERIAL; 105 break; 106 case 'p': 107 howto |= RB_PAUSE; 108 break; 109 case 'r': 110 howto |= RB_DFLTROOT; 111 break; 112 case 's': 113 howto |= RB_SINGLE; 114 break; 115 case 'v': 116 howto |= RB_VERBOSE; 117 break; 118 default: 119 active = 0; 120 break; | 70 char *cp; 71 int howto; 72 int active; 73 int i; 74 75 /* Parse kargs */ 76 howto = 0; 77 if (kargs != NULL) { 78 cp = kargs; 79 active = 0; 80 while (*cp != 0) { 81 if (!active && (*cp == '-')) 82 active = 1; 83 else if (active) 84 switch (*cp) { 85 case 'a': 86 howto |= RB_ASKNAME; 87 break; 88 case 'C': 89 howto |= RB_CDROM; 90 break; 91 case 'd': 92 howto |= RB_KDB; 93 break; 94 case 'D': 95 howto |= RB_MULTIPLE; 96 break; 97 case 'm': 98 howto |= RB_MUTE; 99 break; 100 case 'g': 101 howto |= RB_GDB; 102 break; 103 case 'h': 104 howto |= RB_SERIAL; 105 break; 106 case 'p': 107 howto |= RB_PAUSE; 108 break; 109 case 'r': 110 howto |= RB_DFLTROOT; 111 break; 112 case 's': 113 howto |= RB_SINGLE; 114 break; 115 case 'v': 116 howto |= RB_VERBOSE; 117 break; 118 default: 119 active = 0; 120 break; 121 } 122 cp++; |
121 } | 123 } |
122 cp++; | |
123 } | 124 } |
124 } 125 /* get equivalents from the environment */ 126 for (i = 0; howto_names[i].ev != NULL; i++) 127 if (getenv(howto_names[i].ev) != NULL) 128 howto |= howto_names[i].mask; 129 if (!strcmp(getenv("console"), "comconsole")) 130 howto |= RB_SERIAL; 131 if (!strcmp(getenv("console"), "nullconsole")) 132 howto |= RB_MUTE; 133 return(howto); | 125 126 /* get equivalents from the environment */ 127 for (i = 0; howto_names[i].ev != NULL; i++) { 128 if (getenv(howto_names[i].ev) != NULL) 129 howto |= howto_names[i].mask; 130 } 131 if (!strcmp(getenv("console"), "comconsole")) 132 howto |= RB_SERIAL; 133 if (!strcmp(getenv("console"), "nullconsole")) 134 howto |= RB_MUTE; 135 136 return(howto); |
134} 135 136/* 137 * Copy the environment into the load area starting at (addr). 138 * Each variable is formatted as <name>=<value>, with a single nul 139 * separating each variable, and a double nul terminating the environment. 140 */ 141static vm_offset_t 142md_copyenv(vm_offset_t addr) 143{ | 137} 138 139/* 140 * Copy the environment into the load area starting at (addr). 141 * Each variable is formatted as <name>=<value>, with a single nul 142 * separating each variable, and a double nul terminating the environment. 143 */ 144static vm_offset_t 145md_copyenv(vm_offset_t addr) 146{ |
144 struct env_var *ep; 145 146 /* traverse the environment */ 147 for (ep = environ; ep != NULL; ep = ep->ev_next) { 148 archsw.arch_copyin(ep->ev_name, addr, strlen(ep->ev_name)); 149 addr += strlen(ep->ev_name); 150 archsw.arch_copyin("=", addr, 1); 151 addr++; 152 if (ep->ev_value != NULL) { 153 archsw.arch_copyin(ep->ev_value, addr, strlen(ep->ev_value)); 154 addr += strlen(ep->ev_value); | 147 struct env_var *ep; 148 149 /* traverse the environment */ 150 for (ep = environ; ep != NULL; ep = ep->ev_next) { 151 archsw.arch_copyin(ep->ev_name, addr, strlen(ep->ev_name)); 152 addr += strlen(ep->ev_name); 153 archsw.arch_copyin("=", addr, 1); 154 addr++; 155 if (ep->ev_value != NULL) { 156 archsw.arch_copyin(ep->ev_value, addr, 157 strlen(ep->ev_value)); 158 addr += strlen(ep->ev_value); 159 } 160 archsw.arch_copyin("", addr, 1); 161 addr++; |
155 } 156 archsw.arch_copyin("", addr, 1); 157 addr++; | 162 } 163 archsw.arch_copyin("", addr, 1); 164 addr++; |
158 } 159 archsw.arch_copyin("", addr, 1); 160 addr++; 161 return(addr); | 165 return(addr); |
162} 163 164/* 165 * Copy module-related data into the load area, where it can be 166 * used as a directory for loaded modules. 167 * 168 * Module data is presented in a self-describing format. Each datum 169 * is preceded by a 32-bit identifier and a 32-bit size field. 170 * 171 * Currently, the following data are saved: 172 * 173 * MOD_NAME (variable) module name (string) 174 * MOD_TYPE (variable) module type (string) 175 * MOD_ARGS (variable) module parameters (string) 176 * MOD_ADDR sizeof(vm_offset_t) module load address 177 * MOD_SIZE sizeof(size_t) module size 178 * MOD_METADATA (variable) type-specific metadata 179 */ | 166} 167 168/* 169 * Copy module-related data into the load area, where it can be 170 * used as a directory for loaded modules. 171 * 172 * Module data is presented in a self-describing format. Each datum 173 * is preceded by a 32-bit identifier and a 32-bit size field. 174 * 175 * Currently, the following data are saved: 176 * 177 * MOD_NAME (variable) module name (string) 178 * MOD_TYPE (variable) module type (string) 179 * MOD_ARGS (variable) module parameters (string) 180 * MOD_ADDR sizeof(vm_offset_t) module load address 181 * MOD_SIZE sizeof(size_t) module size 182 * MOD_METADATA (variable) type-specific metadata 183 */ |
180#define COPY32(v, a, c) { \ | 184#define COPY32(v, a, c) { \ |
181 u_int32_t x = (v); \ 182 if (c) \ | 185 u_int32_t x = (v); \ 186 if (c) \ |
183 archsw.arch_copyin(&x, a, sizeof(x)); \ | 187 archsw.arch_copyin(&x, a, sizeof(x)); \ |
184 a += sizeof(x); \ 185} 186 | 188 a += sizeof(x); \ 189} 190 |
187#define MOD_STR(t, a, s, c) { \ | 191#define MOD_STR(t, a, s, c) { \ |
188 COPY32(t, a, c); \ 189 COPY32(strlen(s) + 1, a, c) \ 190 if (c) \ | 192 COPY32(t, a, c); \ 193 COPY32(strlen(s) + 1, a, c) \ 194 if (c) \ |
191 archsw.arch_copyin(s, a, strlen(s) + 1);\ | 195 archsw.arch_copyin(s, a, strlen(s) + 1);\ |
192 a += roundup(strlen(s) + 1, sizeof(u_long));\ 193} 194 | 196 a += roundup(strlen(s) + 1, sizeof(u_long));\ 197} 198 |
195#define MOD_NAME(a, s, c) MOD_STR(MODINFO_NAME, a, s, c) 196#define MOD_TYPE(a, s, c) MOD_STR(MODINFO_TYPE, a, s, c) 197#define MOD_ARGS(a, s, c) MOD_STR(MODINFO_ARGS, a, s, c) | 199#define MOD_NAME(a, s, c) MOD_STR(MODINFO_NAME, a, s, c) 200#define MOD_TYPE(a, s, c) MOD_STR(MODINFO_TYPE, a, s, c) 201#define MOD_ARGS(a, s, c) MOD_STR(MODINFO_ARGS, a, s, c) |
198 | 202 |
199#define MOD_VAR(t, a, s, c) { \ | 203#define MOD_VAR(t, a, s, c) { \ |
200 COPY32(t, a, c); \ 201 COPY32(sizeof(s), a, c); \ 202 if (c) \ | 204 COPY32(t, a, c); \ 205 COPY32(sizeof(s), a, c); \ 206 if (c) \ |
203 archsw.arch_copyin(&s, a, sizeof(s)); \ | 207 archsw.arch_copyin(&s, a, sizeof(s)); \ |
204 a += roundup(sizeof(s), sizeof(u_long)); \ 205} 206 | 208 a += roundup(sizeof(s), sizeof(u_long)); \ 209} 210 |
207#define MOD_ADDR(a, s, c) MOD_VAR(MODINFO_ADDR, a, s, c) 208#define MOD_SIZE(a, s, c) MOD_VAR(MODINFO_SIZE, a, s, c) | 211#define MOD_ADDR(a, s, c) MOD_VAR(MODINFO_ADDR, a, s, c) 212#define MOD_SIZE(a, s, c) MOD_VAR(MODINFO_SIZE, a, s, c) |
209 | 213 |
210#define MOD_METADATA(a, mm, c) { \ | 214#define MOD_METADATA(a, mm, c) { \ |
211 COPY32(MODINFO_METADATA | mm->md_type, a, c);\ 212 COPY32(mm->md_size, a, c); \ 213 if (c) \ | 215 COPY32(MODINFO_METADATA | mm->md_type, a, c);\ 216 COPY32(mm->md_size, a, c); \ 217 if (c) \ |
214 archsw.arch_copyin(mm->md_data, a, mm->md_size);\ | 218 archsw.arch_copyin(mm->md_data, a, mm->md_size);\ |
215 a += roundup(mm->md_size, sizeof(u_long)); \ 216} 217 | 219 a += roundup(mm->md_size, sizeof(u_long)); \ 220} 221 |
218#define MOD_END(a, c) { \ | 222#define MOD_END(a, c) { \ |
219 COPY32(MODINFO_END, a, c); \ 220 COPY32(0, a, c); \ 221} 222 223static vm_offset_t 224md_copymodules(vm_offset_t addr) 225{ | 223 COPY32(MODINFO_END, a, c); \ 224 COPY32(0, a, c); \ 225} 226 227static vm_offset_t 228md_copymodules(vm_offset_t addr) 229{ |
226 struct preloaded_file *fp; 227 struct file_metadata *md; 228 int c; | 230 struct preloaded_file *fp; 231 struct file_metadata *md; 232 int c; |
229 | 233 |
230 c = addr != 0; 231 /* start with the first module on the list, should be the kernel */ 232 for (fp = file_findfile(NULL, NULL); fp != NULL; fp = fp->f_next) { | 234 c = addr != 0; 235 /* start with the first module on the list, should be the kernel */ 236 for (fp = file_findfile(NULL, NULL); fp != NULL; fp = fp->f_next) { |
233 | 237 |
234 MOD_NAME(addr, fp->f_name, c); /* this field must come first */ 235 MOD_TYPE(addr, fp->f_type, c); 236 if (fp->f_args) 237 MOD_ARGS(addr, fp->f_args, c); 238 MOD_ADDR(addr, fp->f_addr, c); 239 MOD_SIZE(addr, fp->f_size, c); 240 for (md = fp->f_metadata; md != NULL; md = md->md_next) { 241 if (!(md->md_type & MODINFOMD_NOCOPY)) { 242 MOD_METADATA(addr, md, c); 243 } | 238 MOD_NAME(addr, fp->f_name, c); /* this field must be first */ 239 MOD_TYPE(addr, fp->f_type, c); 240 if (fp->f_args) 241 MOD_ARGS(addr, fp->f_args, c); 242 MOD_ADDR(addr, fp->f_addr, c); 243 MOD_SIZE(addr, fp->f_size, c); 244 for (md = fp->f_metadata; md != NULL; md = md->md_next) { 245 if (!(md->md_type & MODINFOMD_NOCOPY)) 246 MOD_METADATA(addr, md, c); 247 } |
244 } | 248 } |
245 } 246 MOD_END(addr, c); 247 return(addr); | 249 MOD_END(addr, c); 250 return(addr); |
248} 249 250/* 251 * Prepare the bootinfo structure. Put a ptr to the allocated struct in addr, 252 * return size. 253 */ 254static int 255md_bootinfo(struct bootinfo **addr) 256{ | 251} 252 253/* 254 * Prepare the bootinfo structure. Put a ptr to the allocated struct in addr, 255 * return size. 256 */ 257static int 258md_bootinfo(struct bootinfo **addr) 259{ |
257#define TMP_MAX_ETH 8 258#define TMP_MAX_MR 8 | 260#define TMP_MAX_ETH 8 261#define TMP_MAX_MR 8 |
259 struct bootinfo *bi; 260 struct bi_mem_region tmp_mr[TMP_MAX_MR]; 261 struct bi_eth_addr tmp_eth[TMP_MAX_ETH]; 262 struct sys_info *si; 263 char *str, *end; 264 const char *env; 265 void *ptr; 266 u_int8_t tmp_addr[6]; --- 75 unchanged lines hidden (view full) --- 342 * - The 'boothowto' argument is constructed 343 * - The 'bootdev' argument is constructed 344 * - The kernel environment is copied into kernel space. 345 * - Module metadata are formatted and placed in kernel space. 346 */ 347int 348md_load(char *args, vm_offset_t *modulep) 349{ | 262 struct bootinfo *bi; 263 struct bi_mem_region tmp_mr[TMP_MAX_MR]; 264 struct bi_eth_addr tmp_eth[TMP_MAX_ETH]; 265 struct sys_info *si; 266 char *str, *end; 267 const char *env; 268 void *ptr; 269 u_int8_t tmp_addr[6]; --- 75 unchanged lines hidden (view full) --- 345 * - The 'boothowto' argument is constructed 346 * - The 'bootdev' argument is constructed 347 * - The kernel environment is copied into kernel space. 348 * - Module metadata are formatted and placed in kernel space. 349 */ 350int 351md_load(char *args, vm_offset_t *modulep) 352{ |
350 struct preloaded_file *kfp; 351 struct preloaded_file *xp; 352 struct file_metadata *md; 353 struct bootinfo *bip; 354 vm_offset_t kernend; 355 vm_offset_t addr; 356 vm_offset_t envp; 357 vm_offset_t size; 358 vm_offset_t vaddr; 359 char *rootdevname; 360 int howto; 361 int bisize; 362 int i; | 353 struct preloaded_file *kfp; 354 struct preloaded_file *xp; 355 struct file_metadata *md; 356 struct bootinfo *bip; 357 vm_offset_t kernend; 358 vm_offset_t addr; 359 vm_offset_t envp; 360 vm_offset_t size; 361 vm_offset_t vaddr; 362 char *rootdevname; 363 int howto; 364 int bisize; 365 int i; |
363 | 366 |
364 /* This metadata addreses must be converted for kernel after relocation */ 365 uint32_t mdt[] = { MODINFOMD_SSYM, MODINFOMD_ESYM, 366 MODINFOMD_KERNEND, MODINFOMD_ENVP }; | 367 /* 368 * These metadata addreses must be converted for kernel after 369 * relocation. 370 */ 371 uint32_t mdt[] = { 372 MODINFOMD_SSYM, MODINFOMD_ESYM, MODINFOMD_KERNEND, MODINFOMD_ENVP 373 }; |
367 | 374 |
368 howto = md_getboothowto(args); | 375 howto = md_getboothowto(args); |
369 | 376 |
370 /* 371 * Allow the environment variable 'rootdev' to override the supplied device 372 * This should perhaps go to MI code and/or have $rootdev tested/set by 373 * MI code before launching the kernel. 374 */ 375 rootdevname = getenv("rootdev"); 376 if (rootdevname == NULL) 377 rootdevname = getenv("currdev"); 378 /* Try reading the /etc/fstab file to select the root device */ 379 getrootmount(rootdevname); | 377 /* 378 * Allow the environment variable 'rootdev' to override the supplied 379 * device. This should perhaps go to MI code and/or have $rootdev 380 * tested/set by MI code before launching the kernel. 381 */ 382 rootdevname = getenv("rootdev"); 383 if (rootdevname == NULL) 384 rootdevname = getenv("currdev"); 385 /* Try reading the /etc/fstab file to select the root device */ 386 getrootmount(rootdevname); |
380 | 387 |
381 /* find the last module in the chain */ 382 addr = 0; 383 for (xp = file_findfile(NULL, NULL); xp != NULL; xp = xp->f_next) { 384 if (addr < (xp->f_addr + xp->f_size)) 385 addr = xp->f_addr + xp->f_size; 386 } 387 /* pad to a page boundary */ 388 addr = roundup(addr, PAGE_SIZE); | 388 /* find the last module in the chain */ 389 addr = 0; 390 for (xp = file_findfile(NULL, NULL); xp != NULL; xp = xp->f_next) { 391 if (addr < (xp->f_addr + xp->f_size)) 392 addr = xp->f_addr + xp->f_size; 393 } 394 /* pad to a page boundary */ 395 addr = roundup(addr, PAGE_SIZE); |
389 | 396 |
390 /* copy our environment */ 391 envp = addr; 392 addr = md_copyenv(addr); | 397 /* copy our environment */ 398 envp = addr; 399 addr = md_copyenv(addr); |
393 | 400 |
394 /* pad to a page boundary */ 395 addr = roundup(addr, PAGE_SIZE); | 401 /* pad to a page boundary */ 402 addr = roundup(addr, PAGE_SIZE); |
396 | 403 |
397 /* prepare bootinfo */ 398 bisize = md_bootinfo(&bip); | 404 /* prepare bootinfo */ 405 bisize = md_bootinfo(&bip); |
399 | 406 |
400 kernend = 0; 401 kfp = file_findfile(NULL, "elf32 kernel"); 402 if (kfp == NULL) 403 kfp = file_findfile(NULL, "elf kernel"); 404 if (kfp == NULL) 405 panic("can't find kernel file"); 406 file_addmetadata(kfp, MODINFOMD_HOWTO, sizeof howto, &howto); 407 file_addmetadata(kfp, MODINFOMD_BOOTINFO, bisize, bip); 408 file_addmetadata(kfp, MODINFOMD_ENVP, sizeof envp, &envp); 409 file_addmetadata(kfp, MODINFOMD_KERNEND, sizeof kernend, &kernend); | 407 kernend = 0; 408 kfp = file_findfile(NULL, "elf32 kernel"); 409 if (kfp == NULL) 410 kfp = file_findfile(NULL, "elf kernel"); 411 if (kfp == NULL) 412 panic("can't find kernel file"); 413 file_addmetadata(kfp, MODINFOMD_HOWTO, sizeof howto, &howto); 414 file_addmetadata(kfp, MODINFOMD_BOOTINFO, bisize, bip); 415 file_addmetadata(kfp, MODINFOMD_ENVP, sizeof envp, &envp); 416 file_addmetadata(kfp, MODINFOMD_KERNEND, sizeof kernend, &kernend); |
410 | 417 |
411 *modulep = addr; 412 size = md_copymodules(0); 413 kernend = roundup(addr + size, PAGE_SIZE); | 418 *modulep = addr; 419 size = md_copymodules(0); 420 kernend = roundup(addr + size, PAGE_SIZE); |
414 | 421 |
415 md = file_findmetadata(kfp, MODINFOMD_KERNEND); 416 bcopy(&kernend, md->md_data, sizeof kernend); | 422 md = file_findmetadata(kfp, MODINFOMD_KERNEND); 423 bcopy(&kernend, md->md_data, sizeof kernend); |
417 | 424 |
418 /* Convert addresses to the final VA */ 419 *modulep -= __elfN(relocation_offset); | 425 /* Convert addresses to the final VA */ 426 *modulep -= __elfN(relocation_offset); |
420 | 427 |
421 for (i = 0; i < sizeof mdt / sizeof mdt[0]; i++) { 422 md = file_findmetadata(kfp, mdt[i]); 423 if (md) { 424 bcopy(md->md_data, &vaddr, sizeof vaddr); 425 vaddr -= __elfN(relocation_offset); 426 bcopy(&vaddr, md->md_data, sizeof vaddr); 427 } 428 } 429 (void)md_copymodules(addr); | 428 for (i = 0; i < sizeof mdt / sizeof mdt[0]; i++) { 429 md = file_findmetadata(kfp, mdt[i]); 430 if (md) { 431 bcopy(md->md_data, &vaddr, sizeof vaddr); 432 vaddr -= __elfN(relocation_offset); 433 bcopy(&vaddr, md->md_data, sizeof vaddr); 434 } 435 } 436 (void)md_copymodules(addr); |
430 | 437 |
431 return(0); | 438 return(0); |
432} | 439} |