Module Name: src Committed By: chs Date: Sat Sep 11 20:49:28 UTC 2010
Modified Files: src/sys/compat/linux/common: linux_exec_elf32.c src/sys/compat/linux32/common: linux32_exec_elf32.c src/sys/kern: exec_elf.c src/sys/sys: exec.h Log Message: always supply an auxiliary vector for linux ELF processes. static executables (such as newer versions of /sbin/ldconfig) require this to work properly. since static executables also don't have a PT_PHDR entry, use the same heuristic as linux does to provide a value for AT_PHDR in this case. To generate a diff of this commit: cvs rdiff -u -r1.83 -r1.84 src/sys/compat/linux/common/linux_exec_elf32.c cvs rdiff -u -r1.11 -r1.12 src/sys/compat/linux32/common/linux32_exec_elf32.c cvs rdiff -u -r1.25 -r1.26 src/sys/kern/exec_elf.c cvs rdiff -u -r1.130 -r1.131 src/sys/sys/exec.h Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/compat/linux/common/linux_exec_elf32.c diff -u src/sys/compat/linux/common/linux_exec_elf32.c:1.83 src/sys/compat/linux/common/linux_exec_elf32.c:1.84 --- src/sys/compat/linux/common/linux_exec_elf32.c:1.83 Sun Mar 15 15:55:51 2009 +++ src/sys/compat/linux/common/linux_exec_elf32.c Sat Sep 11 20:49:28 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: linux_exec_elf32.c,v 1.83 2009/03/15 15:55:51 cegger Exp $ */ +/* $NetBSD: linux_exec_elf32.c,v 1.84 2010/09/11 20:49:28 chs Exp $ */ /*- * Copyright (c) 1995, 1998, 2000, 2001 The NetBSD Foundation, Inc. @@ -35,7 +35,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: linux_exec_elf32.c,v 1.83 2009/03/15 15:55:51 cegger Exp $"); +__KERNEL_RCSID(0, "$NetBSD: linux_exec_elf32.c,v 1.84 2010/09/11 20:49:28 chs Exp $"); #ifndef ELFSIZE /* XXX should die */ @@ -383,6 +383,7 @@ if ((error = emul_find_interp(l, epp, itp))) return (error); } + epp->ep_flags |= EXEC_FORCEAUX; DPRINTF(("linux_probe: returning 0\n")); return 0; } Index: src/sys/compat/linux32/common/linux32_exec_elf32.c diff -u src/sys/compat/linux32/common/linux32_exec_elf32.c:1.11 src/sys/compat/linux32/common/linux32_exec_elf32.c:1.12 --- src/sys/compat/linux32/common/linux32_exec_elf32.c:1.11 Wed Jul 7 01:30:35 2010 +++ src/sys/compat/linux32/common/linux32_exec_elf32.c Sat Sep 11 20:49:28 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: linux32_exec_elf32.c,v 1.11 2010/07/07 01:30:35 chs Exp $ */ +/* $NetBSD: linux32_exec_elf32.c,v 1.12 2010/09/11 20:49:28 chs Exp $ */ /*- * Copyright (c) 1995, 1998, 2000, 2001,2006 The NetBSD Foundation, Inc. @@ -31,7 +31,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: linux32_exec_elf32.c,v 1.11 2010/07/07 01:30:35 chs Exp $"); +__KERNEL_RCSID(0, "$NetBSD: linux32_exec_elf32.c,v 1.12 2010/09/11 20:49:28 chs Exp $"); #define ELFSIZE 32 @@ -92,7 +92,7 @@ DPRINTF(("linux32_probe: returning 0\n")); #endif - epp->ep_flags |= EXEC_32; + epp->ep_flags |= EXEC_32 | EXEC_FORCEAUX; epp->ep_vm_minaddr = VM_MIN_ADDRESS; epp->ep_vm_maxaddr = USRSTACK32; @@ -231,4 +231,3 @@ return 0; } - Index: src/sys/kern/exec_elf.c diff -u src/sys/kern/exec_elf.c:1.25 src/sys/kern/exec_elf.c:1.26 --- src/sys/kern/exec_elf.c:1.25 Tue Sep 7 21:32:03 2010 +++ src/sys/kern/exec_elf.c Sat Sep 11 20:49:28 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: exec_elf.c,v 1.25 2010/09/07 21:32:03 joerg Exp $ */ +/* $NetBSD: exec_elf.c,v 1.26 2010/09/11 20:49:28 chs Exp $ */ /*- * Copyright (c) 1994, 2000, 2005 The NetBSD Foundation, Inc. @@ -57,7 +57,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(1, "$NetBSD: exec_elf.c,v 1.25 2010/09/07 21:32:03 joerg Exp $"); +__KERNEL_RCSID(1, "$NetBSD: exec_elf.c,v 1.26 2010/09/11 20:49:28 chs Exp $"); #ifdef _KERNEL_OPT #include "opt_pax.h" @@ -636,11 +636,12 @@ { Elf_Ehdr *eh = epp->ep_hdr; Elf_Phdr *ph, *pp; - Elf_Addr phdr = 0, pos = 0, end_text = 0; + Elf_Addr phdr = 0, computed_phdr = 0, pos = 0, end_text = 0; int error, i, nload; char *interp = NULL; u_long phsize; struct proc *p; + struct elf_args *ap = NULL; bool is_dyn; if (epp->ep_hdrvalid < sizeof(Elf_Ehdr)) @@ -749,6 +750,9 @@ epp->ep_daddr = addr; epp->ep_dsize = size; } + if (ph[i].p_offset == 0) { + computed_phdr = ph[i].p_vaddr + eh->e_phoff; + } break; case PT_SHLIB: @@ -771,6 +775,10 @@ break; } } + if (interp || (epp->ep_flags & EXEC_FORCEAUX) != 0) { + ap = malloc(sizeof(struct elf_args), M_TEMP, M_WAITOK); + ap->arg_interp = (vaddr_t)NULL; + } if (epp->ep_daddr == ELFDEFNNAME(NO_ADDR)) { epp->ep_daddr = end_text; @@ -782,30 +790,26 @@ * its interpreter */ if (interp) { - struct elf_args *ap; int j = epp->ep_vmcmds.evs_used; u_long interp_offset; - ap = (struct elf_args *)malloc(sizeof(struct elf_args), - M_TEMP, M_WAITOK); if ((error = elf_load_file(l, epp, interp, &epp->ep_vmcmds, &interp_offset, ap, &pos)) != 0) { - free(ap, M_TEMP); goto bad; } ap->arg_interp = epp->ep_vmcmds.evs_cmds[j].ev_addr; epp->ep_entry = ap->arg_interp + interp_offset; - ap->arg_phaddr = phdr; + PNBUF_PUT(interp); + } else + epp->ep_entry = eh->e_entry; + if (ap) { + ap->arg_phaddr = phdr ? phdr : computed_phdr; ap->arg_phentsize = eh->e_phentsize; ap->arg_phnum = eh->e_phnum; ap->arg_entry = eh->e_entry; - epp->ep_emul_arg = ap; - - PNBUF_PUT(interp); - } else - epp->ep_entry = eh->e_entry; + } #ifdef ELF_MAP_PAGE_ZERO /* Dell SVR4 maps page zero, yeuch! */ @@ -818,6 +822,8 @@ bad: if (interp) PNBUF_PUT(interp); + if (ap) + free(ap, M_TEMP); kmem_free(ph, phsize); kill_vmcmds(&epp->ep_vmcmds); return error; Index: src/sys/sys/exec.h diff -u src/sys/sys/exec.h:1.130 src/sys/sys/exec.h:1.131 --- src/sys/sys/exec.h:1.130 Sun May 2 05:30:20 2010 +++ src/sys/sys/exec.h Sat Sep 11 20:49:28 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: exec.h,v 1.130 2010/05/02 05:30:20 dholland Exp $ */ +/* $NetBSD: exec.h,v 1.131 2010/09/11 20:49:28 chs Exp $ */ /*- * Copyright (c) 1992, 1993 @@ -209,6 +209,7 @@ #define EXEC_SKIPARG 0x0008 /* don't copy user-supplied argv[0] */ #define EXEC_DESTR 0x0010 /* destructive ops performed */ #define EXEC_32 0x0020 /* 32-bit binary emulation */ +#define EXEC_FORCEAUX 0x0040 /* always use ELF AUX vector */ struct exec_vmcmd { int (*ev_proc)(struct lwp *, struct exec_vmcmd *);