source: trunk/src/peldr/pe.cpp@ 704

Last change on this file since 704 was 704, checked in by sandervl, 26 years ago

Exception handler support for memory mapped exe/dll loading

File size: 5.8 KB
Line 
1/* $Id: pe.cpp,v 1.7 1999-08-26 07:48:14 sandervl Exp $ */
2
3/*
4 * PELDR main exe loader code
5 *
6 * Copyright 1998 Sander van Leeuwen (sandervl@xs4all.nl)
7 *
8 *
9 * Project Odin Software License can be found in LICENSE.TXT
10 *
11 */
12#define INCL_DOSFILEMGR /* File Manager values */
13#define INCL_DOSERRORS /* DOS Error values */
14#define INCL_DOSPROCESS /* DOS Process values */
15#define INCL_DOSMISC /* DOS Miscellanous values */
16#define INCL_DOSMODULEMGR
17#define INCL_WIN
18#include <os2.h>
19#include <bseord.h>
20#include <stdio.h>
21#include <string.h>
22#include <stdlib.h>
23#include <string.h>
24#include <assert.h>
25#include <win32type.h>
26#include <misc.h>
27#include <winexe.h>
28#include <windll.h>
29#include <wprocess.h>
30#include "pe.h"
31#include "exceptions.h"
32#include "..\kernel32\exceptutil.h"
33
34char INFO_BANNER[] = "Usage: PE winexe commandline";
35char szErrorTitle[] = "Odin";
36char szMemErrorMsg[] = "Memory allocation failure";
37char szFileErrorMsg[] = "File IO error";
38char szPEErrorMsg[] = "Not a valid win32 exe. (perhaps 16 bits windows)";
39char szCPUErrorMsg[] = "Executable doesn't run on x86 machines";
40char szExeErrorMsg[] = "File isn't an executable";
41char szInteralErrorMsg[]= "Internal Error";
42
43char fullpath[CCHMAXPATH];
44
45typedef HAB (* APIENTRY WININITIALIZEPROC)(ULONG flOptions);
46typedef BOOL (* APIENTRY WINTERMINATEPROC)(HAB hab);
47typedef HMQ (* APIENTRY WINCREATEMSGQUEUEPROC) (HAB hab, LONG cmsg);
48typedef BOOL (* APIENTRY WINDESTROYMSGQUEUEPROC) (HMQ hmq);
49typedef ULONG (* APIENTRY WINMESSAGEBOXPROC) (HWND hwndParent,
50 HWND hwndOwner,
51 PCSZ pszText,
52 PCSZ pszCaption,
53 ULONG idWindow,
54 ULONG flStyle);
55typedef void (* KRNL32EXCEPTPROC) (void *exceptframe);
56
57WININITIALIZEPROC MyWinInitialize = 0;
58WINTERMINATEPROC MyWinTerminate = 0;
59WINCREATEMSGQUEUEPROC MyWinCreateMsgQueue = 0;
60WINDESTROYMSGQUEUEPROC MyWinDestroyMsgQueue = 0;
61WINMESSAGEBOXPROC MyWinMessageBox = 0;
62KRNL32EXCEPTPROC Krnl32SetExceptionHandler = 0;
63KRNL32EXCEPTPROC Krnl32UnsetExceptionHandler = 0;
64
65WIN32CTOR CreateWin32Exe = 0;
66
67int main(int argc, char *argv[])
68{
69 HAB hab = 0; /* PM anchor block handle */
70 HMQ hmq = 0; /* Message queue handle */
71 char *szCmdLine;
72 char exeName[CCHMAXPATH];
73 PPIB ppib;
74 PTIB ptib;
75 Win32Exe *WinExe;
76 APIRET rc;
77 HMODULE hmodPMWin = 0, hmodKernel32 = 0;
78 WINEXCEPTION_FRAME exceptFrame;
79 ULONG curdisk, curlogdisk, flength = CCHMAXPATH;
80
81 rc = DosLoadModule(exeName, sizeof(exeName), "PMWIN.DLL", &hmodPMWin);
82 rc = DosQueryProcAddr(hmodPMWin, ORD_WIN32INITIALIZE, NULL, (PFN *)&MyWinInitialize);
83 rc = DosQueryProcAddr(hmodPMWin, ORD_WIN32TERMINATE, NULL, (PFN *)&MyWinTerminate);
84 rc = DosQueryProcAddr(hmodPMWin, ORD_WIN32CREATEMSGQUEUE, NULL, (PFN *)&MyWinCreateMsgQueue);
85 rc = DosQueryProcAddr(hmodPMWin, ORD_WIN32DESTROYMSGQUEUE, NULL, (PFN *)&MyWinDestroyMsgQueue);
86 rc = DosQueryProcAddr(hmodPMWin, ORD_WIN32MESSAGEBOX, NULL, (PFN *)&MyWinMessageBox);
87
88 rc = DosLoadModule(exeName, sizeof(exeName), "KERNEL32.DLL", &hmodKernel32);
89 rc = DosQueryProcAddr(hmodKernel32, 0, "CreateWin32Exe", (PFN *)&CreateWin32Exe);
90 rc = DosQueryProcAddr(hmodKernel32, 0, "OS2SetExceptionHandler", (PFN *)&Krnl32SetExceptionHandler);
91 rc = DosQueryProcAddr(hmodKernel32, 0, "OS2UnsetExceptionHandler", (PFN *)&Krnl32UnsetExceptionHandler);
92
93 if ((hab = MyWinInitialize(0)) == 0L) /* Initialize PM */
94 goto fail;
95
96 hmq = MyWinCreateMsgQueue(hab, 0);
97
98 if(argc < 2) {
99 MyWinMessageBox(HWND_DESKTOP, NULL, INFO_BANNER, szErrorTitle, 0, MB_OK | MB_ERROR | MB_MOVEABLE);
100 goto fail;
101 }
102
103 strcpy(exeName, argv[1]);
104 strupr(exeName);
105 if(strstr(exeName, ".EXE") == NULL) {
106 strcat(exeName, ".EXE");
107 }
108 WinExe = CreateWin32Exe(exeName);
109 if(WinExe == NULL) {
110 MyWinMessageBox(HWND_DESKTOP, HWND_DESKTOP, szMemErrorMsg, szErrorTitle, 0, MB_OK | MB_ERROR | MB_MOVEABLE);
111 goto fail;
112 }
113 rc = DosGetInfoBlocks(&ptib, &ppib);
114 if(rc) {
115 MyWinMessageBox(HWND_DESKTOP, HWND_DESKTOP, szInteralErrorMsg, szErrorTitle, 0, MB_OK | MB_ERROR | MB_MOVEABLE);
116 delete WinExe;
117 goto fail;
118 }
119 szCmdLine = ppib->pib_pchcmd;
120 while(*szCmdLine == ' ' && *szCmdLine ) //skip leading spaces
121 szCmdLine++;
122 while(*szCmdLine != ' ' && *szCmdLine ) //skip pe (.exe)
123 szCmdLine++;
124 while(*szCmdLine == ' ' && *szCmdLine ) //skip spaces
125 szCmdLine++;
126
127 DosQueryCurrentDisk(&curdisk, &curlogdisk);
128 DosQueryCurrentDir(curdisk, &fullpath[3], &flength);
129 fullpath[0] = 'A' + (curdisk-1);
130 fullpath[1] = ':';
131 fullpath[2] = '\\';
132 strcat(fullpath, "\\");
133 strcat(fullpath, exeName);
134 WinExe->setFullPath(fullpath);
135 WinExe->setCommandLine(szCmdLine);
136
137 Krnl32SetExceptionHandler(&exceptFrame);
138 if(WinExe->init(ReserveMem()) == FALSE) {
139 delete WinExe;
140 goto fail;
141 }
142 Krnl32UnsetExceptionHandler(&exceptFrame);
143 WinExe->start();
144
145 delete WinExe;
146
147 if(hmq) MyWinDestroyMsgQueue( hmq ); /* Tidy up... */
148 MyWinTerminate( hab ); /* Terminate the application */
149
150 DosFreeModule(hmodPMWin);
151 DosFreeModule(hmodKernel32);
152 return 0;
153
154fail:
155 if(hmq) MyWinDestroyMsgQueue( hmq ); /* Tidy up... */
156 if(hab) MyWinTerminate( hab ); /* Terminate the application */
157
158 if(hmodPMWin) DosFreeModule(hmodPMWin);
159 if(hmodKernel32) DosFreeModule(hmodKernel32);
160 return(1);
161}
162//******************************************************************************
163//******************************************************************************
Note: See TracBrowser for help on using the repository browser.