Rev 4421 | Rev 5363 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
2288 | clevermous | 1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
2 | ;; ;; |
||
2455 | mario79 | 3 | ;; Copyright (C) KolibriOS team 2004-2012. All rights reserved. ;; |
2288 | clevermous | 4 | ;; Distributed under terms of the GNU General Public License ;; |
5 | ;; ;; |
||
6 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
||
7 | |||
8 | $Revision: 5039 $ |
||
9 | |||
10 | include 'export.inc' |
||
11 | |||
12 | align 4 |
||
13 | |||
14 | proc load_PE stdcall, file_name:dword |
||
15 | locals |
||
16 | image dd ? |
||
17 | entry dd ? |
||
18 | base dd ? |
||
19 | endl |
||
20 | |||
21 | stdcall load_file, [file_name] |
||
22 | test eax, eax |
||
23 | jz .fail |
||
24 | |||
25 | mov [image], eax |
||
26 | |||
5039 | clevermous | 27 | mov edx, [eax+STRIPPED_PE_HEADER.SizeOfImage] |
28 | ; mov cl, [eax+STRIPPED_PE_HEADER.Subsystem] |
||
29 | cmp word [eax], STRIPPED_PE_SIGNATURE |
||
30 | jz @f |
||
31 | |||
2288 | clevermous | 32 | mov edx, [eax+60] |
5039 | clevermous | 33 | ; mov cl, [eax+5Ch+edx] |
34 | mov edx, [eax+80+edx] |
||
2288 | clevermous | 35 | |
5039 | clevermous | 36 | @@: |
37 | mov [entry], 0 |
||
38 | ; cmp cl, 1 |
||
39 | ; jnz .cleanup |
||
40 | stdcall kernel_alloc, edx |
||
2288 | clevermous | 41 | test eax, eax |
42 | jz .cleanup |
||
43 | |||
44 | mov [base], eax |
||
45 | |||
5039 | clevermous | 46 | push ebx ebp |
47 | mov ebx, [image] |
||
48 | mov ebp, eax |
||
49 | call map_PE |
||
50 | pop ebp ebx |
||
2288 | clevermous | 51 | |
52 | mov [entry], eax |
||
53 | test eax, eax |
||
54 | jnz .cleanup |
||
55 | |||
56 | stdcall kernel_free, [base] |
||
57 | .cleanup: |
||
58 | stdcall kernel_free, [image] |
||
59 | mov eax, [entry] |
||
60 | ret |
||
61 | .fail: |
||
62 | xor eax, eax |
||
63 | ret |
||
64 | endp |
||
65 | |||
5039 | clevermous | 66 | map_PE: ;ebp=base:dword, ebx=image:dword |
2288 | clevermous | 67 | push edi |
68 | push esi |
||
5039 | clevermous | 69 | sub esp, .locals_size |
70 | virtual at esp |
||
71 | .numsections dd ? |
||
72 | .import_names dd ? |
||
73 | .import_targets dd ? |
||
74 | .peheader dd ? |
||
75 | .bad_import dd ? |
||
76 | .import_idx dd ? |
||
77 | .import_descr dd ? |
||
78 | .relocs_rva dd ? |
||
79 | .relocs_size dd ? |
||
80 | .section_header_size dd ? |
||
81 | .AddressOfEntryPoint dd ? |
||
82 | .ImageBase dd ? |
||
83 | .locals_size = $ - esp |
||
84 | end virtual |
||
85 | cmp word [ebx], STRIPPED_PE_SIGNATURE |
||
86 | jz .stripped |
||
87 | |||
2288 | clevermous | 88 | mov edx, ebx |
5039 | clevermous | 89 | add edx, [ebx+60] |
90 | movzx eax, word [edx+6] |
||
91 | mov [.numsections], eax |
||
92 | mov eax, [edx+40] |
||
93 | mov [.AddressOfEntryPoint], eax |
||
94 | mov eax, [edx+52] |
||
95 | mov [.ImageBase], eax |
||
96 | mov ecx, [edx+84] |
||
97 | mov [.section_header_size], 40 |
||
98 | mov eax, [edx+128] |
||
99 | mov [.import_descr], eax |
||
100 | mov eax, [edx+160] |
||
101 | mov [.relocs_rva], eax |
||
102 | mov eax, [edx+164] |
||
103 | mov [.relocs_size], eax |
||
104 | add edx, 256 |
||
105 | |||
106 | jmp .common |
||
107 | .stripped: |
||
108 | mov eax, [ebx+STRIPPED_PE_HEADER.AddressOfEntryPoint] |
||
109 | mov [.AddressOfEntryPoint], eax |
||
110 | mov eax, [ebx+STRIPPED_PE_HEADER.ImageBase] |
||
111 | mov [.ImageBase], eax |
||
112 | movzx eax, [ebx+STRIPPED_PE_HEADER.NumberOfSections] |
||
113 | mov [.numsections], eax |
||
114 | movzx ecx, [ebx+STRIPPED_PE_HEADER.NumberOfRvaAndSizes] |
||
115 | xor eax, eax |
||
116 | mov [.relocs_rva], eax |
||
117 | mov [.relocs_size], eax |
||
118 | test ecx, ecx |
||
119 | jz @f |
||
120 | mov eax, [ebx+sizeof.STRIPPED_PE_HEADER+SPE_DIRECTORY_IMPORT*8] |
||
121 | @@: |
||
122 | mov [.import_descr], eax |
||
123 | cmp ecx, SPE_DIRECTORY_BASERELOC |
||
124 | jbe @f |
||
125 | mov eax, [ebx+sizeof.STRIPPED_PE_HEADER+SPE_DIRECTORY_BASERELOC*8] |
||
126 | mov [.relocs_rva], eax |
||
127 | mov eax, [ebx+sizeof.STRIPPED_PE_HEADER+SPE_DIRECTORY_BASERELOC*8+4] |
||
128 | mov [.relocs_size], eax |
||
129 | @@: |
||
130 | mov [.section_header_size], 28 |
||
131 | lea edx, [ebx+ecx*8+sizeof.STRIPPED_PE_HEADER+8] |
||
132 | mov ecx, [ebx+STRIPPED_PE_HEADER.SizeOfHeaders] |
||
133 | |||
134 | .common: |
||
2288 | clevermous | 135 | mov esi, ebx |
136 | mov edi, ebp |
||
137 | shr ecx, 2 |
||
138 | rep movsd |
||
139 | |||
5039 | clevermous | 140 | cmp [.numsections], 0 |
141 | jz .nosections |
||
142 | .copy_sections: |
||
143 | mov eax, [edx+8] |
||
2288 | clevermous | 144 | test eax, eax |
5039 | clevermous | 145 | je .no_section_data |
2288 | clevermous | 146 | mov esi, ebx |
147 | mov edi, ebp |
||
5039 | clevermous | 148 | add esi, [edx+12] |
2288 | clevermous | 149 | mov ecx, eax |
5039 | clevermous | 150 | add edi, [edx+4] |
2288 | clevermous | 151 | |
4418 | clevermous | 152 | add ecx, 3 |
2288 | clevermous | 153 | shr ecx, 2 |
154 | rep movsd |
||
155 | |||
5039 | clevermous | 156 | .no_section_data: |
157 | mov ecx, [edx] |
||
2288 | clevermous | 158 | cmp ecx, eax |
5039 | clevermous | 159 | jbe .no_section_fill |
2288 | clevermous | 160 | sub ecx, eax |
5039 | clevermous | 161 | add eax, [edx+4] |
2288 | clevermous | 162 | lea edi, [eax+ebp] |
163 | |||
164 | xor eax, eax |
||
165 | rep stosb |
||
166 | |||
5039 | clevermous | 167 | .no_section_fill: |
168 | add edx, [.section_header_size] |
||
169 | dec [.numsections] |
||
170 | jnz .copy_sections |
||
171 | .nosections: |
||
172 | cmp [.relocs_size], 0 |
||
173 | je .no_relocations |
||
2288 | clevermous | 174 | mov esi, ebp |
175 | mov ecx, ebp |
||
5039 | clevermous | 176 | sub esi, [.ImageBase] |
177 | add ecx, [.relocs_rva] |
||
178 | .relocs_block: |
||
179 | mov edi, [ecx] |
||
180 | add edi, ebp |
||
181 | mov ebx, [ecx+4] |
||
182 | add ecx, 8 |
||
183 | sub [.relocs_size], ebx |
||
184 | sub ebx, 8 |
||
2288 | clevermous | 185 | shr ebx, 1 |
5039 | clevermous | 186 | jz .relocs_next_block |
187 | .one_reloc: |
||
188 | movzx eax, word [ecx] |
||
189 | add ecx, 2 |
||
2288 | clevermous | 190 | mov edx, eax |
191 | shr eax, 12 |
||
192 | and edx, 4095 |
||
5039 | clevermous | 193 | cmp eax, 3 |
194 | jne @f |
||
195 | add [edx+edi], esi |
||
196 | @@: |
||
197 | dec ebx |
||
198 | jnz .one_reloc |
||
199 | .relocs_next_block: |
||
200 | cmp [.relocs_size], 0 |
||
201 | jg .relocs_block |
||
202 | .no_relocations: |
||
203 | cmp [.import_descr], 0 |
||
204 | je .no_imports |
||
205 | add [.import_descr], ebp |
||
206 | mov [.bad_import], 0 |
||
207 | .import_block: |
||
208 | mov ecx, [.import_descr] |
||
209 | cmp dword [ecx+4], 0 |
||
210 | jne @f |
||
211 | cmp dword [ecx+12], 0 |
||
212 | je .done_imports |
||
213 | @@: |
||
214 | mov edx, dword [ecx] |
||
215 | mov ecx, dword [ecx+16] |
||
4418 | clevermous | 216 | test edx, edx |
217 | jnz @f |
||
218 | mov edx, ecx |
||
219 | @@: |
||
5039 | clevermous | 220 | mov [.import_idx], 0 |
2288 | clevermous | 221 | add ecx, ebp |
222 | add edx, ebp |
||
5039 | clevermous | 223 | mov [.import_names], edx |
224 | mov [.import_targets], ecx |
||
225 | .import_func: |
||
226 | mov esi, [.import_idx] |
||
227 | mov edi, [.import_names] |
||
228 | mov eax, [edi+esi*4] |
||
2288 | clevermous | 229 | test eax, eax |
5039 | clevermous | 230 | je .next_import_block |
231 | js .next_import_block |
||
2288 | clevermous | 232 | lea edi, [ebp+eax] |
5039 | clevermous | 233 | mov eax, [.import_targets] |
234 | mov dword [eax+esi*4], 0 |
||
2288 | clevermous | 235 | lea esi, [edi+2] |
5039 | clevermous | 236 | movzx ebx, word [edi] |
2288 | clevermous | 237 | push 32 |
5039 | clevermous | 238 | mov ecx, [__exports+32] |
239 | mov eax, [ecx+OS_BASE+ebx*4] |
||
2288 | clevermous | 240 | add eax, OS_BASE |
241 | push eax |
||
242 | push esi |
||
243 | call strncmp |
||
5039 | clevermous | 244 | test eax, eax |
245 | jz .import_func_found |
||
2288 | clevermous | 246 | xor ebx, ebx |
5039 | clevermous | 247 | .import_func_candidate: |
2288 | clevermous | 248 | push 32 |
5039 | clevermous | 249 | mov ecx, [__exports+32] |
250 | mov eax, [ecx+OS_BASE+ebx*4] |
||
2288 | clevermous | 251 | add eax, OS_BASE |
252 | push eax |
||
253 | push esi |
||
254 | call strncmp |
||
255 | test eax, eax |
||
5039 | clevermous | 256 | je .import_func_found |
2288 | clevermous | 257 | inc ebx |
5039 | clevermous | 258 | cmp ebx, [__exports+24] |
259 | jb .import_func_candidate |
||
2288 | clevermous | 260 | |
261 | mov esi, msg_unresolved |
||
262 | call sys_msg_board_str |
||
263 | lea esi, [edi+2] |
||
264 | call sys_msg_board_str |
||
265 | mov esi, msg_CR |
||
266 | call sys_msg_board_str |
||
267 | |||
5039 | clevermous | 268 | mov [.bad_import], 1 |
269 | jmp .next_import_func |
||
270 | .import_func_found: |
||
271 | mov esi, [__exports+28] |
||
272 | mov edx, [.import_idx] |
||
273 | mov ecx, [.import_targets] |
||
274 | mov eax, [esi+OS_BASE+ebx*4] |
||
2288 | clevermous | 275 | add eax, OS_BASE |
5039 | clevermous | 276 | mov [ecx+edx*4], eax |
277 | .next_import_func: |
||
278 | inc [.import_idx] |
||
279 | jmp .import_func |
||
280 | .next_import_block: |
||
281 | add [.import_descr], 20 |
||
282 | jmp .import_block |
||
283 | .done_imports: |
||
2288 | clevermous | 284 | xor eax, eax |
5039 | clevermous | 285 | cmp [.bad_import], 0 |
286 | jne @f |
||
287 | .no_imports: |
||
2288 | clevermous | 288 | mov eax, ebp |
5039 | clevermous | 289 | add eax, [.AddressOfEntryPoint] |
290 | @@: |
||
291 | add esp, .locals_size |
||
2288 | clevermous | 292 | pop esi |
293 | pop edi |
||
5039 | clevermous | 294 | ret |