123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110 |
- #define LDSO_NEED_DPNT
- unsigned int _dl_nios2_get_gp_value(ElfW(Dyn) *dpnt);
- unsigned int
- _dl_nios2_get_gp_value (ElfW(Dyn) *dpnt)
- {
- while (dpnt->d_tag != DT_NULL) {
- if (dpnt->d_tag == DT_NIOS2_GP) {
- return (unsigned int)(dpnt->d_un.d_ptr);
- }
- ++dpnt;
- }
- return 0;
- }
- __asm__ (
- ".text\n"
- ".globl _start\n"
- ".type _start, %function\n"
- "_start:\n"
- " /* At start time, all the args are on the stack. */\n"
- " mov r4, sp\n"
- "\n"
- " /* Start the calculation of the GOT pointer. */\n"
- " nextpc r22\n"
- "1: movhi r8, %hiadj(_gp_got - 1b)\n"
- " addi r8, r8, %lo(_gp_got - 1b)\n"
- "\n"
- " /* Figure out where _dl_start will need to return to. */\n"
- " movhi ra, %hiadj(2f - 1b)\n"
- " addi ra, ra, %lo(2f - 1b)\n"
- " add ra, ra, r22\n"
- "\n"
- " /* Finish the calculation of the GOT pointer. */\n"
- " add r22, r22, r8\n"
- "\n"
- " br _dl_start\n"
- "\n"
- " /* Save the returned user entry point. */\n"
- "2: mov r16, r2\n"
- "\n"
- " /* Initialize gp. */\n"
- " ldw r4, %got(_dl_saved_dpnt)(r22)\n"
- " ldw r8, %call(_dl_nios2_get_gp_value)(r22)\n"
- " callr r8\n"
- " mov gp, r2\n"
- "\n"
- " /* Find the number of arguments to skip. */\n"
- " ldw r8, %got(_dl_skip_args)(r22)\n"
- " ldw r8, 0(r8)\n"
- "\n"
- " /* Find argc. */\n"
- " ldw r5, 0(sp)\n"
- " sub r5, r5, r8\n"
- " stw r5, 0(sp)\n"
- "\n"
- " /* Find the first unskipped argument. */\n"
- " slli r8, r8, 2\n"
- " addi r6, sp, 4\n"
- " add r9, r6, r8\n"
- " mov r10, r6\n"
- "\n"
- " /* Shuffle envp down. */\n"
- " mov r7, r10\n"
- "3: ldw r11, 0(r9)\n"
- " stw r11, 0(r10)\n"
- " addi r9, r9, 4\n"
- " addi r10, r10, 4\n"
- " bne r11, zero, 3b\n"
- "\n"
- " /* Shuffle auxv down. */\n"
- "4: ldw r11, 4(r9)\n"
- " stw r11, 4(r10)\n"
- " ldw r11, 0(r9)\n"
- " stw r11, 0(r10)\n"
- " addi r9, r9, 8\n"
- " addi r10, r10, 8\n"
- " bne r11, zero, 4b\n"
- "\n"
- " /* Jump to the user's entry point. */\n"
- " jmp r16\n"
- );
- /*
- * Get a pointer to the argv array. On many platforms this can be just
- * the address of the first argument, on other platforms we need to
- * do something a little more subtle here.
- */
- #define GET_ARGV(ARGVP, ARGS) ARGVP = (((unsigned long*) ARGS)+1)
- /* We can't call functions earlier in the dl startup process */
- #define NO_FUNCS_BEFORE_BOOTSTRAP
- /* The ld.so library requires relocations */
- #define ARCH_NEEDS_BOOTSTRAP_RELOCS
- static __always_inline
- void PERFORM_BOOTSTRAP_RELOC(ELF_RELOC *rpnt, unsigned long *reloc_addr,
- unsigned long symbol_addr, unsigned long load_addr, attribute_unused Elf32_Sym *symtab)
- {
- switch (ELF_R_TYPE(rpnt->r_info)) {
- case R_NIOS2_RELATIVE:
- *reloc_addr = load_addr + rpnt->r_addend;
- break;
- default:
- _dl_exit(1);
- break;
- }
- }
|