OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [uclinux/] [uClinux-2.0.x/] [fs/] [binfmt_elf.c] - Diff between revs 701 and 707

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 701 Rev 707
Line 35... Line 35...
 
 
#define DLINFO_ITEMS 12
#define DLINFO_ITEMS 12
 
 
#include <linux/elf.h>
#include <linux/elf.h>
 
 
#define STACK_SIZE (1*PAGE_SIZE)
#define JUMP_TO_MAIN 0
 
#define STACK_SIZE (2*PAGE_SIZE)
 
 
static int load_elf_binary(struct linux_binprm *bprm, struct pt_regs *regs);
static int load_elf_binary(struct linux_binprm *bprm, struct pt_regs *regs);
 
 
#define ELF_PAGESTART(_v) ((_v) & ~(unsigned long)(ELF_EXEC_PAGESIZE-1))
#define ELF_PAGESTART(_v) ((_v) & ~(unsigned long)(ELF_EXEC_PAGESIZE-1))
#define ELF_PAGEOFFSET(_v) ((_v) & (ELF_EXEC_PAGESIZE-1))
#define ELF_PAGEOFFSET(_v) ((_v) & (ELF_EXEC_PAGESIZE-1))
Line 60... Line 61...
} sec[ELF_SECTION_NB];
} sec[ELF_SECTION_NB];
 
 
unsigned short *or32_consth_add = (unsigned short *)NULL;
unsigned short *or32_consth_add = (unsigned short *)NULL;
unsigned long or32_consth_rel;
unsigned long or32_consth_rel;
 
 
 
#if JUMP_TO_MAIN
unsigned long *create_elf_tables(char *p, int argc, int envc, struct pt_regs *regs)
unsigned long *create_elf_tables(char *p, int argc, int envc, struct pt_regs *regs)
{
{
        unsigned long *argv, *envp;
        unsigned long *argv, *envp;
        unsigned long *sp;
        unsigned long *sp;
 
 
Line 96... Line 98...
        }
        }
        put_user(0, envp);
        put_user(0, envp);
        current->mm->env_end = (unsigned long) p;
        current->mm->env_end = (unsigned long) p;
        return sp;
        return sp;
}
}
 
#else
 
unsigned long *create_elf_tables(char *p, int argc, int envc, struct pt_regs *regs)
 
{
 
        unsigned long *argv, *envp;
 
        unsigned long *sp;
 
 
 
        /*
 
         * Force 16 byte alignment here for generality.
 
         */
 
        sp = (unsigned long *) (~15UL & (unsigned long) p);
 
        sp -= 2;
 
        sp -= envc + 1;
 
        envp = sp;
 
        sp -= argc + 1;
 
        argv = sp;
 
 
 
        regs->gprs[1] = sp;
 
        put_user((unsigned long) argc, --sp);
 
        current->mm->arg_start = (unsigned long) p;
 
        while (argc-- > 0) {
 
                put_user(p, argv++);
 
                while (get_user(p++))   /* nothing */
 
                        ;
 
        }
 
        put_user(0, argv);
 
        current->mm->arg_end = current->mm->env_start = (unsigned long) p;
 
        while (envc-- > 0) {
 
                put_user(p, envp++);
 
                while (get_user(p++))   /* nothing */
 
                        ;
 
        }
 
        put_user(0, envp);
 
        current->mm->env_end = (unsigned long) p;
 
        return sp;
 
}
 
#endif
 
 
static unsigned long putstring(unsigned long p, char * string)
static unsigned long putstring(unsigned long p, char * string)
{
{
        unsigned long l = strlen(string)+1;
        unsigned long l = strlen(string)+1;
        p -= l;
        p -= l;
Line 145... Line 183...
                /* Section index of section that contains symbol */
                /* Section index of section that contains symbol */
                src_indx = sym_tab->st_shndx;
                src_indx = sym_tab->st_shndx;
                /* Location in physical memory to which this relocation
                /* Location in physical memory to which this relocation
                   is refering to */
                   is refering to */
                rel_loc = (void *)(rel_ptr->r_offset + sec[dst_indx].pm_add);
                rel_loc = (void *)(rel_ptr->r_offset + sec[dst_indx].pm_add);
 
 
                if((rel_ptr->r_info & 0x000000ff) == R_OR32_32) {
                if((rel_ptr->r_info & 0x000000ff) == R_OR32_32) {
                        *(unsigned long *)rel_loc = *(unsigned long *)rel_loc
                        *(unsigned long *)rel_loc = *(unsigned long *)rel_loc
                                                - sec[src_indx].vm_add
                                                - sec[src_indx].vm_add
                                                + sec[src_indx].pm_add;
                                                + sec[src_indx].pm_add;
                }
                }
Line 194... Line 231...
                }
                }
        }
        }
        return 0;
        return 0;
}
}
 
 
 
