- Fix KiDispatchException to unmask KI_EXCEPTION_INTERNAL when setting the exception...
[reactos.git] / rosapps / devutils / cputointel / ImageLoader.c
1 #include <windows.h>
2 #include <winnt.h>
3
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <string.h>
7 #include "misc.h"
8 #include "From/ARM/ARM.h"
9 #include "From/m68k/m68k.h"
10 #include "From/PPC/PPC.h"
11
12 static CPU_INT machine_type = 0;
13 //static CPU_INT ToMachine_type = IMAGE_FILE_MACHINE_I386;
14 static CPU_INT ToMachine_type = IMAGE_FILE_MACHINE_POWERPC;
15 /*
16 * infileName file name to convert or disambler
17 * outputfileName file name to save to
18 * BaseAddress the address we should emulate
19 * cpuid the cpu we choice not vaild for pe loader
20 * type the loading mode Auto, PE, bin
21 * mode disambler mode : 0 the arch cpu.
22 * translate mode : 1 intel
23 * translate mode : 2 ppc
24 *
25 */
26
27 static void SetCPU(CPU_INT FromCpu, CPU_INT mode)
28 {
29 machine_type = FromCpu;
30 switch(mode)
31 {
32 case 0:
33 ToMachine_type = machine_type;
34 break;
35
36 case 1:
37 ToMachine_type = IMAGE_FILE_MACHINE_I386;
38 break;
39
40 case 2:
41 ToMachine_type = IMAGE_FILE_MACHINE_POWERPC;
42 break;
43
44 default:
45 printf("Not supported mode\n");
46 break;
47
48 }
49 }
50
51 static void Convert(FILE *outfp, CPU_INT FromCpu, CPU_INT mode)
52 {
53 SetCPU(machine_type,mode);
54 AnyalsingProcess();
55 ConvertProcess(outfp, machine_type, ToMachine_type);
56 FreeAny();
57 }
58
59
60 CPU_INT LoadPFileImage( char *infileName, char *outputfileName,
61 CPU_UNINT BaseAddress, char *cpuid,
62 CPU_UNINT type, CPU_INT mode)
63 {
64 FILE *infp;
65 FILE *outfp;
66 CPU_BYTE *cpu_buffer;
67 CPU_UNINT cpu_pos = 0;
68 CPU_UNINT cpu_size=0;
69 CPU_INT ret;
70 //fopen("testms.exe","RB");
71
72
73 /* Open file for read */
74
75 if (!(infp = fopen(infileName, "rb")))
76 {
77 printf("Can not open file %s\n",infileName);
78 return 3;
79 }
80
81 /* Open file for write */
82 if (!(outfp = fopen(outputfileName,"wb")))
83 {
84 printf("Can not open file %s\n",outputfileName);
85 return 4;
86 }
87
88 /* Load the binary file to a memory buffer */
89 fseek(infp,0,SEEK_END);
90 if (ferror(infp))
91 {
92 printf("error can not seek in the read file");
93 fclose(infp);
94 fclose(outfp);
95 return 5;
96 }
97
98 /* get the memory size buffer */
99 cpu_size = ftell(infp);
100 if (ferror(infp))
101 {
102 printf("error can not get file size of the read file");
103 fclose(infp);
104 fclose(outfp);
105 return 6;
106 }
107
108 /* Load the binary file to a memory buffer */
109 fseek(infp,0,SEEK_SET);
110 if (ferror(infp))
111 {
112 printf("error can not seek in the read file");
113 fclose(infp);
114 fclose(outfp);
115 return 5;
116 }
117
118 if (cpu_size==0)
119 {
120 printf("error file size is Zero lenght of the read file");
121 fclose(infp);
122 fclose(outfp);
123 return 7;
124 }
125
126 /* alloc memory now */
127 ;
128 if (!(cpu_buffer = (unsigned char *) malloc(cpu_size+1)))
129 {
130 printf("error can not alloc %uld size for memory buffer",cpu_size);
131 fclose(infp);
132 fclose(outfp);
133 return 8;
134 }
135 ZeroMemory(cpu_buffer,cpu_size);
136
137 /* read from the file now in one sweep */
138 fread((void *)cpu_buffer,1,cpu_size,infp);
139 if (ferror(infp))
140 {
141 printf("error can not read file ");
142 fclose(infp);
143 fclose(outfp);
144 return 9;
145 }
146 fclose(infp);
147
148 if (type==0)
149 {
150 if ( PEFileStart(cpu_buffer, 0, BaseAddress, cpu_size, outfp, mode) !=0)
151 {
152 type=1;
153 }
154 else
155 {
156 if (mode > 0)
157 {
158 Convert(outfp,machine_type,mode);
159 }
160 fclose(outfp);
161 return 0;
162 }
163
164 /* fixme */
165 return -1;
166 }
167
168 if (type== 1)
169 {
170 if (stricmp(cpuid,"m68000"))
171 {
172 ret = M68KBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,68000,outfp);
173 if (mode > 1)
174 {
175 Convert(outfp,machine_type,mode);
176 }
177 fclose(outfp);
178 }
179 else if (stricmp(cpuid,"m68010"))
180 {
181 ret = M68KBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,68010,outfp);
182 if (mode > 1)
183 {
184 Convert(outfp,machine_type,mode);
185 }
186 fclose(outfp);
187 return ret;
188 }
189 else if (stricmp(cpuid,"m68020"))
190 {
191 ret = M68KBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,68020,outfp);
192 if (mode > 1)
193 {
194 Convert(outfp,machine_type,mode);
195 }
196 fclose(outfp);
197 return ret;
198 }
199 else if (stricmp(cpuid,"m68030"))
200 {
201 ret = M68KBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,68030,outfp);
202 if (mode > 1)
203 {
204 Convert(outfp,machine_type,mode);
205 }
206 fclose(outfp);
207 return ret;
208 }
209 else if (stricmp(cpuid,"m68040"))
210 {
211 ret = M68KBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,68040,outfp);
212 if (mode > 1)
213 {
214 Convert(outfp,machine_type,mode);
215 }
216 fclose(outfp);
217 return ret;
218 }
219 else if (stricmp(cpuid,"ppc"))
220 {
221 ret = PPCBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,0,outfp);
222 if (mode > 1)
223 {
224 Convert(outfp,machine_type,mode);
225 }
226 fclose(outfp);
227 return ret;
228 }
229 else if (stricmp(cpuid,"arm4"))
230 {
231 ret = ARMBrain(cpu_buffer,cpu_pos,cpu_size,BaseAddress,4,outfp);
232 if (mode > 1)
233 {
234 Convert(outfp,machine_type,mode);
235 }
236 fclose(outfp);
237 return ret;
238 }
239 }
240
241 if (type==2)
242 {
243
244 ret = PEFileStart(cpu_buffer, 0, BaseAddress, cpu_size, outfp, mode);
245 if (mode > 1)
246 {
247 Convert(outfp,machine_type,mode);
248 }
249 fclose(outfp);
250 return ret;
251 }
252
253 return 0;
254 }
255
256 #define MAXSECTIONNUMBER 16
257
258 CPU_INT PEFileStart( CPU_BYTE *memory, CPU_UNINT pos,
259 CPU_UNINT base, CPU_UNINT size,
260 FILE *outfp, CPU_INT mode)
261 {
262 PIMAGE_DOS_HEADER DosHeader;
263 PIMAGE_NT_HEADERS NtHeader;
264 IMAGE_SECTION_HEADER SectionHeader[MAXSECTIONNUMBER] = {NULL};
265 PIMAGE_SECTION_HEADER pSectionHeader;
266 PIMAGE_EXPORT_DIRECTORY ExportEntry;
267 INT NumberOfSections;
268 INT NumberOfSectionsCount=0;
269 INT i;
270
271 DosHeader = (PIMAGE_DOS_HEADER)memory;
272 if ( (DosHeader->e_magic != IMAGE_DOS_SIGNATURE) ||
273 (size < 0x3c+2) )
274 {
275 printf("No MZ file \n");
276 return -1;
277 }
278
279 NtHeader = (PIMAGE_NT_HEADERS) (((ULONG)memory) + ((ULONG)DosHeader->e_lfanew));
280 if (NtHeader->Signature != IMAGE_NT_SIGNATURE)
281 {
282 printf("No PE header found \n");
283 }
284
285 if (!(NtHeader->FileHeader.Characteristics & IMAGE_FILE_EXECUTABLE_IMAGE))
286 {
287 printf("No execute image found \n");
288 return -1;
289 }
290
291 switch(NtHeader->OptionalHeader.Subsystem)
292 {
293 case IMAGE_SUBSYSTEM_EFI_APPLICATION:
294 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_EFI_APPLICATION\n");
295 printf("This exe file is desgin run in EFI bios as applactions\n");
296 break;
297 case IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER:
298 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER\n");
299 printf("This exe file is desgin run in EFI bios as service driver\n");
300 break;
301 case IMAGE_SUBSYSTEM_EFI_ROM:
302 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_EFI_ROM\n");
303 printf("This exe file is EFI ROM\n");
304 break;
305 case IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER:
306 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER\n");
307 printf("This exe file is desgin run in EFI bios as driver\n");
308 break;
309 case IMAGE_SUBSYSTEM_NATIVE:
310 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_NATIVE\n");
311 printf("This exe file does not need any subsystem\n");
312 break;
313 case IMAGE_SUBSYSTEM_NATIVE_WINDOWS:
314 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_NATIVE_WINDOWS\n");
315 printf("This exe file is desgin run on Windows 9x as driver \n");
316 break;
317 case IMAGE_SUBSYSTEM_OS2_CUI:
318 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_OS2_CUI\n");
319 printf("This exe file is desgin run on OS2 as CUI\n");
320 break;
321 case IMAGE_SUBSYSTEM_POSIX_CUI:
322 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_POSIX_CUI\n");
323 printf("This exe file is desgin run on POSIX as CUI\n");
324 break;
325 case IMAGE_SUBSYSTEM_WINDOWS_CE_GUI:
326 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_WINDOWS_CE_GUI\n");
327 printf("This exe file is desgin run on Windows CE as GUI\n");
328 break;
329 case IMAGE_SUBSYSTEM_WINDOWS_CUI:
330 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_WINDOWS_CUI\n");
331 printf("This exe file is desgin run on Windows as CUI\n");
332 break;
333 case IMAGE_SUBSYSTEM_WINDOWS_GUI:
334 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_WINDOWS_GUI\n");
335 printf("This exe file is desgin run on Windows as GUI\n");
336 break;
337 case IMAGE_SUBSYSTEM_XBOX:
338 fprintf(outfp,"; OS type : IMAGE_SUBSYSTEM_XBOX\n");
339 printf("This exe file is desgin run on X-Box\n");
340 break;
341 default:
342 fprintf(outfp,"; OS type : Unknown\n");
343 printf("Unknown OS : SubID : %d\n",NtHeader->OptionalHeader.Subsystem);
344 break;
345 }
346
347
348 printf("Number of object : %d\n",NtHeader->FileHeader.NumberOfSections);
349 printf("Base Address : %8x\n\n",NtHeader->OptionalHeader.ImageBase);
350
351 pSectionHeader = IMAGE_FIRST_SECTION(NtHeader);
352
353 NumberOfSections = NtHeader->FileHeader.NumberOfSections;
354
355 for (i = 0; i < NumberOfSections; i++)
356 {
357 SectionHeader[i] = *pSectionHeader++;
358 printf("Found Sector : %s \n ",SectionHeader[i].Name);
359 printf("RVA: %08lX ",SectionHeader[i].VirtualAddress);
360 printf("Offset: %08lX ",SectionHeader[i].PointerToRawData);
361 printf("Size: %08lX ",SectionHeader[i].SizeOfRawData);
362 printf("Flags: %08lX \n\n",SectionHeader[i].Characteristics);
363 }
364
365 /* Get export data */
366 if (NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size != 0)
367 {
368 for (i = 0; i < NumberOfSections; i++)
369 {
370 if ( SectionHeader[i].VirtualAddress <= (ULONG) NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress &&
371 SectionHeader[i].VirtualAddress + SectionHeader[i].SizeOfRawData > (ULONG)NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress)
372 {
373 ExportEntry = (PIMAGE_NT_HEADERS) (((ULONG)memory) +
374 (ULONG)(NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress -
375 SectionHeader[i].VirtualAddress +
376 SectionHeader[i].PointerToRawData));
377 }
378 }
379 }
380
381
382 /* start decoding */
383
384 for (i=0;i < NumberOfSections; i++)
385 {
386 if (strnicmp((PCHAR) SectionHeader[i].Name,".text\0",6)==0)
387 {
388 switch (NtHeader->FileHeader.Machine)
389 {
390 case IMAGE_FILE_MACHINE_ALPHA:
391 printf("CPU ALPHA Detected no CPUBrain implement for it\n");
392 fprintf(outfp,"; CPU found Alpha\n");
393 machine_type = IMAGE_FILE_MACHINE_ALPHA;
394 return 3;
395
396 case IMAGE_FILE_MACHINE_ALPHA64:
397 printf("CPU ALPHA64/AXP64 Detected no CPUBrain implement for it\n");
398 fprintf(outfp,"; CPU found Alpha64/AXP64\n");
399 machine_type = IMAGE_FILE_MACHINE_ALPHA64;
400 return 3;
401
402 case IMAGE_FILE_MACHINE_AM33:
403 printf("CPU AM33 Detected no CPUBrain implement for it\n");
404 fprintf(outfp,"; CPU found AM33\n");
405 machine_type = IMAGE_FILE_MACHINE_AM33;
406 return 3;
407
408 case IMAGE_FILE_MACHINE_AMD64:
409 printf("CPU AMD64 Detected no CPUBrain implement for it\n");
410 fprintf(outfp,"; CPU found AMD64\n");
411 machine_type = IMAGE_FILE_MACHINE_AMD64;
412 return 3;
413
414 case IMAGE_FILE_MACHINE_ARM:
415 printf("CPU ARM Detected no CPUBrain implement for it\n");
416 fprintf(outfp,"; CPU found ARM\n");
417 machine_type = IMAGE_FILE_MACHINE_ARM;
418 return 3;
419
420 case IMAGE_FILE_MACHINE_CEE:
421 printf("CPU CEE Detected no CPUBrain implement for it\n");
422 fprintf(outfp,"; CPU found CEE\n");
423 machine_type = IMAGE_FILE_MACHINE_CEE;
424 return 3;
425
426 case IMAGE_FILE_MACHINE_CEF:
427 printf("CPU CEF Detected no CPUBrain implement for it\n");
428 fprintf(outfp,"; CPU found CEF\n");
429 machine_type = IMAGE_FILE_MACHINE_CEF;
430 return 3;
431
432 case IMAGE_FILE_MACHINE_EBC:
433 printf("CPU EBC Detected no CPUBrain implement for it\n");
434 fprintf(outfp,"; CPU found EBC\n");
435 machine_type = IMAGE_FILE_MACHINE_EBC;
436 return 3;
437
438 case IMAGE_FILE_MACHINE_I386:
439 printf("CPU I386 Detected no CPUBrain implement for it\n");
440 fprintf(outfp,"; CPU found I386\n");
441 machine_type = IMAGE_FILE_MACHINE_I386;
442 return 3;
443
444 case IMAGE_FILE_MACHINE_IA64:
445 printf("CPU IA64 Detected no CPUBrain implement for it\n");
446 fprintf(outfp,"; CPU found IA64\n");
447 machine_type = IMAGE_FILE_MACHINE_IA64;
448 return 3;
449
450 case IMAGE_FILE_MACHINE_M32R:
451 printf("CPU M32R Detected no CPUBrain implement for it\n");
452 fprintf(outfp,"; CPU found M32R\n");
453 machine_type = IMAGE_FILE_MACHINE_M32R;
454 return 3;
455
456 case IMAGE_FILE_MACHINE_MIPS16:
457 printf("CPU MIPS16 Detected no CPUBrain implement for it\n");
458 fprintf(outfp,"; CPU found MIPS16\n");
459 machine_type = IMAGE_FILE_MACHINE_MIPS16;
460 return 3;
461
462 case IMAGE_FILE_MACHINE_MIPSFPU:
463 printf("CPU MIPSFPU Detected no CPUBrain implement for it\n");
464 fprintf(outfp,"; CPU found MIPSFPU\n");
465 machine_type = IMAGE_FILE_MACHINE_MIPSFPU;
466 return 3;
467
468 case IMAGE_FILE_MACHINE_MIPSFPU16:
469 printf("CPU MIPSFPU16 Detected no CPUBrain implement for it\n");
470 fprintf(outfp,"; CPU found MIPSFPU16\n");
471 machine_type = IMAGE_FILE_MACHINE_MIPSFPU16;
472 return 3;
473
474 case IMAGE_FILE_MACHINE_POWERPC:
475 printf("CPU POWERPC Detected partily CPUBrain implement for it\n");
476 fprintf(outfp,"; CPU found POWERPC\n");
477 //PPCBrain(memory, pos, cpu_size, base, 0, outfp);
478 machine_type = IMAGE_FILE_MACHINE_POWERPC;
479 PPCBrain(memory+SectionHeader[i].PointerToRawData, 0, SectionHeader[i].SizeOfRawData, NtHeader->OptionalHeader.ImageBase, 0, outfp);
480 break;
481
482
483 case IMAGE_FILE_MACHINE_POWERPCFP:
484 printf("CPU POWERPCFP Detected no CPUBrain implement for it\n");
485 fprintf(outfp,"; CPU found POWERPCFP\n");
486 machine_type = IMAGE_FILE_MACHINE_POWERPCFP;
487 return 3;
488
489 case IMAGE_FILE_MACHINE_R10000:
490 printf("CPU R10000 Detected no CPUBrain implement for it\n");
491 fprintf(outfp,"; CPU found R10000\n");
492 machine_type = IMAGE_FILE_MACHINE_R10000;
493 return 3;
494
495 case IMAGE_FILE_MACHINE_R3000:
496 printf("CPU R3000 Detected no CPUBrain implement for it\n");
497 fprintf(outfp,"; CPU found R3000\n");
498 machine_type = IMAGE_FILE_MACHINE_R3000;
499 return 3;
500
501 case IMAGE_FILE_MACHINE_R4000:
502 printf("CPU R4000 Detected no CPUBrain implement for it\n");
503 fprintf(outfp,"; CPU found R4000\n");
504 machine_type = IMAGE_FILE_MACHINE_R4000;
505 return 3;
506
507 case IMAGE_FILE_MACHINE_SH3:
508 printf("CPU SH3 Detected no CPUBrain implement for it\n");
509 fprintf(outfp,"; CPU found SH3\n");
510 machine_type = IMAGE_FILE_MACHINE_SH3;
511 return 3;
512
513 case IMAGE_FILE_MACHINE_SH3DSP:
514 printf("CPU SH3DSP Detected no CPUBrain implement for it\n");
515 fprintf(outfp,"; CPU found SH3DSP\n");
516 machine_type = IMAGE_FILE_MACHINE_SH3DSP;
517 return 3;
518
519 case IMAGE_FILE_MACHINE_SH3E:
520 printf("CPU SH3E Detected no CPUBrain implement for it\n");
521 fprintf(outfp,"; CPU found SH3E\n");
522 machine_type = IMAGE_FILE_MACHINE_SH3E;
523 return 3;
524
525 case IMAGE_FILE_MACHINE_SH4:
526 printf("CPU SH4 Detected no CPUBrain implement for it\n");
527 fprintf(outfp,"; CPU found SH4\n");
528 machine_type = IMAGE_FILE_MACHINE_SH4;
529 return 3;
530
531 case IMAGE_FILE_MACHINE_SH5:
532 printf("CPU SH5 Detected no CPUBrain implement for it\n");
533 fprintf(outfp,"; CPU found SH5\n");
534 machine_type = IMAGE_FILE_MACHINE_SH5;
535 return 3;
536
537 case IMAGE_FILE_MACHINE_THUMB:
538 printf("CPU THUMB Detected no CPUBrain implement for it\n");
539 fprintf(outfp,"; CPU found THUMB\n");
540 machine_type = IMAGE_FILE_MACHINE_THUMB;
541 return 3;
542
543 case IMAGE_FILE_MACHINE_TRICORE:
544 printf("CPU TRICORE Detected no CPUBrain implement for it\n");
545 fprintf(outfp,"; CPU found TRICORE\n");
546 machine_type = IMAGE_FILE_MACHINE_TRICORE;
547 return 3;
548
549 case IMAGE_FILE_MACHINE_WCEMIPSV2:
550 printf("CPU WCEMIPSV2 Detected no CPUBrain implement for it\n");
551 fprintf(outfp,"; CPU found WCEMIPSV2\n");
552 machine_type = IMAGE_FILE_MACHINE_WCEMIPSV2;
553 return 3;
554
555 default:
556 printf("Unknown Machine : %d",NtHeader->FileHeader.Machine);
557 return 4;
558 } /* end case switch*/
559 } /* end if text sector */
560 } /* end for */
561
562 return 0;
563 }