Adapted to CreateProcess changes.

This commit is contained in:
Ulrich Weigand 1999-02-28 11:19:10 +00:00 committed by Alexandre Julliard
parent fe14b6603d
commit f6a9361942
7 changed files with 125 additions and 128 deletions

View File

@ -30,10 +30,7 @@ typedef struct _DOSTASK {
#define MZ_SUPPORTED #define MZ_SUPPORTED
struct _NE_MODULE; extern BOOL MZ_InitTask( LPDOSTASK lpDosTask );
extern int MZ_InitTask( LPDOSTASK lpDosTask );
extern int MZ_InitMemory( LPDOSTASK lpDosTask, struct _NE_MODULE *pModule );
extern void MZ_KillModule( LPDOSTASK lpDosTask ); extern void MZ_KillModule( LPDOSTASK lpDosTask );
extern LPDOSTASK MZ_AllocDPMITask( HMODULE16 hModule ); extern LPDOSTASK MZ_AllocDPMITask( HMODULE16 hModule );
@ -43,8 +40,9 @@ extern LPDOSTASK MZ_AllocDPMITask( HMODULE16 hModule );
extern void MZ_Tick( WORD handle ); extern void MZ_Tick( WORD handle );
extern HINSTANCE16 MZ_CreateProcess( LPCSTR name, LPCSTR cmdline, LPCSTR env, BOOL inherit, extern BOOL MZ_CreateProcess( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmdline,
LPSTARTUPINFOA startup, LPPROCESS_INFORMATION info ); LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup,
LPPROCESS_INFORMATION info );
extern int DOSVM_Enter( PCONTEXT context ); extern int DOSVM_Enter( PCONTEXT context );
extern void DOSVM_SetTimer( unsigned ticks ); extern void DOSVM_SetTimer( unsigned ticks );
extern unsigned DOSVM_GetTimer( void ); extern unsigned DOSVM_GetTimer( void );

View File

@ -33,12 +33,12 @@ extern HRSRC PE_FindResourceExW(struct _wine_modref*,LPCWSTR,LPCWSTR,WORD);
extern DWORD PE_SizeofResource(HMODULE,HRSRC); extern DWORD PE_SizeofResource(HMODULE,HRSRC);
extern HMODULE PE_LoadLibraryExA(LPCSTR,HFILE,DWORD); extern HMODULE PE_LoadLibraryExA(LPCSTR,HFILE,DWORD);
extern HGLOBAL PE_LoadResource(struct _wine_modref *wm,HRSRC); extern HGLOBAL PE_LoadResource(struct _wine_modref *wm,HRSRC);
extern HMODULE PE_LoadImage( LPCSTR name, OFSTRUCT *ofs, LPCSTR *modName ); extern HMODULE PE_LoadImage( HFILE hFile, OFSTRUCT *ofs, LPCSTR *modName );
extern struct _wine_modref *PE_CreateModule( HMODULE hModule, OFSTRUCT *ofs, extern struct _wine_modref *PE_CreateModule( HMODULE hModule, OFSTRUCT *ofs,
DWORD flags, BOOL builtin ); DWORD flags, BOOL builtin );
extern HINSTANCE16 PE_CreateProcess( LPCSTR name, LPCSTR cmd_line, extern BOOL PE_CreateProcess( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmd_line,
LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup, LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup,
LPPROCESS_INFORMATION info ); LPPROCESS_INFORMATION info );
struct _THDB; /* forward definition */ struct _THDB; /* forward definition */
extern void PE_InitTls(struct _THDB*); extern void PE_InitTls(struct _THDB*);

View File

@ -18,6 +18,7 @@
#include <sys/time.h> #include <sys/time.h>
#include "windef.h" #include "windef.h"
#include "wine/winbase16.h" #include "wine/winbase16.h"
#include "winerror.h"
#include "module.h" #include "module.h"
#include "peexe.h" #include "peexe.h"
#include "neexe.h" #include "neexe.h"
@ -174,11 +175,11 @@ static WORD MZ_InitEnvironment( LPDOSTASK lpDosTask, LPCSTR env, LPCSTR name )
return seg; return seg;
} }
int MZ_InitMemory( LPDOSTASK lpDosTask, NE_MODULE *pModule ) static BOOL MZ_InitMemory( LPDOSTASK lpDosTask, NE_MODULE *pModule )
{ {
int x; int x;
if (lpDosTask->img_ofs) return 32; /* already allocated */ if (lpDosTask->img_ofs) return TRUE; /* already allocated */
/* allocate 1MB+64K shared memory */ /* allocate 1MB+64K shared memory */
lpDosTask->img_ofs=START_OFFSET; lpDosTask->img_ofs=START_OFFSET;
@ -199,7 +200,7 @@ int MZ_InitMemory( LPDOSTASK lpDosTask, NE_MODULE *pModule )
#endif #endif
if (lpDosTask->img==(LPVOID)-1) { if (lpDosTask->img==(LPVOID)-1) {
ERR(module,"could not map shared memory, error=%s\n",strerror(errno)); ERR(module,"could not map shared memory, error=%s\n",strerror(errno));
return 0; return FALSE;
} }
TRACE(module,"DOS VM86 image mapped at %08lx\n",(DWORD)lpDosTask->img); TRACE(module,"DOS VM86 image mapped at %08lx\n",(DWORD)lpDosTask->img);
pModule->dos_image=lpDosTask->img; pModule->dos_image=lpDosTask->img;
@ -210,11 +211,11 @@ int MZ_InitMemory( LPDOSTASK lpDosTask, NE_MODULE *pModule )
MZ_InitHandlers(lpDosTask); MZ_InitHandlers(lpDosTask);
MZ_InitXMS(lpDosTask); MZ_InitXMS(lpDosTask);
MZ_InitDPMI(lpDosTask); MZ_InitDPMI(lpDosTask);
return lpDosTask->hModule; return TRUE;
} }
static int MZ_LoadImage( HFILE16 hFile, LPCSTR name, LPCSTR cmdline, static BOOL MZ_LoadImage( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmdline,
LPCSTR env, LPDOSTASK lpDosTask, NE_MODULE *pModule ) LPCSTR env, LPDOSTASK lpDosTask, NE_MODULE *pModule )
{ {
IMAGE_DOS_HEADER mz_header; IMAGE_DOS_HEADER mz_header;
DWORD image_start,image_size,min_size,max_size,avail; DWORD image_start,image_size,min_size,max_size,avail;
@ -223,14 +224,12 @@ static int MZ_LoadImage( HFILE16 hFile, LPCSTR name, LPCSTR cmdline,
SEGPTR reloc; SEGPTR reloc;
WORD env_seg; WORD env_seg;
if ((_hread16(hFile,&mz_header,sizeof(mz_header)) != sizeof(mz_header)) || _llseek(hFile,0,FILE_BEGIN);
if ((_lread(hFile,&mz_header,sizeof(mz_header)) != sizeof(mz_header)) ||
(mz_header.e_magic != IMAGE_DOS_SIGNATURE)) { (mz_header.e_magic != IMAGE_DOS_SIGNATURE)) {
#if 0
return 11; /* invalid exe */
#endif
old_com=1; /* assume .COM file */ old_com=1; /* assume .COM file */
image_start=0; image_start=0;
image_size=GetFileSize(FILE_GetHandle(hFile),NULL); image_size=GetFileSize(hFile,NULL);
min_size=0x10000; max_size=0x100000; min_size=0x10000; max_size=0x100000;
mz_header.e_crlc=0; mz_header.e_crlc=0;
mz_header.e_ss=0; mz_header.e_sp=0xFFFE; mz_header.e_ss=0; mz_header.e_sp=0xFFFE;
@ -248,20 +247,22 @@ static int MZ_LoadImage( HFILE16 hFile, LPCSTR name, LPCSTR cmdline,
MZ_InitMemory(lpDosTask,pModule); MZ_InitMemory(lpDosTask,pModule);
/* allocate environment block */ /* allocate environment block */
env_seg=MZ_InitEnvironment(lpDosTask,env,name); env_seg=MZ_InitEnvironment(lpDosTask,env,ofs->szPathName);
/* allocate memory for the executable */ /* allocate memory for the executable */
TRACE(module,"Allocating DOS memory (min=%ld, max=%ld)\n",min_size,max_size); TRACE(module,"Allocating DOS memory (min=%ld, max=%ld)\n",min_size,max_size);
avail=DOSMEM_Available(lpDosTask->hModule); avail=DOSMEM_Available(lpDosTask->hModule);
if (avail<min_size) { if (avail<min_size) {
ERR(module, "insufficient DOS memory\n"); ERR(module, "insufficient DOS memory\n");
return 0; SetLastError(ERROR_NOT_ENOUGH_MEMORY);
return FALSE;
} }
if (avail>max_size) avail=max_size; if (avail>max_size) avail=max_size;
psp_start=DOSMEM_GetBlock(lpDosTask->hModule,avail,&lpDosTask->psp_seg); psp_start=DOSMEM_GetBlock(lpDosTask->hModule,avail,&lpDosTask->psp_seg);
if (!psp_start) { if (!psp_start) {
ERR(module, "error allocating DOS memory\n"); ERR(module, "error allocating DOS memory\n");
return 0; SetLastError(ERROR_NOT_ENOUGH_MEMORY);
return FALSE;
} }
lpDosTask->load_seg=lpDosTask->psp_seg+(old_com?0:PSP_SIZE); lpDosTask->load_seg=lpDosTask->psp_seg+(old_com?0:PSP_SIZE);
load_start=psp_start+(PSP_SIZE<<4); load_start=psp_start+(PSP_SIZE<<4);
@ -269,18 +270,22 @@ static int MZ_LoadImage( HFILE16 hFile, LPCSTR name, LPCSTR cmdline,
/* load executable image */ /* load executable image */
TRACE(module,"loading DOS %s image, %08lx bytes\n",old_com?"COM":"EXE",image_size); TRACE(module,"loading DOS %s image, %08lx bytes\n",old_com?"COM":"EXE",image_size);
_llseek16(hFile,image_start,FILE_BEGIN); _llseek(hFile,image_start,FILE_BEGIN);
if ((_hread16(hFile,load_start,image_size)) != image_size) if ((_lread(hFile,load_start,image_size)) != image_size) {
return 11; /* invalid exe */ SetLastError(ERROR_BAD_FORMAT);
return FALSE;
}
if (mz_header.e_crlc) { if (mz_header.e_crlc) {
/* load relocation table */ /* load relocation table */
TRACE(module,"loading DOS EXE relocation table, %d entries\n",mz_header.e_crlc); TRACE(module,"loading DOS EXE relocation table, %d entries\n",mz_header.e_crlc);
/* FIXME: is this too slow without read buffering? */ /* FIXME: is this too slow without read buffering? */
_llseek16(hFile,mz_header.e_lfarlc,FILE_BEGIN); _llseek(hFile,mz_header.e_lfarlc,FILE_BEGIN);
for (x=0; x<mz_header.e_crlc; x++) { for (x=0; x<mz_header.e_crlc; x++) {
if (_lread16(hFile,&reloc,sizeof(reloc)) != sizeof(reloc)) if (_lread(hFile,&reloc,sizeof(reloc)) != sizeof(reloc)) {
return 11; /* invalid exe */ SetLastError(ERROR_BAD_FORMAT);
return FALSE;
}
*(WORD*)SEGPTR16(load_start,reloc)+=lpDosTask->load_seg; *(WORD*)SEGPTR16(load_start,reloc)+=lpDosTask->load_seg;
} }
} }
@ -291,8 +296,7 @@ static int MZ_LoadImage( HFILE16 hFile, LPCSTR name, LPCSTR cmdline,
lpDosTask->init_sp=mz_header.e_sp; lpDosTask->init_sp=mz_header.e_sp;
TRACE(module,"entry point: %04x:%04x\n",lpDosTask->init_cs,lpDosTask->init_ip); TRACE(module,"entry point: %04x:%04x\n",lpDosTask->init_cs,lpDosTask->init_ip);
return TRUE;
return lpDosTask->hModule;
} }
LPDOSTASK MZ_AllocDPMITask( HMODULE16 hModule ) LPDOSTASK MZ_AllocDPMITask( HMODULE16 hModule )
@ -335,17 +339,17 @@ static void MZ_InitTimer( LPDOSTASK lpDosTask, int ver )
} }
} }
int MZ_InitTask( LPDOSTASK lpDosTask ) BOOL MZ_InitTask( LPDOSTASK lpDosTask )
{ {
int read_fd[2],write_fd[2]; int read_fd[2],write_fd[2];
pid_t child; pid_t child;
char *fname,*farg,arg[16],fproc[64],path[256],*fpath; char *fname,*farg,arg[16],fproc[64],path[256],*fpath;
if (!lpDosTask) return 0; if (!lpDosTask) return FALSE;
/* create read pipe */ /* create read pipe */
if (pipe(read_fd)<0) return 0; if (pipe(read_fd)<0) return FALSE;
if (pipe(write_fd)<0) { if (pipe(write_fd)<0) {
close(read_fd[0]); close(read_fd[1]); return 0; close(read_fd[0]); close(read_fd[1]); return FALSE;
} }
lpDosTask->read_pipe=read_fd[0]; lpDosTask->read_pipe=read_fd[0];
lpDosTask->write_pipe=write_fd[1]; lpDosTask->write_pipe=write_fd[1];
@ -361,7 +365,7 @@ int MZ_InitTask( LPDOSTASK lpDosTask )
TRACE(module,"Loading DOS VM support module (hmodule=%04x)\n",lpDosTask->hModule); TRACE(module,"Loading DOS VM support module (hmodule=%04x)\n",lpDosTask->hModule);
if ((child=fork())<0) { if ((child=fork())<0) {
close(write_fd[0]); close(write_fd[1]); close(write_fd[0]); close(write_fd[1]);
close(read_fd[0]); close(read_fd[1]); return 0; close(read_fd[0]); close(read_fd[1]); return FALSE;
} }
if (child!=0) { if (child!=0) {
/* parent process */ /* parent process */
@ -376,7 +380,7 @@ int MZ_InitTask( LPDOSTASK lpDosTask )
/* failure */ /* failure */
ERR(module,"dosmod has failed to initialize\n"); ERR(module,"dosmod has failed to initialize\n");
if (lpDosTask->mm_name[0]!=0) unlink(lpDosTask->mm_name); if (lpDosTask->mm_name[0]!=0) unlink(lpDosTask->mm_name);
return 0; return FALSE;
} }
} while (0); } while (0);
/* the child has now mmaped the temp file, it's now safe to unlink. /* the child has now mmaped the temp file, it's now safe to unlink.
@ -408,35 +412,31 @@ int MZ_InitTask( LPDOSTASK lpDosTask )
ERR(module,"Failed to spawn dosmod, error=%s\n",strerror(errno)); ERR(module,"Failed to spawn dosmod, error=%s\n",strerror(errno));
exit(1); exit(1);
} }
return lpDosTask->hModule; return TRUE;
} }
HINSTANCE16 MZ_CreateProcess( LPCSTR name, LPCSTR cmdline, LPCSTR env, BOOL inherit, BOOL MZ_CreateProcess( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmdline,
LPSTARTUPINFOA startup, LPPROCESS_INFORMATION info ) LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup,
LPPROCESS_INFORMATION info )
{ {
LPDOSTASK lpDosTask = NULL; /* keep gcc from complaining */ LPDOSTASK lpDosTask = NULL; /* keep gcc from complaining */
HMODULE16 hModule; HMODULE16 hModule;
HINSTANCE16 hInstance;
PDB *pdb = PROCESS_Current(); PDB *pdb = PROCESS_Current();
TDB *pTask = (TDB*)GlobalLock16( GetCurrentTask() ); TDB *pTask = (TDB*)GlobalLock16( GetCurrentTask() );
NE_MODULE *pModule = pTask ? NE_GetPtr( pTask->hModule ) : NULL; NE_MODULE *pModule = pTask ? NE_GetPtr( pTask->hModule ) : NULL;
HFILE16 hFile; int alloc = !(pModule && pModule->dos_image);
OFSTRUCT ofs;
int err, alloc = !(pModule && pModule->dos_image);
GlobalUnlock16( GetCurrentTask() ); if (alloc && (lpDosTask = calloc(1, sizeof(DOSTASK))) == NULL) {
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
if (alloc && (lpDosTask = calloc(1, sizeof(DOSTASK))) == NULL) return FALSE;
return 0; }
if ((hFile = OpenFile16( name, &ofs, OF_READ )) == HFILE_ERROR16)
return 2; /* File not found */
if ((!env)&&pdb) env = pdb->env_db->environ; if ((!env)&&pdb) env = pdb->env_db->environ;
if (alloc) { if (alloc) {
if ((hModule = MODULE_CreateDummyModule(&ofs, NULL)) < 32) if ((hModule = MODULE_CreateDummyModule(ofs, NULL)) < 32) {
return hModule; SetLastError(hModule);
return FALSE;
}
lpDosTask->hModule = hModule; lpDosTask->hModule = hModule;
pModule = (NE_MODULE *)GlobalLock16(hModule); pModule = (NE_MODULE *)GlobalLock16(hModule);
@ -444,32 +444,29 @@ HINSTANCE16 MZ_CreateProcess( LPCSTR name, LPCSTR cmdline, LPCSTR env, BOOL inhe
lpDosTask->img=NULL; lpDosTask->mm_name[0]=0; lpDosTask->mm_fd=-1; lpDosTask->img=NULL; lpDosTask->mm_name[0]=0; lpDosTask->mm_fd=-1;
} else lpDosTask=pModule->lpDosTask; } else lpDosTask=pModule->lpDosTask;
err = MZ_LoadImage( hFile, name, cmdline, env, lpDosTask, pModule ); if (!MZ_LoadImage( hFile, ofs, cmdline, env, lpDosTask, pModule )) {
_lclose16(hFile); if (alloc) {
if (alloc) {
pModule->dos_image = lpDosTask->img;
if (err<32) {
if (lpDosTask->mm_name[0]!=0) { if (lpDosTask->mm_name[0]!=0) {
if (lpDosTask->img!=NULL) munmap(lpDosTask->img,0x110000-START_OFFSET); if (lpDosTask->img!=NULL) munmap(lpDosTask->img,0x110000-START_OFFSET);
if (lpDosTask->mm_fd>=0) close(lpDosTask->mm_fd); if (lpDosTask->mm_fd>=0) close(lpDosTask->mm_fd);
unlink(lpDosTask->mm_name); unlink(lpDosTask->mm_name);
} else } else
if (lpDosTask->img!=NULL) VirtualFree(lpDosTask->img,0x110000,MEM_RELEASE); if (lpDosTask->img!=NULL) VirtualFree(lpDosTask->img,0x110000,MEM_RELEASE);
return err;
} }
err = MZ_InitTask( lpDosTask ); return FALSE;
if (err<32) { }
if (alloc) {
pModule->dos_image = lpDosTask->img;
if (!MZ_InitTask( lpDosTask )) {
MZ_KillModule( lpDosTask ); MZ_KillModule( lpDosTask );
/* FIXME: cleanup hModule */ /* FIXME: cleanup hModule */
return err; SetLastError(ERROR_GEN_FAILURE);
return FALSE;
} }
if (!PROCESS_Create( pModule, cmdline, env, 0, 0, inherit, startup, info ))
hInstance = NE_CreateInstance(pModule, NULL, (cmdline == NULL)); return FALSE;
PROCESS_Create( pModule, cmdline, env, hInstance, 0, inherit, startup, info );
return hInstance;
} else {
return (err<32) ? err : pTask->hInstance;
} }
return TRUE;
} }
void MZ_KillModule( LPDOSTASK lpDosTask ) void MZ_KillModule( LPDOSTASK lpDosTask )
@ -494,11 +491,13 @@ void MZ_KillModule( LPDOSTASK lpDosTask )
#else /* !MZ_SUPPORTED */ #else /* !MZ_SUPPORTED */
HINSTANCE16 MZ_CreateProcess( LPCSTR name, LPCSTR cmdline, LPCSTR env, BOOL inherit, BOOL MZ_CreateProcess( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmdline,
LPSTARTUPINFOA startup, LPPROCESS_INFORMATION info ) LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup,
LPPROCESS_INFORMATION info )
{ {
WARN(module,"DOS executables not supported on this architecture\n"); WARN(module,"DOS executables not supported on this architecture\n");
return (HMODULE16)11; /* invalid exe */ SetLastError(ERROR_BAD_FORMAT);
return FALSE;
} }
#endif #endif

View File

@ -267,7 +267,6 @@ HINSTANCE MAIN_WinelibInit( int *argc, char *argv[] )
NE_MODULE *pModule; NE_MODULE *pModule;
OFSTRUCT ofs; OFSTRUCT ofs;
HMODULE16 hModule; HMODULE16 hModule;
HINSTANCE16 hInstance;
/* Create the initial process */ /* Create the initial process */
if (!PROCESS_Init()) return 0; if (!PROCESS_Init()) return 0;
@ -292,9 +291,7 @@ HINSTANCE MAIN_WinelibInit( int *argc, char *argv[] )
pModule->flags = NE_FFLAGS_WIN32; pModule->flags = NE_FFLAGS_WIN32;
pModule->module32 = wm->module; pModule->module32 = wm->module;
hInstance = NE_CreateInstance( pModule, NULL, TRUE ); if (!TASK_Create( THREAD_Current(), pModule, 0, 0, FALSE )) return 0;
PROCESS_Current()->task = TASK_Create( THREAD_Current(), pModule, hInstance, 0, FALSE );
TASK_StartTask( PROCESS_Current()->task ); TASK_StartTask( PROCESS_Current()->task );
/* Initialize GDI and USER */ /* Initialize GDI and USER */

View File

@ -43,6 +43,7 @@
#include <sys/mman.h> #include <sys/mman.h>
#include "windef.h" #include "windef.h"
#include "winbase.h" #include "winbase.h"
#include "winerror.h"
#include "callback.h" #include "callback.h"
#include "file.h" #include "file.h"
#include "heap.h" #include "heap.h"
@ -452,10 +453,9 @@ static void do_relocations( unsigned int load_addr, IMAGE_BASE_RELOCATION *r )
* BUT we have to map the whole image anyway, for Win32 programs sometimes * BUT we have to map the whole image anyway, for Win32 programs sometimes
* want to access them. (HMODULE32 point to the start of it) * want to access them. (HMODULE32 point to the start of it)
*/ */
HMODULE PE_LoadImage( LPCSTR name, OFSTRUCT *ofs, LPCSTR *modName ) HMODULE PE_LoadImage( HFILE hFile, OFSTRUCT *ofs, LPCSTR *modName )
{ {
HMODULE hModule; HMODULE hModule;
HFILE hFile;
HANDLE mapping; HANDLE mapping;
IMAGE_NT_HEADERS *nt; IMAGE_NT_HEADERS *nt;
@ -464,20 +464,6 @@ HMODULE PE_LoadImage( LPCSTR name, OFSTRUCT *ofs, LPCSTR *modName )
BY_HANDLE_FILE_INFORMATION bhfi; BY_HANDLE_FILE_INFORMATION bhfi;
int i, rawsize, lowest_va, lowest_fa, vma_size, file_size = 0; int i, rawsize, lowest_va, lowest_fa, vma_size, file_size = 0;
DWORD load_addr, aoep, reloc = 0; DWORD load_addr, aoep, reloc = 0;
char dllname[256], *p;
/* Append .DLL to name if no extension present */
strcpy( dllname, name );
if ((p = strrchr( dllname, '\\' ))) p++; else p = dllname;
if (!strchr( p, '.' )) strcat( dllname, ".DLL" );
/* Open PE file */
hFile = OpenFile( dllname, ofs, OF_READ | OF_SHARE_DENY_WRITE );
if ( hFile == HFILE_ERROR )
{
WARN( win32, "OpenFile error %ld\n", GetLastError() );
return 2;
}
/* Retrieve file size */ /* Retrieve file size */
if ( GetFileInformationByHandle( hFile, &bhfi ) ) if ( GetFileInformationByHandle( hFile, &bhfi ) )
@ -486,7 +472,6 @@ HMODULE PE_LoadImage( LPCSTR name, OFSTRUCT *ofs, LPCSTR *modName )
/* Map the PE file somewhere */ /* Map the PE file somewhere */
mapping = CreateFileMappingA( hFile, NULL, PAGE_READONLY | SEC_COMMIT, mapping = CreateFileMappingA( hFile, NULL, PAGE_READONLY | SEC_COMMIT,
0, 0, NULL ); 0, 0, NULL );
CloseHandle( hFile );
if (!mapping) if (!mapping)
{ {
WARN( win32, "CreateFileMapping error %ld\n", GetLastError() ); WARN( win32, "CreateFileMapping error %ld\n", GetLastError() );
@ -810,26 +795,38 @@ HMODULE PE_LoadLibraryExA (LPCSTR name,
HMODULE16 hModule16; HMODULE16 hModule16;
NE_MODULE *pModule; NE_MODULE *pModule;
WINE_MODREF *wm; WINE_MODREF *wm;
BOOL builtin; BOOL builtin = TRUE;
char dllname[256], *p;
/* Check for already loaded module */ /* Check for already loaded module */
if ((hModule32 = MODULE_FindModule( name ))) if ((hModule32 = MODULE_FindModule( name )))
return hModule32; return hModule32;
/* try to load builtin, enabled modules first */ /* Append .DLL to name if no extension present */
if ((hModule32 = BUILTIN32_LoadImage( name, &ofs, FALSE ))) strcpy( dllname, name );
builtin = TRUE; if (!(p = strrchr( dllname, '.')) || strchr( p, '/' ) || strchr( p, '\\'))
/* try to load the specified dll/exe */ strcat( dllname, ".DLL" );
else if ((hModule32 = PE_LoadImage( name, &ofs, &modName )) >= 32)
builtin = FALSE; /* Try to load builtin enabled modules first */
/* Now try the built-in even if disabled */ if ( !(hModule32 = BUILTIN32_LoadImage( name, &ofs, FALSE )) )
else if ((hModule32 = BUILTIN32_LoadImage( name, &ofs, TRUE )))
{ {
WARN( module, "Could not load external DLL '%s', using built-in module.\n", name ); /* Load PE module */
builtin = TRUE;
hFile = OpenFile( dllname, &ofs, OF_READ | OF_SHARE_DENY_WRITE );
if ( hFile != HFILE_ERROR )
if ( (hModule32 = PE_LoadImage( hFile, &ofs, &modName )) >= 32 )
builtin = FALSE;
CloseHandle( hFile );
} }
else
return 0; /* Now try the built-in even if disabled */
if ( builtin )
if ( (hModule32 = BUILTIN32_LoadImage( name, &ofs, TRUE )) )
WARN( module, "Could not load external DLL '%s', using built-in module.\n", name );
else
return 0;
/* Create 16-bit dummy module */ /* Create 16-bit dummy module */
if ((hModule16 = MODULE_CreateDummyModule( &ofs, modName )) < 32) return hModule16; if ((hModule16 = MODULE_CreateDummyModule( &ofs, modName )) < 32) return hModule16;
@ -853,45 +850,52 @@ HMODULE PE_LoadLibraryExA (LPCSTR name,
} }
/***************************************************************************** /*****************************************************************************
* Load the PE main .EXE. All other loading is done by PE_LoadLibraryEx32A * Load the PE main .EXE. All other loading is done by PE_LoadLibraryExA
* FIXME: this function should use PE_LoadLibraryEx32A, but currently can't * FIXME: this function should use PE_LoadLibraryExA, but currently can't
* due to the PROCESS_Create stuff. * due to the PROCESS_Create stuff.
*/ */
HINSTANCE16 PE_CreateProcess( LPCSTR name, LPCSTR cmd_line, BOOL PE_CreateProcess( HFILE hFile, OFSTRUCT *ofs, LPCSTR cmd_line,
LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup, LPCSTR env, BOOL inherit, LPSTARTUPINFOA startup,
LPPROCESS_INFORMATION info ) LPPROCESS_INFORMATION info )
{ {
LPCSTR modName = NULL; LPCSTR modName = NULL;
HMODULE16 hModule16; HMODULE16 hModule16;
HMODULE hModule32; HMODULE hModule32;
HINSTANCE16 hInstance;
NE_MODULE *pModule; NE_MODULE *pModule;
OFSTRUCT ofs;
PDB *process;
/* Load file */ /* Load file */
if ((hModule32 = PE_LoadImage( name, &ofs, &modName )) < 32) if ( (hModule32 = PE_LoadImage( hFile, ofs, &modName )) < 32 )
return hModule32; {
SetLastError( hModule32 );
return FALSE;
}
#if 0 #if 0
if (PE_HEADER(hModule32)->FileHeader.Characteristics & IMAGE_FILE_DLL) if (PE_HEADER(hModule32)->FileHeader.Characteristics & IMAGE_FILE_DLL)
return 20; /* FIXME: not the right error code */ {
SetLastError( 20 ); /* FIXME: not the right error code */
return FALSE;
}
#endif #endif
/* Create 16-bit dummy module */ /* Create 16-bit dummy module */
if ((hModule16 = MODULE_CreateDummyModule( &ofs, modName )) < 32) return hModule16; if ( (hModule16 = MODULE_CreateDummyModule( ofs, modName )) < 32 )
{
SetLastError( hModule16 );
return FALSE;
}
pModule = (NE_MODULE *)GlobalLock16( hModule16 ); pModule = (NE_MODULE *)GlobalLock16( hModule16 );
pModule->flags = NE_FFLAGS_WIN32; pModule->flags = NE_FFLAGS_WIN32;
pModule->module32 = hModule32; pModule->module32 = hModule32;
/* Create new process */ /* Create new process */
hInstance = NE_CreateInstance( pModule, NULL, FALSE ); if ( !PROCESS_Create( pModule, cmd_line, env,
process = PROCESS_Create( pModule, cmd_line, env, 0, 0, inherit, startup, info ) )
hInstance, 0, inherit, startup, info ); return FALSE;
/* Note: PE_CreateModule and the remaining process initialization will /* Note: PE_CreateModule and the remaining process initialization will
be done in the context of the new process, in TASK_CallToStart */ be done in the context of the new process, in TASK_CallToStart */
return hInstance; return TRUE;
} }
/********************************************************************* /*********************************************************************

View File

@ -119,7 +119,6 @@ void MAIN_EmulatorRun( void )
int main( int argc, char *argv[] ) int main( int argc, char *argv[] )
{ {
NE_MODULE *pModule; NE_MODULE *pModule;
HINSTANCE16 hInstance;
extern char * DEBUG_argv0; extern char * DEBUG_argv0;
__winelib = 0; /* First of all, clear the Winelib flag */ __winelib = 0; /* First of all, clear the Winelib flag */
@ -166,8 +165,7 @@ int main( int argc, char *argv[] )
/* Create initial task */ /* Create initial task */
if ( !(pModule = NE_GetPtr( GetModuleHandle16( "KERNEL32" ) )) ) return 1; if ( !(pModule = NE_GetPtr( GetModuleHandle16( "KERNEL32" ) )) ) return 1;
hInstance = NE_CreateInstance( pModule, NULL, TRUE ); if ( !TASK_Create( THREAD_Current(), pModule, 0, 0, FALSE ) ) return 1;
PROCESS_Current()->task = TASK_Create( THREAD_Current(), pModule, hInstance, 0, FALSE );
/* Initialize CALL32 routines */ /* Initialize CALL32 routines */
/* This needs to be done just before switching stacks */ /* This needs to be done just before switching stacks */

View File

@ -14,7 +14,8 @@
#include "miscemu.h" #include "miscemu.h"
#include "msdos.h" #include "msdos.h"
#include "task.h" #include "task.h"
#include "thread.h" #include "thread.h" /* for !MZ_SUPPORTED */
#include "stackframe.h" /* for !MZ_SUPPORTED */
#include "toolhelp.h" #include "toolhelp.h"
#include "selectors.h" #include "selectors.h"
#include "process.h" #include "process.h"
@ -293,7 +294,7 @@ callrmproc_again:
if (!(CurrRMCB || pModule->lpDosTask)) { if (!(CurrRMCB || pModule->lpDosTask)) {
FIXME(int31,"DPMI real-mode call using DOS VM task system, not fully tested!\n"); FIXME(int31,"DPMI real-mode call using DOS VM task system, not fully tested!\n");
TRACE(int31,"creating VM86 task\n"); TRACE(int31,"creating VM86 task\n");
if (MZ_InitTask( MZ_AllocDPMITask( pModule->self ) ) < 32) { if (!MZ_InitTask( MZ_AllocDPMITask( pModule->self ) )) {
ERR(int31,"could not setup VM86 task\n"); ERR(int31,"could not setup VM86 task\n");
return 1; return 1;
} }