Skip to content

Commit 531b8a5

Browse files
committed
[elf] Get back dynamic loader
1 parent 1e2eb38 commit 531b8a5

File tree

10 files changed

+1805
-0
lines changed

10 files changed

+1805
-0
lines changed

components/libc/libdl/arch/arm.c

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
/*
2+
* Copyright (c) 2006-2018, RT-Thread Development Team
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*
6+
* Change Logs:
7+
* Date Author Notes
8+
* 2018/08/29 Bernard first version
9+
*/
10+
11+
#include "../dlmodule.h"
12+
#include "../dlelf.h"
13+
14+
#ifdef __arm__
15+
int dlmodule_relocate(struct rt_dlmodule *module, Elf32_Rel *rel, Elf32_Addr sym_val)
16+
{
17+
Elf32_Addr *where, tmp;
18+
Elf32_Sword addend, offset;
19+
rt_uint32_t upper, lower, sign, j1, j2;
20+
21+
where = (Elf32_Addr *)((rt_uint8_t *)module->mem_space
22+
+ rel->r_offset
23+
- module->vstart_addr);
24+
switch (ELF32_R_TYPE(rel->r_info))
25+
{
26+
case R_ARM_NONE:
27+
break;
28+
case R_ARM_ABS32:
29+
*where += (Elf32_Addr)sym_val;
30+
RT_DEBUG_LOG(RT_DEBUG_MODULE, ("R_ARM_ABS32: %x -> %x\n",
31+
where, *where));
32+
break;
33+
case R_ARM_PC24:
34+
case R_ARM_PLT32:
35+
case R_ARM_CALL:
36+
case R_ARM_JUMP24:
37+
addend = *where & 0x00ffffff;
38+
if (addend & 0x00800000)
39+
addend |= 0xff000000;
40+
tmp = sym_val - (Elf32_Addr)where + (addend << 2);
41+
tmp >>= 2;
42+
*where = (*where & 0xff000000) | (tmp & 0x00ffffff);
43+
RT_DEBUG_LOG(RT_DEBUG_MODULE, ("R_ARM_PC24: %x -> %x\n",
44+
where, *where));
45+
break;
46+
case R_ARM_REL32:
47+
*where += sym_val - (Elf32_Addr)where;
48+
RT_DEBUG_LOG(RT_DEBUG_MODULE,
49+
("R_ARM_REL32: %x -> %x, sym %x, offset %x\n",
50+
where, *where, sym_val, rel->r_offset));
51+
break;
52+
case R_ARM_V4BX:
53+
*where &= 0xf000000f;
54+
*where |= 0x01a0f000;
55+
break;
56+
57+
case R_ARM_GLOB_DAT:
58+
case R_ARM_JUMP_SLOT:
59+
*where = (Elf32_Addr)sym_val;
60+
RT_DEBUG_LOG(RT_DEBUG_MODULE, ("R_ARM_JUMP_SLOT: 0x%x -> 0x%x 0x%x\n",
61+
where, *where, sym_val));
62+
break;
63+
#if 0 /* To do */
64+
case R_ARM_GOT_BREL:
65+
temp = (Elf32_Addr)sym_val;
66+
*where = (Elf32_Addr)&temp;
67+
RT_DEBUG_LOG(RT_DEBUG_MODULE, ("R_ARM_GOT_BREL: 0x%x -> 0x%x 0x%x\n",
68+
where, *where, sym_val));
69+
break;
70+
#endif
71+
72+
case R_ARM_RELATIVE:
73+
*where = (Elf32_Addr)sym_val + *where;
74+
RT_DEBUG_LOG(RT_DEBUG_MODULE, ("R_ARM_RELATIVE: 0x%x -> 0x%x 0x%x\n",
75+
where, *where, sym_val));
76+
break;
77+
case R_ARM_THM_CALL:
78+
case R_ARM_THM_JUMP24:
79+
upper = *(rt_uint16_t *)where;
80+
lower = *(rt_uint16_t *)((Elf32_Addr)where + 2);
81+
82+
sign = (upper >> 10) & 1;
83+
j1 = (lower >> 13) & 1;
84+
j2 = (lower >> 11) & 1;
85+
offset = (sign << 24) |
86+
((~(j1 ^ sign) & 1) << 23) |
87+
((~(j2 ^ sign) & 1) << 22) |
88+
((upper & 0x03ff) << 12) |
89+
((lower & 0x07ff) << 1);
90+
if (offset & 0x01000000)
91+
offset -= 0x02000000;
92+
offset += sym_val - (Elf32_Addr)where;
93+
94+
if (!(offset & 1) ||
95+
offset <= (rt_int32_t)0xff000000 ||
96+
offset >= (rt_int32_t)0x01000000)
97+
{
98+
rt_kprintf("Module: Only Thumb addresses allowed\n");
99+
100+
return -1;
101+
}
102+
103+
sign = (offset >> 24) & 1;
104+
j1 = sign ^ (~(offset >> 23) & 1);
105+
j2 = sign ^ (~(offset >> 22) & 1);
106+
*(rt_uint16_t *)where = (rt_uint16_t)((upper & 0xf800) |
107+
(sign << 10) |
108+
((offset >> 12) & 0x03ff));
109+
*(rt_uint16_t *)(where + 2) = (rt_uint16_t)((lower & 0xd000) |
110+
(j1 << 13) | (j2 << 11) |
111+
((offset >> 1) & 0x07ff));
112+
upper = *(rt_uint16_t *)where;
113+
lower = *(rt_uint16_t *)((Elf32_Addr)where + 2);
114+
break;
115+
default:
116+
return -1;
117+
}
118+
119+
return 0;
120+
}
121+
#endif

components/libc/libdl/dlclose.c

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
/*
2+
* Copyright (c) 2006-2018, RT-Thread Development Team
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*
6+
* Change Logs:
7+
* Date Author Notes
8+
* 2010-11-17 yi.qiu first version
9+
*/
10+
11+
#include <rtthread.h>
12+
#include <rtm.h>
13+
14+
#include "dlmodule.h"
15+
16+
int dlclose(void *handle)
17+
{
18+
struct rt_dlmodule *module;
19+
20+
RT_ASSERT(handle != RT_NULL);
21+
22+
module = (struct rt_dlmodule *)handle;
23+
24+
rt_enter_critical();
25+
module->nref--;
26+
if (module->nref <= 0)
27+
{
28+
rt_exit_critical();
29+
30+
dlmodule_destroy(module);
31+
}
32+
else
33+
{
34+
rt_exit_critical();
35+
}
36+
37+
return RT_TRUE;
38+
}
39+
RTM_EXPORT(dlclose)

0 commit comments

Comments
 (0)