#if JUMP_TO_MAIN
unsigned long do_find_main(int sym_nb, struct elf32_sym *sym_prt, char *str_ptr)
unsigned long do_find_main(int sym_nb, struct elf32_sym *sym_prt, char *str_ptr)
{
{
        int i;
        int i;
 
 
        for(i = 0; i < sym_nb; i++, sym_prt++) {
        for(i = 0; i < sym_nb; i++, sym_prt++) {
Line 207... Line 245...
                if(strcmp(&str_ptr[sym_prt->st_name], "_main") == 0)
                if(strcmp(&str_ptr[sym_prt->st_name], "_main") == 0)
                        return (sym_prt->st_value + sec[sym_prt->st_shndx].pm_add);
                        return (sym_prt->st_value + sec[sym_prt->st_shndx].pm_add);
        }
        }
        return 0;
        return 0;
}
}
 
#else
 
unsigned long do_find_start(int sym_nb, struct elf32_sym *sym_prt, char *str_ptr)
 
{
 
        int i;
 
 
 
        for(i = 0; i < sym_nb; i++, sym_prt++) {
 
                if(sym_prt->st_name == 0)
 
                        continue;
 
 
 
                if(strcmp(&str_ptr[sym_prt->st_name], "_start") == 0)
 
                        return (sym_prt->st_value + sec[sym_prt->st_shndx].pm_add);
 
        }
 
        return 0;
 
}
 
#endif
/*
/*
 * These are the functions used to load ELF style executables and shared
 * These are the functions used to load ELF style executables and shared
 * libraries.  There is no binary dependent code anywhere else.
 * libraries.  There is no binary dependent code anywhere else.
 */
 */
 
 
