le.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355
  1. /*
  2. * Dumping of LE binaries
  3. *
  4. * Copyright 2004 Robert Reif
  5. *
  6. * This library is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 2.1 of the License, or (at your option) any later version.
  10. *
  11. * This library is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public
  17. * License along with this library; if not, write to the Free Software
  18. * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
  19. */
  20. #include "config.h"
  21. #include <fcntl.h>
  22. #include <stdarg.h>
  23. #include <stdio.h>
  24. #include "windef.h"
  25. #include "winbase.h"
  26. #include "winedump.h"
  27. struct o32_obj
  28. {
  29. unsigned long o32_size;
  30. unsigned long o32_base;
  31. unsigned long o32_flags;
  32. unsigned long o32_pagemap;
  33. unsigned long o32_mapsize;
  34. char o32_name[4];
  35. };
  36. struct o32_map
  37. {
  38. unsigned short o32_pagedataoffset;
  39. unsigned char o32_pagesize;
  40. unsigned char o32_pageflags;
  41. };
  42. struct b32_bundle
  43. {
  44. unsigned char b32_cnt;
  45. unsigned char b32_type;
  46. };
  47. struct vxd_descriptor
  48. {
  49. unsigned long next;
  50. unsigned short sdk_version;
  51. unsigned short device_number;
  52. unsigned char version_major;
  53. unsigned char version_minor;
  54. unsigned short flags;
  55. char name[8];
  56. unsigned long init_order;
  57. unsigned long ctrl_ofs;
  58. unsigned long v86_ctrl_ofs;
  59. unsigned long pm_ctrl_ofs;
  60. unsigned long v86_ctrl_csip;
  61. unsigned long pm_ctrl_csip;
  62. unsigned long rm_ref_data;
  63. unsigned long service_table_ofs;
  64. unsigned long service_table_size;
  65. unsigned long win32_service_table_ofs;
  66. unsigned long prev;
  67. unsigned long size;
  68. unsigned long reserved0;
  69. unsigned long reserved1;
  70. unsigned long reserved2;
  71. };
  72. static inline WORD get_word( const BYTE *ptr )
  73. {
  74. return ptr[0] | (ptr[1] << 8);
  75. }
  76. static void dump_le_header( const IMAGE_VXD_HEADER *le )
  77. {
  78. printf( "File header:\n" );
  79. printf( " Magic: %04x (%c%c)\n",
  80. le->e32_magic, LOBYTE(le->e32_magic), HIBYTE(le->e32_magic));
  81. printf( " Byte order: %s\n",
  82. le->e32_border == 0 ? "little-indian" : "big-endian");
  83. printf( " Word order: %s\n",
  84. le->e32_worder == 0 ? "little-indian" : "big-endian");
  85. printf( " Executable format level: %d\n",
  86. le->e32_level);
  87. printf( " CPU type: %s\n",
  88. le->e32_cpu == 0x01 ? "Intel 80286" :
  89. le->e32_cpu == 0x02 ? "Intel 80386" :
  90. le->e32_cpu == 0x03 ? "Intel 80486" :
  91. le->e32_cpu == 0x04 ? "Intel 80586" :
  92. le->e32_cpu == 0x20 ? "Intel i860 (N10)" :
  93. le->e32_cpu == 0x21 ? "Intel i860 (N11)" :
  94. le->e32_cpu == 0x40 ? "MIPS Mark I" :
  95. le->e32_cpu == 0x41 ? "MIPS Mark II" :
  96. le->e32_cpu == 0x42 ? "MIPS Mark III" :
  97. "Unknown");
  98. printf( " Target operating system: %s\n",
  99. le->e32_os == 0x01 ? "OS/2" :
  100. le->e32_os == 0x02 ? "Windows" :
  101. le->e32_os == 0x03 ? "DOS 4.x" :
  102. le->e32_os == 0x04 ? "Windows 386" :
  103. "Unknown");
  104. printf( " Module version: %d\n",
  105. le->e32_ver);
  106. printf( " Module type flags: %08x\n",
  107. le->e32_mflags);
  108. if (le->e32_mflags & 0x8000)
  109. {
  110. if (le->e32_mflags & 0x0004)
  111. printf( " Global initialization\n");
  112. else
  113. printf( " Per-Process initialization\n");
  114. if (le->e32_mflags & 0x0010)
  115. printf( " No internal fixup\n");
  116. if (le->e32_mflags & 0x0020)
  117. printf( " No external fixup\n");
  118. if ((le->e32_mflags & 0x0700) == 0x0100)
  119. printf( " Incompatible with PM windowing\n");
  120. else if ((le->e32_mflags & 0x0700) == 0x0200)
  121. printf( " Compatible with PM windowing\n");
  122. else if ((le->e32_mflags & 0x0700) == 0x0300)
  123. printf( " Uses PM windowing API\n");
  124. if (le->e32_mflags & 0x2000)
  125. printf( " Module not loadable\n");
  126. if (le->e32_mflags & 0x8000)
  127. printf( " Module is DLL\n");
  128. }
  129. printf( " Number of memory pages: %d\n",
  130. le->e32_mpages);
  131. printf( " Initial object CS number: %08x\n",
  132. le->e32_startobj);
  133. printf( " Initial EIP: %08x\n",
  134. le->e32_eip);
  135. printf( " Initial object SS number: %08x\n",
  136. le->e32_stackobj);
  137. printf( " Initial ESP: %08x\n",
  138. le->e32_esp);
  139. printf( " Memory page size: %d\n",
  140. le->e32_pagesize);
  141. printf( " Bytes on last page: %d\n",
  142. le->e32_lastpagesize);
  143. printf( " Fix-up section size: %d\n",
  144. le->e32_fixupsize);
  145. printf( " Fix-up section checksum: %08x\n",
  146. le->e32_fixupsum);
  147. printf( " Loader section size: %d\n",
  148. le->e32_ldrsize);
  149. printf( " Loader section checksum: %08x\n",
  150. le->e32_ldrsum);
  151. printf( " Offset of object table: %08x\n",
  152. le->e32_objtab);
  153. printf( " Object table entries: %d\n",
  154. le->e32_objcnt);
  155. printf( " Object page map offset: %08x\n",
  156. le->e32_objmap);
  157. printf( " Object iterate data map offset: %08x\n",
  158. le->e32_itermap);
  159. printf( " Resource table offset: %08x\n",
  160. le->e32_rsrctab);
  161. printf( " Resource table entries: %d\n",
  162. le->e32_rsrccnt);
  163. printf( " Resident names table offset: %08x\n",
  164. le->e32_restab);
  165. printf( " Entry table offset: %08x\n",
  166. le->e32_enttab);
  167. printf( " Module directives table offset: %08x\n",
  168. le->e32_dirtab);
  169. printf( " Module directives entries: %d\n",
  170. le->e32_dircnt);
  171. printf( " Fix-up page table offset: %08x\n",
  172. le->e32_fpagetab);
  173. printf( " Fix-up record table offset: %08x\n",
  174. le->e32_frectab);
  175. printf( " Imported modules name table offset: %08x\n",
  176. le->e32_impmod);
  177. printf( " Imported modules count: %d\n",
  178. le->e32_impmodcnt);
  179. printf( " Imported procedure name table offset: %08x\n",
  180. le->e32_impproc);
  181. printf( " Per-page checksum table offset: %08x\n",
  182. le->e32_pagesum);
  183. printf( " Data pages offset from top of table: %08x\n",
  184. le->e32_datapage);
  185. printf( " Preload page count: %08x\n",
  186. le->e32_preload);
  187. printf( " Non-resident names table offset: %08x\n",
  188. le->e32_nrestab);
  189. printf( " Non-resident names table length: %d\n",
  190. le->e32_cbnrestab);
  191. printf( " Non-resident names table checksum: %08x\n",
  192. le->e32_nressum);
  193. printf( " Automatic data object: %08x\n",
  194. le->e32_autodata);
  195. printf( " Debug information offset: %08x\n",
  196. le->e32_debuginfo);
  197. printf( " Debug information length: %d\n",
  198. le->e32_debuglen);
  199. printf( " Preload instance pages number: %d\n",
  200. le->e32_instpreload);
  201. printf( " Demand instance pages number: %d\n",
  202. le->e32_instdemand);
  203. printf( " Extra heap allocation: %d\n",
  204. le->e32_heapsize);
  205. printf( " VxD resource table offset: %08x\n",
  206. le->e32_winresoff);
  207. printf( " Size of VxD resource table: %d\n",
  208. le->e32_winreslen);
  209. printf( " VxD identifier: %x\n",
  210. le->e32_devid);
  211. printf( " VxD DDK version: %x\n",
  212. le->e32_ddkver);
  213. }
  214. static void dump_le_objects( const IMAGE_VXD_HEADER *le )
  215. {
  216. const struct o32_obj *pobj;
  217. unsigned int i;
  218. printf("\nObject table:\n");
  219. pobj = (const struct o32_obj *)((const unsigned char *)le + le->e32_objtab);
  220. for (i = 0; i < le->e32_objcnt; i++)
  221. {
  222. unsigned int j;
  223. const struct o32_map *pmap=0;
  224. printf(" Obj. Rel.Base Codesize Flags Tableidx Tablesize Name\n");
  225. printf(" %04X %08lx %08lx %08lx %08lx %08lx ", i + 1,
  226. pobj->o32_base, pobj->o32_size, pobj->o32_flags,
  227. pobj->o32_pagemap, pobj->o32_mapsize);
  228. for (j = 0; j < 4; j++)
  229. {
  230. if (isprint(pobj->o32_name[j]))
  231. printf("%c", pobj->o32_name[j]);
  232. else
  233. printf(".");
  234. }
  235. printf("\n");
  236. if(pobj->o32_flags & 0x0001)
  237. printf("\tReadable\n");
  238. if(pobj->o32_flags & 0x0002)
  239. printf("\tWritable\n");
  240. if(pobj->o32_flags & 0x0004)
  241. printf("\tExecutable\n");
  242. if(pobj->o32_flags & 0x0008)
  243. printf("\tResource\n");
  244. if(pobj->o32_flags & 0x0010)
  245. printf("\tDiscardable\n");
  246. if(pobj->o32_flags & 0x0020)
  247. printf("\tShared\n");
  248. if(pobj->o32_flags & 0x0040)
  249. printf("\tPreloaded\n");
  250. if(pobj->o32_flags & 0x0080)
  251. printf("\tInvalid\n");
  252. if(pobj->o32_flags & 0x2000)
  253. printf("\tUse 32\n");
  254. printf(" Page tables:\n");
  255. printf(" Tableidx Offset Flags\n");
  256. pmap = (const struct o32_map *)((const unsigned char *)le + le->e32_objmap);
  257. pmap = &(pmap[pobj->o32_pagemap - 1]);
  258. for (j = 0; j < pobj->o32_mapsize; j++)
  259. {
  260. printf(" %08lx %06x %02x\n",
  261. pobj->o32_pagemap + j,
  262. (pmap->o32_pagedataoffset << 8) + pmap->o32_pagesize,
  263. (int)pmap->o32_pageflags);
  264. pmap++;
  265. }
  266. pobj++;
  267. }
  268. }
  269. static void dump_le_names( const IMAGE_VXD_HEADER *le )
  270. {
  271. const unsigned char *pstr = (const unsigned char *)le + le->e32_restab;
  272. printf( "\nResident name table:\n" );
  273. while (*pstr)
  274. {
  275. printf( " %4d: %*.*s\n", get_word(pstr + *pstr + 1), *pstr, *pstr,
  276. pstr + 1 );
  277. pstr += *pstr + 1 + sizeof(WORD);
  278. }
  279. if (le->e32_cbnrestab)
  280. {
  281. printf( "\nNon-resident name table:\n" );
  282. pstr = PRD(le->e32_nrestab, 0);
  283. while (*pstr)
  284. {
  285. printf( " %4d: %*.*s\n", get_word(pstr + *pstr + 1), *pstr, *pstr,
  286. pstr + 1 );
  287. pstr += *pstr + 1 + sizeof(WORD);
  288. }
  289. }
  290. }
  291. static void dump_le_resources( const IMAGE_VXD_HEADER *le )
  292. {
  293. printf( "\nResources:\n" );
  294. printf( " Not Implemented\n" );
  295. }
  296. static void dump_le_modules( const IMAGE_VXD_HEADER *le )
  297. {
  298. printf( "\nImported modulename table:\n" );
  299. printf( " Not Implemented\n" );
  300. }
  301. static void dump_le_entries( const IMAGE_VXD_HEADER *le )
  302. {
  303. printf( "\nEntry table:\n" );
  304. printf( " Not Implemented\n" );
  305. }
  306. static void dump_le_fixups( const IMAGE_VXD_HEADER *le )
  307. {
  308. printf( "\nFixup table:\n" );
  309. printf( " Not Implemented\n" );
  310. }
  311. static void dump_le_VxD( const IMAGE_VXD_HEADER *le )
  312. {
  313. printf( "\nVxD descriptor:\n" );
  314. printf( " Not Implemented\n" );
  315. }
  316. void le_dump( void )
  317. {
  318. const IMAGE_DOS_HEADER *dos;
  319. const IMAGE_VXD_HEADER *le;
  320. dos = PRD(0, sizeof(*dos));
  321. if (!dos) return;
  322. le = PRD(dos->e_lfanew, sizeof(*le));
  323. dump_le_header( le );
  324. dump_le_objects( le );
  325. dump_le_resources( le );
  326. dump_le_names( le );
  327. dump_le_entries( le );
  328. dump_le_modules( le );
  329. dump_le_fixups( le );
  330. dump_le_VxD( le );
  331. }