Alexandre Julliard : krnl386.exe: Propagate DOS startup errors up to winevdm.

Alexandre Julliard julliard at winehq.org
Thu Nov 11 12:05:52 CST 2010


Module: wine
Branch: master
Commit: 173957d294253112c55fd3202225859e0f6c65aa
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=173957d294253112c55fd3202225859e0f6c65aa

Author: Alexandre Julliard <julliard at winehq.org>
Date:   Thu Nov 11 18:01:05 2010 +0100

krnl386.exe: Propagate DOS startup errors up to winevdm.

---

 dlls/krnl386.exe16/dosexe.c |   37 +++++++++++++------------------------
 programs/winevdm/winevdm.c  |   36 ++++++++++++++++++++++++++----------
 2 files changed, 39 insertions(+), 34 deletions(-)

diff --git a/dlls/krnl386.exe16/dosexe.c b/dlls/krnl386.exe16/dosexe.c
index 55735f3..ff55326 100644
--- a/dlls/krnl386.exe16/dosexe.c
+++ b/dlls/krnl386.exe16/dosexe.c
@@ -114,7 +114,7 @@ static WORD init_cs,init_ip,init_ss,init_sp;
 static HANDLE dosvm_thread, loop_thread;
 static DWORD dosvm_tid, loop_tid;
 
-static void MZ_Launch( LPCSTR cmdtail, int length );
+static DWORD MZ_Launch( LPCSTR cmdtail, int length );
 static BOOL MZ_InitTask(void);
 
 static void MZ_CreatePSP( LPVOID lpPSP, WORD env, WORD par )
@@ -433,8 +433,12 @@ void __wine_load_dos_exe( LPCSTR filename, LPCSTR cmdline )
         }
     }
 
-    if (MZ_DoLoadImage( hFile, filename, NULL, 0 )) 
-        MZ_Launch( dos_cmdtail, dos_length );
+    if (MZ_DoLoadImage( hFile, filename, NULL, 0 ))
+    {
+        DWORD err = MZ_Launch( dos_cmdtail, dos_length );
+        /* if we get back here it failed */
+        SetLastError( err );
+    }
 }
 
 /***********************************************************************
@@ -633,24 +637,9 @@ static DWORD WINAPI MZ_DOSVM( LPVOID lpExtra )
   context.EFlags = V86_FLAG | VIF_MASK;
   DOSVM_SetTimer(0x10000);
   ret = DOSVM_Enter( &context );
-  if (ret == -1)
-  {
-      /* fetch the app name from the environment */
-      PDB16 *psp = PTR_REAL_TO_LIN( DOSVM_psp, 0 );
-      char *env = PTR_REAL_TO_LIN( psp->environment, 0 );
-      while (*env) env += strlen(env) + 1;
-      env += 1 + sizeof(WORD);
-
-      if (GetLastError() == ERROR_NOT_SUPPORTED)
-          MESSAGE( "wine: Cannot start DOS application %s\n"
-                   "      because vm86 mode is not supported on this platform.\n"
-                   "      Try running the application with DOSBox.\n",
-                   debugstr_a(env) );
-      else
-          FIXME( "vm86 mode failed error %u\n", GetLastError() );
-  }
+  if (ret == -1) ret = GetLastError();
   dosvm_pid = 0;
-  return ret != 0;
+  return ret;
 }
 
 static BOOL MZ_InitTask(void)
@@ -669,7 +658,7 @@ static BOOL MZ_InitTask(void)
   return TRUE;
 }
 
-static void MZ_Launch( LPCSTR cmdtail, int length )
+static DWORD MZ_Launch( LPCSTR cmdtail, int length )
 {
   TDB *pTask = GlobalLock16( GetCurrentTask() );
   BYTE *psp_start = PTR_REAL_TO_LIN( DOSVM_psp, 0 );
@@ -696,9 +685,10 @@ static void MZ_Launch( LPCSTR cmdtail, int length )
   dosvm_thread = 0; dosvm_tid = 0;
   CloseHandle(loop_thread);
   loop_thread = 0; loop_tid = 0;
+  if (rv) return rv;
 
   VGA_Clean();
-  ExitProcess(rv);
+  ExitProcess(0);
 }
 
 /***********************************************************************
@@ -756,8 +746,7 @@ BOOL MZ_Current( void )
  */
 void __wine_load_dos_exe( LPCSTR filename, LPCSTR cmdline )
 {
-    FIXME("DOS executables not supported on this platform\n");
-    SetLastError(ERROR_BAD_FORMAT);
+    SetLastError( ERROR_NOT_SUPPORTED );
 }
 
 /***********************************************************************
diff --git a/programs/winevdm/winevdm.c b/programs/winevdm/winevdm.c
index 92ca508..65f4bf2 100644
--- a/programs/winevdm/winevdm.c
+++ b/programs/winevdm/winevdm.c
@@ -102,6 +102,30 @@ typedef struct {
 #include "poppack.h"
 
 /***********************************************************************
+ *           start_dos_exe
+ */
+static void start_dos_exe( LPCSTR filename, LPCSTR cmdline )
+{
+    MEMORY_BASIC_INFORMATION mem_info;
+    const char *reason;
+
+    if (VirtualQuery( NULL, &mem_info, sizeof(mem_info) ) && mem_info.State != MEM_FREE)
+    {
+        __wine_load_dos_exe( filename, cmdline );
+        if (GetLastError() == ERROR_NOT_SUPPORTED)
+            reason = "because vm86 mode is not supported on this platform";
+        else
+            reason = wine_dbg_sprintf( "It failed with error code %u", GetLastError() );
+    }
+    else reason = "because the DOS memory range is unavailable";
+
+    WINE_MESSAGE( "winevdm: Cannot start DOS application %s\n", filename );
+    WINE_MESSAGE( "         %s.\n", reason );
+    WINE_MESSAGE( "         Try running this application with DOSBox.\n" );
+    ExitProcess(1);
+}
+
+/***********************************************************************
  *           read_pif_file
  *pif386rec_tu
  * Read a pif file and return the header and possibly the 286 (real mode)
@@ -244,8 +268,7 @@ static VOID pif_cmd( char *filename, char *cmdline)
      * - hot key's
      * - etc.
      */ 
-    __wine_load_dos_exe( progpath, cmdline );
-    return;
+    start_dos_exe( progpath, cmdline );
 }
 
 /***********************************************************************
@@ -382,7 +405,6 @@ int main( int argc, char *argv[] )
     STARTUPINFOA info;
     char *cmdline, *appname, **first_arg;
     char *p;
-    MEMORY_BASIC_INFORMATION mem_info;
 
     if (!argv[1]) usage();
 
@@ -439,15 +461,9 @@ int main( int argc, char *argv[] )
                 pif_cmd( appname, cmdline + 1);
             else
             {
-                if (!VirtualQuery( NULL, &mem_info, sizeof(mem_info) ) || mem_info.State == MEM_FREE)
-                {
-                    WINE_MESSAGE( "winevdm: unable to exec '%s': DOS memory range unavailable\n", appname );
-                    ExitProcess(1);
-                }
-
                 /* try DOS format */
                 /* loader expects arguments to be regular C strings */
-                __wine_load_dos_exe( appname, cmdline + 1 );
+                start_dos_exe( appname, cmdline + 1 );
             }
             /* if we get back here it failed */
             instance = GetLastError();




More information about the wine-cvs mailing list