Line 313... Line 366...
                        if(elf_spnt->sh_flags & SHF_ALLOC)
                        if(elf_spnt->sh_flags & SHF_ALLOC)
                                bss_len += (elf_spnt->sh_size + 3) & ~(3);
                                bss_len += (elf_spnt->sh_size + 3) & ~(3);
                }
                }
        }
        }
 
 
 
        /* Make room on stack for arguments & environment */
 
        stack_len = STACK_SIZE;
 
        stack_len += strlen(bprm->filename) + 1;
 
        stack_len += stringarraylen(bprm->envc, bprm->envp);
 
        stack_len += stringarraylen(bprm->argc, bprm->argv);
 
 
        /* Allocate space */
        /* Allocate space */
        retval = (unsigned long)do_mmap(NULL,
        retval = (unsigned long)do_mmap(NULL,
                                        0,
                                        0,
                                        code_len + code_len + bss_len + stack_len,
                                        code_len + code_len + bss_len + stack_len,
                                        PROT_EXEC | PROT_WRITE | PROT_READ,
                                        PROT_EXEC | PROT_WRITE | PROT_READ,
Line 332... Line 391...
        code_end = code_start;
        code_end = code_start;
        data_start = code_start + code_len;
        data_start = code_start + code_len;
        data_end = data_start;
        data_end = data_start;
        bss_start = data_start + data_len;
        bss_start = data_start + data_len;
        bss_end = bss_start;
        bss_end = bss_start;
        stack_len = STACK_SIZE;
 
 
 
        /* Make room on stack for arguments & environment */
 
        stack_len += strlen(bprm->filename) + 1;
 
        stack_len += stringarraylen(bprm->envc, bprm->envp);
 
        stack_len += stringarraylen(bprm->argc, bprm->argv);
 
 
 
        current->mm->executable = 0;
        current->mm->executable = 0;
 
 
        /* Now copy sections in memory */
        /* Now copy sections in memory */
 
 
        for(i = 0, elf_spnt = elf_shdata; i < elf_ex.e_shnum; i++, elf_spnt++) {
        for(i = 0, elf_spnt = elf_shdata; i < elf_ex.e_shnum; i++, elf_spnt++) {
 
 
                if(elf_spnt->sh_type == SHT_PROGBITS && elf_spnt->sh_flags & SHF_EXECINSTR) {
                if(elf_spnt->sh_type == SHT_PROGBITS && elf_spnt->sh_flags & SHF_EXECINSTR) {
 
 
 
                        if(elf_spnt->sh_size == 0)
 
                                continue;
 
 
                        retval = read_exec(bprm->inode, elf_spnt->sh_offset,
                        retval = read_exec(bprm->inode, elf_spnt->sh_offset,
                                        (char *)code_end, elf_spnt->sh_size, 1);
                                        (char *)code_end, elf_spnt->sh_size, 1);
 
 
                        if (retval < 0) {
                        if (retval < 0) {
                                do_munmap(code_start, code_len + code_len + bss_len + stack_len);
                                do_munmap(code_start, code_len + code_len + bss_len + stack_len);
Line 363... Line 419...
 
 
                        code_end = code_end + ((elf_spnt->sh_size + 3) & ~(3));
                        code_end = code_end + ((elf_spnt->sh_size + 3) & ~(3));
                }
                }
                else if (elf_spnt->sh_type == SHT_PROGBITS && elf_spnt->sh_flags & SHF_ALLOC) {
                else if (elf_spnt->sh_type == SHT_PROGBITS && elf_spnt->sh_flags & SHF_ALLOC) {
 
 
 
                        if(elf_spnt->sh_size == 0)
 
                                continue;
 
 
                        retval = read_exec(bprm->inode, elf_spnt->sh_offset,
                        retval = read_exec(bprm->inode, elf_spnt->sh_offset,
                                        (char *)data_end, elf_spnt->sh_size, 1);
                                        (char *)data_end, elf_spnt->sh_size, 1);
 
 
                        if (retval < 0) {
                        if (retval < 0) {
                                do_munmap(code_start, code_len + code_len + bss_len + stack_len);
                                do_munmap(code_start, code_len + code_len + bss_len + stack_len);
Line 379... Line 438...
 
 
                        data_end = data_end + ((elf_spnt->sh_size + 3) & ~(3));
                        data_end = data_end + ((elf_spnt->sh_size + 3) & ~(3));
                }
                }
                else if (elf_spnt->sh_type == SHT_NOBITS && elf_spnt->sh_flags & SHF_ALLOC) {
                else if (elf_spnt->sh_type == SHT_NOBITS && elf_spnt->sh_flags & SHF_ALLOC) {
 
 
 
                        if(elf_spnt->sh_size == 0)
 
                                continue;
 
 
                        sec[i].pm_add = bss_end;
                        sec[i].pm_add = bss_end;
                        sec[i].vm_add = elf_spnt->sh_addr;
                        sec[i].vm_add = elf_spnt->sh_addr;
 
 
                        bss_end = bss_end + ((elf_spnt->sh_size + 3) & ~(3));
                        bss_end = bss_end + ((elf_spnt->sh_size + 3) & ~(3));
                }
                }
Line 462... Line 524...
                                kfree(elf_shdata);
                                kfree(elf_shdata);
                                return retval;
                                return retval;
                        }
                        }
 
 
                        sym_nb = sec[symtab_indx].len / sizeof(struct elf32_sym);
                        sym_nb = sec[symtab_indx].len / sizeof(struct elf32_sym);
 
#if JUMP_TO_MAIN
                        elf_entry = do_find_main(sym_nb, sym_ptr, str_ptr);
                        elf_entry = do_find_main(sym_nb, sym_ptr, str_ptr);
 
#else
 
                        elf_entry = do_find_start(sym_nb, sym_ptr, str_ptr);
 
#endif
                        break;
                        break;
                }
                }
        }
        }
 
 
        for(i = 0, elf_spnt = elf_shdata; i < elf_ex.e_shnum; elf_spnt++, i++) {
        for(i = 0, elf_spnt = elf_shdata; i < elf_ex.e_shnum; elf_spnt++, i++) {

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.