Release 940607

Tue Jun  7 08:41:27 1994  Bob Amstadt  (bob@pooh)

	* loader/selector.c (FixupFunctionPrologs): 
	New function to fixup loaded DLL function prologs.  It replaces the
	do nothing code with code that loads DS with the appropriate data
	segment for the DLL.

	* misc/cursor.c (LoadCursor): 
	Disabled cursor loading from .EXE or .DLL.  The code needs to handle
	the possibility of multiple cursors in a single directory.  Also,
	it should check to see if the cursor is the right size.

	* objects/font.c (EnumFonts): 
	Checked for lpLogFontList[i] == NULL

	* objects/gdiobj.c (SetObjectOwner): 
	Removed stub.  Replaced with simple return in gdi.spec.  This
	function is not defined for the retail version of Windows.

	* memory/heap.c (WIN16_LocalHandleDelta): 
	New function.  This is really a dummy that imitates the proper
	return values.

	* loader/library.c (GetProcAddress): 
	Fixed definition of IS_BUILTIN_DLL() macro.

Mon Jun  6 18:15:40 1994  Bob Amstadt  (bob@pooh)

	* miscemu/int21.c (SeekFile): 
	Needed to return current position in DX:AX.

	* windows/utility.c (windows_wsprintf): 
	Added support for '#' in format, and fixed bug with "ptr" being
	incremented too many times.

	* miscemu/int21.c (OpenExistingFile): 
	Add code to handle opening files read-only and write-only.

	* loader/wine.c:
	Segment fixups now done in LoadImage instead of _WinMain.  This
	is necessary to support LoadLibrary().

Sun Jun  5 17:34:24 1994  Erik Bos (erik@hacktic.nl)

	* [loader/*]
		- fixed: GetModuleHandle() sometimes returned
		  a wrong handle.
		- don't init dlls when cs == 0 (lzexpand, doesn't
		  seem to have a init function)
		- LoadLibrary & LoadImage now return error instead
		  of stopping wine.
		- moved most of NE-functions into one file.
		- LoadLibrary() uses w_files list instead of its
		  own list.
		- NE exectables are now fixed-up and initialised when
		  loaded instead of only once before calling InitTask.

	* [miscemu/int15.c] [miscemu/int31.c]
	Added.	

	* [loader/selector.c]
	Stubs added for {Get|Set}SelectorLimit(), {Get|Set}SelectorBase().

	* [misc/main.c]
	Stub added for IsRomModule().

	* [miscemu/int21.c]
	Some cleanup, added heap for returning data.

Jun 6, 94 martin2@trgcorp.solucorp.qc.ca (Martin Ayotte)

	* [tools/build.c]
	Change MAX_ORDINALS	define to higher value, 1299 entries.
	(MMSYSTEM doesn't have succesive numbers, some are around 1200).

	* [windows/utility.c]
	Bug fix in windows_wsprintf(), (twice increments ...).

	* [windows/winpos.c]
	Bug fix in SetWindowPos(), redraw was done if flag
		was set to SWP_NOREDRAW while SWP_SHOWWINDOW).

	* [misc/message.c] [controls/combo.c]
	Add an InvalidateRect() in WM_SHOWWINDOW to statisfy the new 'saveunder'.

	* [windows/win.c]
	In CreateWindowEx(), do SetMenu() calls after window creation,
		just before sending to WM_NCCALCSIZE.

	* [controls/menu.c]
	In function SetMenu(), now use SetWindowPos() with 
		flags SWP_FRAMECHANGED to readjust menu area.
	Function MenuBarCalcSize() redone.

Sun May 29 11:08:24 1994  David B. Thomas  (dt@yenta.abq.nm.us)

        * [objects/text.c]
        Fixed problems associated with DT_WORDBREAK flag.  String length
        was not being properly decremented when lines were folded, and
        wrapping was not performed when DT_NOCLIP and DT_NOPREFIX were
        both on in addition to DT_WORDBREAK.  Windows does wrapping in
        this case, and now so does wine.

Sun Jun  5 19:17:49 1994  Olaf Flebbe  (olaf@dragon)

        * [edit.c]
        cp1 was uninitialized iff lineno == 0

        *  FindFile tests for existance of file even if a full
           filename was supplied. What about unix file names?

        * [controls/listbox ]
        wndPtr was uninitialized for LB_SETTOPINDEX

        * [misc/property.c]     
        Do not free lpProp. Is it really allocated by malloc?
	{edited by Bob Amstadt: changed free() to GlobalFree()}
diff --git a/BUGS b/BUGS
index 3d53722..f006749 100644
--- a/BUGS
+++ b/BUGS
@@ -3,3 +3,4 @@
 - RegisterClass() with hbrBackground = COLOR_APPWORKSPACE+1 does not work.
 - MDI does not send WM_GETMINMAX message.
 - InitializeLoadedDLLs() can't init LZEXPAND.DLL. (cs:ip => 0:0)
+- LoadCursor does not correctly handle bitmap cursors
diff --git a/ChangeLog b/ChangeLog
index 5b0424f..407674d 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,124 @@
+Tue Jun  7 08:41:27 1994  Bob Amstadt  (bob@pooh)
+
+	* loader/selector.c (FixupFunctionPrologs): 
+	New function to fixup loaded DLL function prologs.  It replaces the
+	do nothing code with code that loads DS with the appropriate data
+	segment for the DLL.
+
+	* misc/cursor.c (LoadCursor): 
+	Disabled cursor loading from .EXE or .DLL.  The code needs to handle
+	the possibility of multiple cursors in a single directory.  Also,
+	it should check to see if the cursor is the right size.
+
+	* objects/font.c (EnumFonts): 
+	Checked for lpLogFontList[i] == NULL
+
+	* objects/gdiobj.c (SetObjectOwner): 
+	Removed stub.  Replaced with simple return in gdi.spec.  This
+	function is not defined for the retail version of Windows.
+
+	* memory/heap.c (WIN16_LocalHandleDelta): 
+	New function.  This is really a dummy that imitates the proper
+	return values.
+
+	* loader/library.c (GetProcAddress): 
+	Fixed definition of IS_BUILTIN_DLL() macro.
+
+Mon Jun  6 18:15:40 1994  Bob Amstadt  (bob@pooh)
+
+	* miscemu/int21.c (SeekFile): 
+	Needed to return current position in DX:AX.
+
+	* windows/utility.c (windows_wsprintf): 
+	Added support for '#' in format, and fixed bug with "ptr" being
+	incremented too many times.
+
+	* miscemu/int21.c (OpenExistingFile): 
+	Add code to handle opening files read-only and write-only.
+
+	* loader/wine.c:
+	Segment fixups now done in LoadImage instead of _WinMain.  This
+	is necessary to support LoadLibrary().
+
+Sun Jun  5 17:34:24 1994  Erik Bos (erik@hacktic.nl)
+
+	* [loader/*]
+		- fixed: GetModuleHandle() sometimes returned
+		  a wrong handle.
+		- don't init dlls when cs == 0 (lzexpand, doesn't
+		  seem to have a init function)
+		- LoadLibrary & LoadImage now return error instead
+		  of stopping wine.
+		- moved most of NE-functions into one file.
+		- LoadLibrary() uses w_files list instead of its
+		  own list.
+		- NE exectables are now fixed-up and initialised when
+		  loaded instead of only once before calling InitTask.
+
+	* [miscemu/int15.c] [miscemu/int31.c]
+	Added.	
+
+	* [loader/selector.c]
+	Stubs added for {Get|Set}SelectorLimit(), {Get|Set}SelectorBase().
+
+	* [misc/main.c]
+	Stub added for IsRomModule().
+
+	* [miscemu/int21.c]
+	Some cleanup, added heap for returning data.
+
+Jun 6, 94 martin2@trgcorp.solucorp.qc.ca (Martin Ayotte)
+
+	* [tools/.c]
+	Change MAX_ORDINALS	define to higher value, 1299 entries.
+	(MMSYSTEM doesn't have succesive numbers, some are around 1200).
+
+	* [windows/utility.c]
+	Bug fix in windows_wsprintf(), (twice increments ...).
+
+	* [windows/winpos.c]
+	Bug fix in SetWindowPos(), redraw was done if flag
+		was set to SWP_NOREDRAW while SWP_SHOWWINDOW).
+
+	* [misc/message.c] [controls/combo.c]
+	Add an InvalidateRect() in WM_SHOWWINDOW to statisfy the new 'saveunder'.
+
+	* [windows/winpos.c]
+	Bug fix in SetWindowPos(), (redraw was done if SWP_NOREDRAW set).
+
+	* [windows/win.c]
+	In CreateWindowEx(), do SetMenu() calls after window creation,
+		just before sending to WM_NCCALCSIZE.
+
+	* [controls/menu.c]
+	In function SetMenu(), now use SetWindowPos() with 
+		flags SWP_FRAMECHANGED to readjust menu area.
+	Function MenuBarCalcSize() redone.
+
+Sun May 29 11:08:24 1994  David B. Thomas  (dt@yenta.abq.nm.us)
+
+        * [objects/text.c]
+        Fixed problems associated with DT_WORDBREAK flag.  String length
+        was not being properly decremented when lines were folded, and
+        wrapping was not performed when DT_NOCLIP and DT_NOPREFIX were
+        both on in addition to DT_WORDBREAK.  Windows does wrapping in
+        this case, and now so does wine.
+
+Sun Jun  5 19:17:49 1994  Olaf Flebbe  (olaf@dragon)
+
+        * [edit.c]
+        cp1 was uninitialized iff lineno == 0
+
+        *  FindFile tests for existance of file even if a full
+           filename was supplied. What about unix file names?
+
+        * [controls/listbox ]
+        wndPtr was uninitialized for LB_SETTOPINDEX
+
+        * [misc/property.c]     
+        Do not free lpProp. Is it really allocated by malloc?
+	{edited by Bob Amstadt: changed free() to GlobalFree()}
+
 ----------------------------------------------------------------------
 Sat May 28 12:03:23 1994  Bob Amstadt  (bob@pooh)
 
diff --git a/controls/edit.c b/controls/edit.c
index 7ff105f..8d43172 100644
--- a/controls/edit.c
+++ b/controls/edit.c
@@ -2084,6 +2084,7 @@
     unsigned int *textPtrs = (unsigned int *)EDIT_HEAP_ADDR(es->hTextPtrs);
 
     if (off > strlen(text)) off = strlen(text);
+    cp1 = text;
     for (lineno = 0; lineno < es->wlines; lineno++)
     {
 	cp = text + *(textPtrs + lineno);
diff --git a/controls/listbox.c b/controls/listbox.c
index d18e785..522131a 100644
--- a/controls/listbox.c
+++ b/controls/listbox.c
@@ -462,8 +462,9 @@
 		printf("ListBox LB_SETTOPINDEX wParam=%x !\n", wParam);
 		lphl = ListBoxGetStorageHeader(hwnd);
 		lphl->FirstVisible = wParam;
+		wndPtr = WIN_FindWndPtr(hwnd);
 		if (wndPtr->dwStyle & WS_VSCROLL)
-		SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
+		    SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
 		InvalidateRect(hwnd, NULL, TRUE);
 		UpdateWindow(hwnd);
 		break;
diff --git a/controls/menu.c b/controls/menu.c
index dd9c880..6470497 100644
--- a/controls/menu.c
+++ b/controls/menu.c
@@ -103,7 +103,6 @@
 #endif
 		lppop = PopupMenuGetWindowAndStorage(hwnd, &wndPtr);
 		if (lppop == NULL) break;
-/*		if (!lppop->BarFlag)  ShowWindow(hwnd, SW_HIDE); */
 		if (lppop->SysFlag) {
 			MenuHasFocus = FALSE;
 			if (wParam == SC_ABOUTWINE) {
@@ -112,12 +111,12 @@
 				DialogBox(hSysRes, MAKEINTRESOURCE(2), 
 					GetParent(hwnd), (FARPROC)AboutWine_Proc);
 				}
-			else
+			else {
 #ifdef DEBUG_MENU
 				printf("PopupMenuWndProc // push to Owner WM_SYSCOMMAND !\n");
 #endif
 				PostMessage(lppop->ownerWnd, WM_SYSCOMMAND, wParam, lParam);
-/*				PostMessage(lppop->hWndParent, WM_SYSCOMMAND, wParam, lParam); */
+				}
 			break;
 			}
 #ifdef DEBUG_MENU
@@ -125,7 +124,6 @@
 #endif
 		MenuHasFocus = FALSE;
 		PostMessage(lppop->hWndParent, WM_COMMAND, wParam, lParam);
-/*		PostMessage(lppop->ownerWnd, WM_COMMAND, wParam, lParam); */
 		break;
 	case WM_SHOWWINDOW:
 #ifdef DEBUG_MENU
@@ -152,7 +150,7 @@
 									hwnd, lppop->Width, lppop->Height);
 #endif
 			SetWindowPos(hwnd, 0, 0, 0, lppop->Width + 2, lppop->Height, 
-											SWP_NOZORDER | SWP_NOMOVE);
+									SWP_NOZORDER | SWP_NOMOVE);
 #ifdef DEBUG_MENU
 			printf("PopupMenuWndProc // End of WM_SHOWWINDOW !\n");
 #endif
@@ -414,11 +412,23 @@
 											hWnd, x, y, wRet, lpitem);
 #endif
 	if (lpitem != NULL) {
+		if (lppop->FocusedItem != (WORD)-1 && wRet == lppop->FocusedItem) {
+			lpitem2 = GetMenuItemPtr(lppop, lppop->FocusedItem);
+			if ((lpitem2->item_flags & MF_POPUP) == MF_POPUP) {
+				hSubMenu = (HMENU)lpitem2->item_id;
+				lppop2 = (LPPOPUPMENU) GlobalLock(hSubMenu);
+				if (lppop2 == NULL) return FALSE;
+				if (IsWindowVisible(lppop2->hWnd)) {
+					ShowWindow(lppop2->hWnd, SW_HIDE);
+					return TRUE;
+					}
+				}
+			}
 		MenuItemSelect(hWnd, lppop, wRet);
 		if ((lpitem->item_flags & MF_POPUP) == MF_POPUP) {
 			hSubMenu = (HMENU)lpitem->item_id;
 			lppop2 = (LPPOPUPMENU) GlobalLock(hSubMenu);
-			if (lppop2 == NULL) return;
+			if (lppop2 == NULL) return FALSE;
 			lppop2->hWndParent = hWnd;
 			if (lppop->BarFlag) {
 				GetWindowRect(hWnd, &rect);
@@ -456,6 +466,7 @@
 		return TRUE;
 		}
 	printf("MenuButtonDown // x=%d y=%d // Not Found !\n", x, y);
+	if (GetCapture() != 0) ReleaseCapture(); 
 	MenuHasFocus = FALSE;
 	ShowWindow(lppop->hWnd, SW_HIDE);
 	return FALSE;
@@ -557,11 +568,14 @@
 {
 	LPMENUITEM lpitem;
 	int		i;
+#ifdef DEBUG_MENU
+	printf("ResetHiliteFlags lppop=%08X\n", lppop);
+#endif
 	if (lppop == NULL) return;
 	lpitem = lppop->firstItem;
 	for(i = 0; i < lppop->nItems; i++) {
 		if (lpitem == NULL) return;
-		lpitem->item_flags &= MF_HILITE ^ 0xFFFF;
+		lpitem->item_flags &= 0xFFFF ^ MF_HILITE;
 		lpitem = (LPMENUITEM)lpitem->next;
 		}
 }
@@ -1042,12 +1056,15 @@
 void MenuBarCalcSize(HDC hDC, LPRECT lprect, LPPOPUPMENU lppop)
 {
 	LPMENUITEM 	lpitem;
+	LPMENUITEM 	lpitem2;
 	RECT 	rect;
 	HBITMAP	hBitMap;
 	BITMAP	bm;
 	HFONT	hOldFont;
-	UINT  	i, OldHeight;
+	UINT  	i, j;
+	UINT	OldHeight, LineHeight;
 	DWORD	dwRet;
+	if (lprect == NULL) return;
 	if (lppop == NULL) return;
 	if (lppop->nItems == 0) return;
 	InitStdBitmaps();
@@ -1056,39 +1073,47 @@
 		lprect->left, lprect->top, lprect->right, lprect->bottom);
 #endif
 	hOldFont = SelectObject(hDC, GetStockObject(SYSTEM_FONT));
-	lppop->Height = lprect->bottom - lprect->top;
-CalcAGAIN:
-	OldHeight = lppop->Height;
-	SetRect(&rect, lprect->left, lprect->top, 0, lprect->top + OldHeight);
-	lpitem = lppop->firstItem;
-	for(i = 0; i < lppop->nItems; i++) {
-		if (lpitem == NULL) break;
-		rect.bottom = lprect->top + lppop->Height;
-		if (rect.right > lprect->right) 
-			SetRect(&rect, lprect->left, rect.bottom, 
-				0, rect.bottom + SYSMETRICS_CYMENU);
-		if ((lpitem->item_flags & MF_BITMAP) == MF_BITMAP) {
-			hBitMap = (HBITMAP)LOWORD((LONG)lpitem->item_text);
-			GetObject(hBitMap, sizeof(BITMAP), (LPSTR)&bm);
-			rect.right = rect.left + bm.bmWidth;
-			lppop->Height = max(lppop->Height, bm.bmHeight);
+	LineHeight = OldHeight = SYSMETRICS_CYMENU + 1;
+	SetRect(&rect, lprect->left, lprect->top, 0, lprect->top + LineHeight);
+	lpitem2 = lppop->firstItem;
+	while (lpitem != NULL) {
+		lpitem = lpitem2;
+		while(rect.right < lprect->right) {
+			if (lpitem == NULL) break;
+			if ((lpitem->item_flags & MF_BITMAP) == MF_BITMAP) {
+				hBitMap = (HBITMAP)LOWORD((LONG)lpitem->item_text);
+				GetObject(hBitMap, sizeof(BITMAP), (LPSTR)&bm);
+				rect.right = rect.left + bm.bmWidth;
+				LineHeight = max(LineHeight, bm.bmHeight);
+				}
+			if (((lpitem->item_flags & MF_BITMAP) != MF_BITMAP) &&
+				((lpitem->item_flags & MF_SEPARATOR) != MF_SEPARATOR) &&
+				((lpitem->item_flags & MF_MENUBREAK) != MF_MENUBREAK)) {
+				dwRet = GetTextExtent(hDC, (char *)lpitem->item_text, 
+				strlen((char *)lpitem->item_text));
+				rect.right = rect.left + LOWORD(dwRet) + 10;
+				dwRet = max(SYSMETRICS_CYMENU, (HIWORD(dwRet) + 6));
+				LineHeight = max(LineHeight, (WORD)dwRet);
+				}
+			CopyRect(&lpitem->rect, &rect);
+			rect.left = rect.right;
+			lpitem = (LPMENUITEM)lpitem->next;
 			}
-		if (((lpitem->item_flags & MF_BITMAP) != MF_BITMAP) &&
-			((lpitem->item_flags & MF_SEPARATOR) != MF_SEPARATOR) &&
-			((lpitem->item_flags & MF_MENUBREAK) != MF_MENUBREAK)) {
-			dwRet = GetTextExtent(hDC, (char *)lpitem->item_text, 
-			strlen((char *)lpitem->item_text));
-			rect.right = rect.left + LOWORD(dwRet) + 10;
-			dwRet = max(SYSMETRICS_CYMENU, (HIWORD(dwRet) + 6));
-			lppop->Height = max(lppop->Height, (WORD)dwRet);
+		if (LineHeight == OldHeight) {
+			lpitem2 = lpitem;
+			LineHeight = OldHeight = SYSMETRICS_CYMENU + 1;
+			if (lpitem != NULL) 
+				SetRect(&rect, lprect->left, rect.bottom, 
+						0, rect.bottom + LineHeight);
 			}
-		CopyRect(&lpitem->rect, &rect);
-		rect.left = rect.right;
-		lpitem = (LPMENUITEM)lpitem->next;
+		else {
+			OldHeight = LineHeight;
+			SetRect(&rect, lprect->left, rect.top, 0, rect.top + LineHeight);
+			}
 		}
-	if (OldHeight < lppop->Height) goto CalcAGAIN;
-	lppop->Width = rect.right;
-	lprect->bottom =  lprect->top + lppop->Height;
+	lppop->Width = lprect->right - lprect->left;
+	lppop->Height =  rect.bottom - lprect->top;
+	lprect->bottom = lprect->top + lppop->Height;
 	CopyRect(&lppop->rect, lprect);
 #ifdef DEBUG_MENUCALC
 	printf("MenuBarCalcSize w=%d h=%d !\n", lppop->Width, lppop->Height);
@@ -2074,8 +2099,7 @@
 {
 	RECT	rect;
 	LPPOPUPMENU lpmenu;
-	NCCALCSIZE_PARAMS *params;
-	HANDLE hparams;
+	WORD	flags;
 	WND * wndPtr = WIN_FindWndPtr(hWnd);
 	if (wndPtr == NULL) {
 		printf("SetMenu(%04X, %04X) // Bad window handle !\n", hWnd, hMenu);
@@ -2085,20 +2109,17 @@
 	printf("SetMenu(%04X, %04X);\n", hWnd, hMenu);
 #endif
 	if (GetCapture() == hWnd) ReleaseCapture();
-	wndPtr->wIDmenu = hMenu;
-	if (hMenu == 0) {
-		printf("SetMenu(%04X, %04X) // Menu removed !\n", hWnd, hMenu);
-		hparams = USER_HEAP_ALLOC(GMEM_MOVEABLE, sizeof(NCCALCSIZE_PARAMS));
-		if (hparams) {
-			params = (NCCALCSIZE_PARAMS *) USER_HEAP_ADDR(hparams);
-			params->rgrc[0] = wndPtr->rectWindow;
-			params->lppos = NULL;
-			SendMessage(hWnd, WM_NCCALCSIZE, FALSE, (LONG)params);
-			wndPtr->rectClient = params->rgrc[0];
-			USER_HEAP_FREE(hparams);
-			}	
-		SendMessage(hWnd, WM_NCPAINT, 0, 0L);
-		return TRUE;
+	if (wndPtr->window != 0) {
+		flags = SWP_NOZORDER | SWP_NOMOVE | SWP_NOSIZE | SWP_FRAMECHANGED;
+		if (!IsWindowVisible(hWnd)) flags |= SWP_NOREDRAW;
+		if (hMenu == 0) {
+			wndPtr->wIDmenu = hMenu;
+			printf("SetMenu(%04X, %04X) // Menu removed, need NC recalc!\n", hWnd, hMenu);
+			SetWindowPos(hWnd, 0, 0, 0, 0, 0, flags);
+			return TRUE;
+			}
+		wndPtr->wIDmenu = hMenu;
+		SetWindowPos(hWnd, 0, 0, 0, 0, 0, flags);
 		}
 	lpmenu = (LPPOPUPMENU) GlobalLock(hMenu);
 	if (lpmenu == NULL) {
@@ -2222,9 +2243,9 @@
 	printf("CopySysMenu entry !\n");
 #endif
 	if (hSysMenu == 0) {
-		hSysMenu = LoadMenu((HINSTANCE)NULL, MAKEINTRESOURCE(1));
+/*		hSysMenu = LoadMenu((HINSTANCE)NULL, MAKEINTRESOURCE(1)); */
 /*		hSysMenu = LoadMenu((HINSTANCE)NULL, MAKEINTRESOURCE(SC_SYSMENU));*/
-/*		hSysMenu = LoadMenu((HINSTANCE)NULL, "SYSMENU"); */
+		hSysMenu = LoadMenu((HINSTANCE)NULL, "SYSMENU"); 
 		if (hSysMenu == 0) {
 			printf("SysMenu not found in system resources !\n");
 			return (HMENU)NULL;
diff --git a/debugger/hash.c b/debugger/hash.c
index a6d640f..97254af 100644
--- a/debugger/hash.c
+++ b/debugger/hash.c
@@ -13,6 +13,7 @@
 #include <segmem.h>
 #include <prototypes.h>
 #include <wine.h>
+#include <dlls.h>
 
 struct  name_hash{
 	struct name_hash * next;
diff --git a/if1632/callback.c b/if1632/callback.c
index a4bd586..676fc7e 100644
--- a/if1632/callback.c
+++ b/if1632/callback.c
@@ -8,7 +8,7 @@
 #include "wine.h"
 #include "segmem.h"
 #include <setjmp.h>
-
+#include "dlls.h"
 extern SEGDESC Segments[];
 extern unsigned short IF1632_Saved16_ss;
 extern unsigned long  IF1632_Saved16_ebp;
diff --git a/if1632/gdi.spec b/if1632/gdi.spec
index 7c7e1d4..b63e283 100644
--- a/if1632/gdi.spec
+++ b/if1632/gdi.spec
@@ -50,7 +50,7 @@
            StretchBlt(1 2 3 4 5 6 7 8 9 10 11)
 36  pascal Polygon (word ptr word) Polygon (1 2 3)
 37  pascal Polyline (word ptr word) Polyline (1 2 3)
-#38  pascal Escape
+38  pascal Escape(word word word ptr ptr) Escape(1 2 3 4 5)
 39  pascal RestoreDC(word s_word) RestoreDC(1 2)
 40  pascal FillRgn(word word word) FillRgn(1 2 3)
 #41  pascal FrameRgn
@@ -278,7 +278,7 @@
 	   CreatePolyPolygonRgn(1 2 3 4)
 #452 pascal GDISEEGDIDO
 #460 pascal GDITASKTERMINATION
-461 pascal SetObjectOwner(word) SetObjectOwner(1)
+461 return SetObjectOwner 4 0
 #462 pascal ISGDIOBJECT
 #463 pascal MAKEOBJECTPRIVATE
 #464 pascal FIXUPBOGUSPUBLISHERMETAFILE
diff --git a/if1632/kernel.spec b/if1632/kernel.spec
index dc3076e..5f0ed34 100644
--- a/if1632/kernel.spec
+++ b/if1632/kernel.spec
@@ -143,7 +143,8 @@
 135 pascal GetSystemDirectory(ptr word) GetSystemDirectory(1 2)
 136 pascal GetDriveType(byte) GetDriveType(1)
 137 pascal FatalAppExit(word ptr) FatalAppExit(1 2)
-#138 GETHEAPSPACES
+#138 GETHEAPSPACES - This is not correct but may fake out most apps
+138 return GetHeapSpaces 2 0x80004000
 #139 DOSIGNAL
 #140 SETSIGHANDLER
 #141 INITTASK1
@@ -182,10 +183,10 @@
 #183 __0000H
 184 return GlobalDOSAlloc 4 0
 185 return GlobalDOSFree 2 0
-#186 GETSELECTORBASE
-#187 SETSELECTORBASE
-#188 GETSELECTORLIMIT
-#189 SETSELECTORLIMIT
+186 pascal GetSelectorBase(word) GetSelectorBase(1)
+187 pascal SetSelectorBase(word long) SetSelectorBase(1 2)
+188 pascal GetSelectorLimit(word) GetSelectorLimit(1)
+189 pascal SetSelectorLimit(word long) SetSelectorLimit(1 2)
 #190 __E000H
 191 pascal GlobalPageLock(word) GlobalLock(1)
 192 pascal GlobalPageUnlock(word) GlobalUnlock(1)
@@ -204,7 +205,7 @@
 #205 CVWBREAK
 #206 ALLOCSELECTORARRAY
 207 return IsDBCSLeadByte 2 0
-#310 LOCALHANDLEDELTA
+310 pascal LocalHandleDelta(word) WIN16_LocalHandleDelta(1)
 #311 GETSETKERNELDOSPROC
 #314 DEBUGDEFINESEGMENT
 315 pascal WriteOutProfiles() sync_profiles()
@@ -212,7 +213,7 @@
 #318 FATALEXITHOOK
 #319 FLUSHCACHEDFILEHANDLE
 #320 ISTASK
-#323 ISROMMODULE
+323 pascal IsRomModule() IsRomModule()
 #324 LOGERROR
 #325 LOGPARAMERROR
 #326 ISROMFILE
diff --git a/if1632/mmsystem.spec b/if1632/mmsystem.spec
index 22bdf46..df33e6d 100644
--- a/if1632/mmsystem.spec
+++ b/if1632/mmsystem.spec
@@ -2,12 +2,25 @@
 #
 name	mmsystem
 id	11
-length 706
+length 1226
 
-1      pascal  LIBMAIN(word word word ptr) MCI_LibMain(1 2 3 4)
+1      pascal  MMSYSTEM_WEP(word word word ptr) MMSYSTEM_WEP(1 2 3 4)
 2      pascal  SNDPLAYSOUND(ptr word) sndPlaySound(1 2)
 5      pascal  MMSYSTEMGETVERSION() mmsystemGetVersion()
+6      pascal  DriverProc(long word word long long) DriverProc(1 2 3 4 5)
 30     pascal  OUTPUTDEBUGSTR(ptr) OutputDebugStr(1)
+31     pascal  DriverCallback(long word word word long long long) DriverCallback(1 2 3 4 5 6 7)
+#32    pascal  STACKENTER()
+#33    pascal  STACKLEAVE()
+#34    pascal  MMDRVINSTALL()
+101    pascal  JOYGETNUMDEVS() JoyGetNumDevs()
+102    pascal  JOYGETDEVCAPS(word ptr word) JoyGetDevCaps(1 2 3)
+103    pascal  JOYGETPOS(word ptr) JoyGetPos(1 2)
+104    pascal  JOYGETTHRESHOLD(word ptr) JoyGetThreshold(1 2)
+105    pascal  JOYRELEASECAPTURE(word) JoyReleaseCapture(1)
+106    pascal  JOYSETCAPTURE(word word word word) JoySetCapture(1 2 3 4)
+107    pascal  JOYSETTHRESHOLD(word word) JoySetThreshold(1 2)
+109    pascal  JOYSETCALIBRATION(word) JoySetCalibration(1)
 201    pascal  MIDIOUTGETNUMDEVS() midiOutGetNumDevs()
 202    pascal  MIDIOUTGETDEVCAPS(word ptr word) midiOutGetDevCaps(1 2 3)
 203    pascal  MIDIOUTGETERRORTEXT(word ptr word) midiOutGetErrorText(1 2 3)
@@ -73,27 +86,32 @@
 702    pascal  MCISENDSTRING(ptr ptr word word) mciSendString(1 2 3 4)
 703    pascal  MCIGETDEVICEID(ptr) mciSendCommand(1)
 706    pascal  MCIGETERRORSTRING(long ptr word) mciGetErrorString(1 2 3)
-#1100   pascal  DRVOPEN
-#1101   pascal  DRVCLOSE
-#1102   pascal  DRVSENDMESSAGE
-#1103   pascal  DRVGETMODULEHANDLE
-#1104   pascal  DRVDEFDRIVERPROC
-#1210   pascal  MMIOOPEN
-#1211   pascal  MMIOCLOSE
-#1212   pascal  MMIOREAD
-#1213   pascal  MMIOWRITE
-#1214   pascal  MMIOSEEK
-#1215   pascal  MMIOGETINFO
-#1216   pascal  MMIOSETINFO
-#1217   pascal  MMIOSETBUFFER
-#1218   pascal  MMIOFLUSH
-#1219   pascal  MMIOADVANCE
-#1220   pascal  MMIOSTRINGTOFOURCC
-#1221   pascal  MMIOINSTALLIOPROC
-#1222   pascal  MMIOSENDMESSAGE
-#1223   pascal  MMIODESCEND
-#1224   pascal  MMIOASCEND
-#1225   pascal  MMIOCREATECHUNK
-#1226   pascal  MMIORENAME
+#900   pascal  MMTASKCREATE()
+#902   pascal  MMTASKBLOCK()
+#903   pascal  MMTASKSIGNAL()
+#904   pascal  MMGETCURRENTTASK()
+#905   pascal  MMTASKYIELD()
+1100   pascal  DRVOPEN(ptr ptr long) DrvOpen(1 2 3)
+1101   pascal  DRVCLOSE(word long long) DrvClose(1 2 3)
+1102   pascal  DRVSENDMESSAGE(word word long long) DrvSendMessage(1 2 3 4)
+1103   pascal  DRVGETMODULEHANDLE(word) DrvGetModuleHandle(1)
+1104   pascal  DRVDEFDRIVERPROC(long word word long long) DrvDefDriverProc(1 2 3 4 5)
+1210   pascal  MMIOOPEN(ptr ptr long) mmioOpen(1 2 3)
+1211   pascal  MMIOCLOSE(word word) mmioClose(1 2)
+1212   pascal  MMIOREAD(word ptr long) mmioRead(1 2 3)
+1213   pascal  MMIOWRITE(word ptr long) mmioWrite(1 2 3)
+1214   pascal  MMIOSEEK(word long word) mmioSeek(1 2 3)
+1215   pascal  MMIOGETINFO(word ptr word) mmioGetInfo(1 2 3)
+1216   pascal  MMIOSETINFO(word ptr word) mmioSetInfo(1 2 3)
+1217   pascal  MMIOSETBUFFER(word ptr long word) mmioSetBuffer(1 2 3 4)
+1218   pascal  MMIOFLUSH(word word) mmioFlush(1 2)
+1219   pascal  MMIOADVANCE(word ptr word) mmioAdvance(1 2 3)
+1220   pascal  MMIOSTRINGTOFOURCC(ptr word) mmioStringToFOURCC(1 2)
+1221   pascal  MMIOINSTALLIOPROC(long ptr long) mmioInstallIOProc(1 2 3)
+1222   pascal  MMIOSENDMESSAGE(word word long long) mmioSendMessage(1 2 3 4)
+1223   pascal  MMIODESCEND(word ptr ptr word) mmioDescend(1 2 3 4)
+1224   pascal  MMIOASCEND(word ptr word) mmioAscend(1 2 3)
+1225   pascal  MMIOCREATECHUNK(word ptr word) mmioCreateChunk(1 2 3)
+1226   pascal  MMIORENAME(ptr ptr ptr long) mmioRename(1 2 3 4)
 
 
diff --git a/if1632/relay.c b/if1632/relay.c
index ddbf8c9..752fc37 100644
--- a/if1632/relay.c
+++ b/if1632/relay.c
@@ -36,7 +36,7 @@
     { "KEYBOARD",KEYBOARD_table,137, 8 },
     { "WINSOCK", WINSOCK_table, 155, 9 },
     { "STRESS",  STRESS_table,   15, 10},
-    { "MMSYSTEM",MMSYSTEM_table,1023,11},
+    { "MMSYSTEM",MMSYSTEM_table,1226,11},
     { "SYSTEM",  SYSTEM_table,   20 ,12},
     { "TOOLHELP",TOOLHELP_table, 83, 13},
 };
diff --git a/include/dlls.h b/include/dlls.h
index 574db1e..9796955 100644
--- a/include/dlls.h
+++ b/include/dlls.h
@@ -7,6 +7,35 @@
 #ifndef DLLS_H
 #define DLLS_H
 
+#define MAX_NAME_LENGTH		64
+
+typedef struct resource_name_table
+{
+    struct resource_name_table *next;
+    unsigned short type_ord;
+    unsigned short id_ord;
+    char id[MAX_NAME_LENGTH];
+} RESNAMTAB;
+
+struct w_files
+{
+    struct w_files  * next;
+    char * name;   /* Name, as it appears in the windows binaries */
+    char * filename; /* Actual name of the unix file that satisfies this */
+    int fd;
+    struct mz_header_s *mz_header;
+    struct ne_header_s *ne_header;
+    struct ne_segment_table_entry_s *seg_table;
+    struct segment_descriptor_s *selector_table;
+    char * lookup_table;
+    char * nrname_table;
+    char * rname_table;
+    unsigned short hinstance;
+    RESNAMTAB *resnamtab;
+};
+
+extern struct  w_files *wine_files;
+
 typedef struct dll_arg_relocation_s
 {
     unsigned short dst_arg;	/* Offset to argument on stack		*/
diff --git a/include/heap.h b/include/heap.h
index 22fe129..7c389f1 100644
--- a/include/heap.h
+++ b/include/heap.h
@@ -27,6 +27,7 @@
     MDESC *free_list;
     ATOMTABLE *local_table;
     unsigned short selector;
+    unsigned short delta;		/* Number saved for Windows compat. */
 } LHEAP;
 
 extern void HEAP_Init(MDESC **free_list, void *start, int length);
diff --git a/include/prototypes.h b/include/prototypes.h
index a264ed5..cbeee0b 100644
--- a/include/prototypes.h
+++ b/include/prototypes.h
@@ -66,9 +66,6 @@
 					int *addr);
 extern unsigned int GetEntryDLLOrdinal(char *dll_name, int ordinal, int *sel,
 					int *addr);
-extern unsigned int GetEntryPointFromOrdinal(struct w_files * wpnt,
-					int ordinal);
-extern SEGDESC *CreateSelectors(struct  w_files * wpnt);
 
 /* loader/signal.c */
 
@@ -81,16 +78,9 @@
 extern void load_ne_header (int, struct ne_header_s *);
 
 extern char *GetFilenameFromInstance(unsigned short instance);
-extern struct w_files *GetFileInfo(unsigned short instance);
 extern HINSTANCE LoadImage(char *modulename, int filetype, int change_dir);
 extern int _WinMain(int argc, char **argv);
 extern void InitializeLoadedDLLs();
-extern int FixupSegment(struct w_files * wpnt, int segment_num);
-/*
-extern struct mz_header_s *CurrentMZHeader;
-extern struct ne_header_s *CurrentNEHeader;
-extern int CurrentNEFile;
-*/
 
 /* if1632/relay.c */
 
diff --git a/include/toolhelp.h b/include/toolhelp.h
new file mode 100644
index 0000000..6941d1b
--- /dev/null
+++ b/include/toolhelp.h
@@ -0,0 +1,26 @@
+#ifndef __TOOLHELP_H
+#define __TOOLHELP_H
+
+#include "windows.h"
+
+DECLARE_HANDLE(HMODULE);
+
+#define MAX_MODULE_NAME 9
+#define MAX_PATH 255
+
+typedef struct {
+    DWORD dwSize;
+    char szModule[MAX_MODULE_NAME + 1];
+    HMODULE hModule;
+    WORD wcUsage;
+    char szExePath[MAX_PATH + 1];
+    WORD wNext;
+} MODULEENTRY;
+typedef MODULEENTRY *LPMODULEENTRY;
+
+BOOL	ModuleFirst(MODULEENTRY *lpModule);
+BOOL	ModuleNext(MODULEENTRY *lpModule);
+HMODULE ModuleFindName(MODULEENTRY *lpModule, LPCSTR lpstrName);
+HMODULE ModuleFindHandle(MODULEENTRY *lpModule, HMODULE hModule);
+
+#endif /* __TOOLHELP_H */
diff --git a/include/windows.h b/include/windows.h
index 96a29fe..e4ca0e2 100644
--- a/include/windows.h
+++ b/include/windows.h
@@ -11,22 +11,26 @@
 typedef unsigned long DWORD;
 typedef unsigned short BOOL;
 typedef unsigned char BYTE;
-typedef char *LPSTR;
-typedef const char *LPCSTR;
-typedef char *NPSTR;
-typedef INT *LPINT;
-typedef void *LPVOID;
-typedef long (*FARPROC)();
-typedef FARPROC DLGPROC;
-typedef int CATCHBUF[9];
-typedef int *LPCATCHBUF;
-typedef FARPROC HOOKPROC;
 typedef long LONG;
 typedef UINT WPARAM;
 typedef LONG LPARAM;
 typedef LONG LRESULT;
 typedef WORD HANDLE;
 typedef DWORD HHOOK;
+typedef char *LPSTR;
+typedef const char *LPCSTR;
+typedef char *NPSTR;
+typedef INT *LPINT;
+typedef UINT *LPUINT;
+typedef WORD *LPWORD;
+typedef DWORD *LPDWORD;
+typedef LONG *LPLONG;
+typedef void *LPVOID;
+typedef long (*FARPROC)();
+typedef FARPROC DLGPROC;
+typedef int CATCHBUF[9];
+typedef int *LPCATCHBUF;
+typedef FARPROC HOOKPROC;
 #define DECLARE_HANDLE(a) typedef HANDLE a;
 
 DECLARE_HANDLE(HTASK);
diff --git a/include/wine.h b/include/wine.h
index 92e0f9b..5160386 100644
--- a/include/wine.h
+++ b/include/wine.h
@@ -1,37 +1,6 @@
 #ifndef  WINE_H
 #define  WINE_H
 
-#include "dlls.h"
-
-#define MAX_NAME_LENGTH		64
-
-typedef struct resource_name_table
-{
-    struct resource_name_table *next;
-    unsigned short type_ord;
-    unsigned short id_ord;
-    char id[MAX_NAME_LENGTH];
-} RESNAMTAB;
-
-struct w_files
-{
-    struct w_files  * next;
-    char * name;   /* Name, as it appears in the windows binaries */
-    char * filename;  /* Actual name of the unix file that satisfies this */
-    int fd;
-    struct mz_header_s *mz_header;
-    struct ne_header_s *ne_header;
-    struct ne_segment_table_entry_s *seg_table;
-    struct segment_descriptor_s *selector_table;
-    char * lookup_table;
-    char * nrname_table;
-    char * rname_table;
-    unsigned short hinstance;
-    RESNAMTAB *resnamtab;
-};
-
-extern struct  w_files * wine_files;
-
 extern char *WineIniFileName(void);
 extern char *WinIniFileName(void);
 
diff --git a/loader/Imakefile b/loader/Imakefile
index 68297d2..b778667 100644
--- a/loader/Imakefile
+++ b/loader/Imakefile
@@ -6,12 +6,13 @@
 	dump.c \
 	ldt.c \
 	ldtlib.c \
+	main.c \
+	ne_image.c \
 	selector.c \
 	signal.c \
 	library.c \
 	resource.c \
-	task.c \
-	wine.c
+	task.c 
 
 OBJS = $(SRCS:.c=.o)
 
diff --git a/loader/library.c b/loader/library.c
index e99dd6e..02b74d2 100644
--- a/loader/library.c
+++ b/loader/library.c
@@ -21,23 +21,30 @@
 #include "dlls.h"
 #include "task.h"
 
-typedef struct {
-	LPSTR		ModuleName;
-	LPSTR		FileName;
-	WORD		Count;
-	HANDLE		hModule;
-	HINSTANCE	hInst;
-	void		*lpPrevModule;
-	void		*lpNextModule;
-} MODULEENTRY;
-typedef MODULEENTRY *LPMODULEENTRY;
-
-static LPMODULEENTRY lpModList = NULL;
-
-extern struct  w_files * wine_files;
+extern struct  w_files *wine_files;
 extern struct dll_name_table_entry_s dll_builtin_table[];
 
-#define IS_BUILTIN_DLL(handle) ((handle >> 16) == 0xff) 
+#define IS_BUILTIN_DLL(handle) ((handle >> 8) == 0xff) 
+
+/**********************************************************************/
+
+void ExtractDLLName(char *libname, char *temp)
+{
+    int i;
+    
+    strcpy(temp, libname);
+    if (strchr(temp, '\\') || strchr(temp, '/'))
+	for (i = strlen(temp) - 1; i ; i--) 
+		if (temp[i] == '\\' || temp[i] == '/') {
+			strcpy(temp, temp + i + 1);
+			break;
+		}
+    for (i = strlen(temp) - 1; i ; i--) 
+	if (temp[i] == '.') {
+		temp[i] = 0;
+		break;
+	}
+}
 
 /**********************************************************************
  *				GetModuleHandle	[KERNEL.47]
@@ -46,7 +53,28 @@
 {
 	register struct w_files *w = wine_files;
 	int 	i;
- 	printf("GetModuleHandle('%x');\n", lpModuleName);
+	if ((int) lpModuleName & 0xffff0000)
+	 	printf("GetModuleHandle('%s');\n", lpModuleName);
+	else
+	 	printf("GetModuleHandle('%x');\n", lpModuleName);
+
+ 	printf("GetModuleHandle // searching in builtin libraries\n");
+	for (i = 0; i < N_BUILTINS; i++) {
+		if (dll_builtin_table[i].dll_name == NULL) break;
+		if (((int) lpModuleName & 0xffff0000) == 0) {
+			if (0xFF00 + i == (int) lpModuleName) {
+				printf("GetModuleHandle('%s') return %04X \n",
+				       lpModuleName, 0xff00 + i);
+				return 0xFF00 + i;
+				}
+			}
+		else if (strcasecmp(dll_builtin_table[i].dll_name, lpModuleName) == 0) {
+			printf("GetModuleHandle('%x') return %04X \n", 
+							lpModuleName, 0xFF00 + i);
+			return (0xFF00 + i);
+			}
+		}
+
  	printf("GetModuleHandle // searching in loaded modules\n");
 	while (w) {
 /*		printf("GetModuleHandle // '%x' \n", w->name);  */
@@ -64,22 +92,6 @@
 			}
 		w = w->next;
 		}
- 	printf("GetModuleHandle // searching in builtin libraries\n");
-    for (i = 0; i < N_BUILTINS; i++) {
-		if (dll_builtin_table[i].dll_name == NULL) break;
-		if (((int) lpModuleName & 0xffff0000) == 0) {
-			if (0xFF00 + i == (int) lpModuleName) {
-				printf("GetModuleHandle('%s') return %04X \n",
-				       lpModuleName, w->hinstance);
-				return 0xFF + i;
-				}
-			}
-		else if (strcasecmp(dll_builtin_table[i].dll_name, lpModuleName) == 0) {
-			printf("GetModuleHandle('%x') return %04X \n", 
-							lpModuleName, 0xFF00 + i);
-			return (0xFF00 + i);
-			}
-		}
 	printf("GetModuleHandle('%x') not found !\n", lpModuleName);
 	return 0;
 }
@@ -91,7 +103,13 @@
 int GetModuleUsage(HANDLE hModule)
 {
 	struct w_files *w;
+
 	printf("GetModuleUsage(%04X);\n", hModule);
+
+	/* built-in dll ? */
+	if (IS_BUILTIN_DLL(hModule)) 
+		return 2;
+		
 	w = GetFileInfo(hModule);
 /*	return w->Usage; */
 	return 1;
@@ -138,79 +156,15 @@
  */
 HANDLE LoadLibrary(LPSTR libname)
 {
-    HANDLE hModule;
-    LPMODULEENTRY lpMod = lpModList;
-    LPMODULEENTRY lpNewMod;
-    int i;
-    char temp[64];
+	HANDLE h;
+	
+	if ((h = LoadImage(libname, DLL, 0)) < 32)
+		return h;
 
-    printf("LoadLibrary '%s'\n", libname);
-
-    /* extract dllname */
-    strcpy(temp, libname);
-    if (strchr(temp, '\\') || strchr(temp, '/'))
-	for (i = strlen(temp) - 1; i ; i--) 
-		if (temp[i] == '\\' || temp[i] == '/') {
-			strcpy(temp, temp + i + 1);
-			break;
-		}
-    for (i = strlen(temp) - 1; i ; i--) 
-	if (temp[i] == '.') {
-		temp[i] = 0;
-		break;
-	}
-    
-    if (FindDLLTable(temp))
-	{
-	printf("Library was a builtin - \n");
-	return GetModuleHandle(temp);
-	}
-
-    if (lpMod != NULL) 
-    {
-	while (TRUE) 
-	{
-	    if (strcmp(libname, lpMod->FileName) == 0) 
-	    {
-		lpMod->Count++;
-		printf("LoadLibrary // already loaded hInst=%04X\n", 
-		       lpMod->hInst);
-		return lpMod->hInst;
-	    }
-	    if (lpMod->lpNextModule == NULL) break;
-	    lpMod = lpMod->lpNextModule;
-	}
-    }
-
-    hModule = GlobalAlloc(GMEM_MOVEABLE, sizeof(MODULEENTRY));
-    lpNewMod = (LPMODULEENTRY) GlobalLock(hModule);	
-#ifdef DEBUG_LIBRARY
-    printf("LoadLibrary // creating new module entry %08X\n", lpNewMod);
-#endif
-    if (lpNewMod == NULL) 
-	return 0;
-    if (lpModList == NULL) 
-    {
-	lpModList = lpNewMod;
-	lpNewMod->lpPrevModule = NULL;
-    }
-    else 
-    {
-	lpMod->lpNextModule = lpNewMod;
-	lpNewMod->lpPrevModule = lpMod;
-    }
-
-    lpNewMod->lpNextModule = NULL;
-    lpNewMod->hModule = hModule;
-    lpNewMod->ModuleName = NULL;
-    lpNewMod->FileName = (LPSTR) malloc(strlen(libname));
-    if (lpNewMod->FileName != NULL)	
-	strcpy(lpNewMod->FileName, libname);
-    lpNewMod->hInst = LoadImage(libname, DLL, 0);
-    lpNewMod->Count = 1;
-    printf("LoadLibrary returned Library hInst=%04X\n", lpNewMod->hInst);
-    GlobalUnlock(hModule);	
-    return lpNewMod->hInst;
+	if (!IS_BUILTIN_DLL(h))
+		InitDLL(GetFileInfo(h));
+	
+	return h;
 }
 
 
@@ -219,14 +173,13 @@
  */
 void FreeLibrary(HANDLE hLib)
 {
-	LPMODULEENTRY lpMod = lpModList;
-
     printf("FreeLibrary(%04X);\n", hLib);
 
 	/* built-in dll ? */
 	if (IS_BUILTIN_DLL(hLib)) 
 	    	return;
 
+/*
 	while (lpMod != NULL) {
 		if (lpMod->hInst == hLib) {
 			if (lpMod->Count == 1) {
@@ -243,6 +196,7 @@
 			}
 		lpMod = lpMod->lpNextModule;
 		}
+*/
 }
 
 
diff --git a/loader/main.c b/loader/main.c
new file mode 100644
index 0000000..119d00f
--- /dev/null
+++ b/loader/main.c
@@ -0,0 +1,396 @@
+static char RCSId[] = "$Id: wine.c,v 1.2 1993/07/04 04:04:21 root Exp root $";
+static char Copyright[] = "Copyright  Robert J. Amstadt, 1993";
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <string.h>
+#include <errno.h>
+#ifdef linux
+#include <linux/unistd.h>
+#include <linux/head.h>
+#include <linux/ldt.h>
+#include <linux/segment.h>
+#endif
+#include "neexe.h"
+#include "segmem.h"
+#include "prototypes.h"
+#include "dlls.h"
+#include "wine.h"
+#include "windows.h"
+#include "wineopts.h"
+#include "arch.h"
+#include "options.h"
+
+/* #define DEBUG_FIXUP */
+
+extern HANDLE CreateNewTask(HINSTANCE hInst);
+extern int CallToInit16(unsigned long csip, unsigned long sssp, 
+			unsigned short ds);
+extern void CallTo32();
+
+char *GetDosFileName(char *unixfilename);
+char *GetModuleName(struct w_files * wpnt, int index, char *buffer);
+extern unsigned char ran_out;
+extern char WindowsPath[256];
+char *WIN_ProgramName;
+
+unsigned short WIN_StackSize;
+unsigned short WIN_HeapSize;
+
+struct  w_files * wine_files = NULL;
+
+char **Argv;
+int Argc;
+HINSTANCE hSysRes;
+
+static char *DLL_Extensions[] = { "dll", NULL };
+static char *EXE_Extensions[] = { "exe", NULL };
+
+/**********************************************************************
+ *					myerror
+ */
+void
+myerror(const char *s)
+{
+    if (s == NULL)
+	perror("wine");
+    else
+	fprintf(stderr, "wine: %s\n", s);
+
+    exit(1);
+}
+
+/**********************************************************************
+ *					GetFilenameFromInstance
+ */
+char *
+GetFilenameFromInstance(unsigned short instance)
+{
+    register struct w_files *w = wine_files;
+
+    while (w && w->hinstance != instance)
+	w = w->next;
+    
+    if (w)
+	return w->filename;
+    else
+	return NULL;
+}
+
+struct w_files *
+GetFileInfo(unsigned short instance)
+{
+    register struct w_files *w = wine_files;
+
+    while (w && w->hinstance != instance)
+	w = w->next;
+    
+    return w;
+}
+
+/**********************************************************************
+ *
+ * Load MZ Header
+ */
+void load_mz_header(int fd, struct mz_header_s *mz_header)
+{
+    if (read(fd, mz_header, sizeof(struct mz_header_s)) !=
+	sizeof(struct mz_header_s))
+    {
+	myerror("Unable to read MZ header from file");
+    }
+}
+
+int IsDLLLoaded(char *name)
+{
+	struct w_files *wpnt;
+
+	if(FindDLLTable(name))
+		return 1;
+
+	for(wpnt = wine_files; wpnt; wpnt = wpnt->next)
+		if(strcmp(wpnt->name, name) == 0)
+			return 1;
+
+	return 0;
+}
+
+/**********************************************************************
+ *			LoadImage
+ * Load one executable into memory
+ */
+HINSTANCE LoadImage(char *module, int filetype, int change_dir)
+{
+    unsigned int read_size;
+    int i;
+    struct w_files * wpnt, *wpnt1;
+    unsigned int status;
+    char buffer[256], header[2], modulename[64], *fullname;
+
+    ExtractDLLName(module, modulename);
+
+    /* built-in one ? */
+    if (FindDLLTable(modulename)) {
+	return GetModuleHandle(modulename);
+    }
+    
+    /* already loaded ? */
+    for (wpnt = wine_files ; wpnt ; wpnt = wpnt->next)
+    	if (strcasecmp(wpnt->name, modulename) == 0)
+    		return wpnt->hinstance;
+
+    /*
+     * search file
+     */
+    fullname = FindFile(buffer, sizeof(buffer), module, 
+			(filetype == EXE ? EXE_Extensions : DLL_Extensions), 
+			WindowsPath);
+    if (fullname == NULL)
+    {
+    	fprintf(stderr, "LoadImage: I can't find %s.dll | %s.exe !\n",
+		module, module);
+	return 2;
+    }
+
+    fullname = GetDosFileName(fullname);
+    WIN_ProgramName = strdup(fullname);
+    
+    fprintf(stderr,"LoadImage: loading %s (%s)\n           [%s]\n", 
+	    module, buffer, WIN_ProgramName);
+
+    if (change_dir && fullname)
+    {
+	char dirname[256];
+	char *p;
+
+	strcpy(dirname, fullname);
+	p = strrchr(dirname, '\\');
+	*p = '\0';
+
+	DOS_SetDefaultDrive(dirname[0] - 'A');
+	DOS_ChangeDir(dirname[0] - 'A', dirname + 2);
+    }
+
+    /* First allocate a spot to store the info we collect, and add it to
+     * our linked list.
+     */
+
+    wpnt = (struct w_files *) malloc(sizeof(struct w_files));
+    if(wine_files == NULL)
+      wine_files = wpnt;
+    else {
+      wpnt1 = wine_files;
+      while(wpnt1->next) wpnt1 =  wpnt1->next;
+      wpnt1->next  = wpnt;
+    };
+    wpnt->next = NULL;
+    wpnt->resnamtab = (RESNAMTAB *) -1;
+
+    /*
+     * Open file for reading.
+     */
+    wpnt->fd = open(buffer, O_RDONLY);
+    if (wpnt->fd < 0)
+	return 2;
+
+    /* 
+     * Establish header pointers.
+     */
+    wpnt->filename = strdup(buffer);
+    wpnt->name = strdup(modulename);
+
+/*    if(module) {
+    	wpnt->name = strdup(module);
+	ToDos(wpnt->name);
+    }*/
+
+    /* read mz header */
+    wpnt->mz_header = (struct mz_header_s *) malloc(sizeof(struct mz_header_s));;
+    status = lseek(wpnt->fd, 0, SEEK_SET);
+    load_mz_header (wpnt->fd, wpnt->mz_header);
+    if (wpnt->mz_header->must_be_0x40 != 0x40)
+	myerror("This is not a Windows program");
+
+    /* read first two bytes to determine filetype */
+    status = lseek(wpnt->fd, wpnt->mz_header->ne_offset, SEEK_SET);
+    read(wpnt->fd, &header, sizeof(header));
+
+    if (header[0] == 'N' && header[1] == 'E')
+	return (LoadNEImage(wpnt));
+
+    if (header[0] == 'P' && header[1] == 'E') {
+      printf("win32 applications are not supported");
+      return 14;
+    }
+
+    fprintf(stderr, "wine: (%s) unknown fileformat !\n", wpnt->filename);
+
+    return 14;
+}
+
+
+#ifndef WINELIB
+/**********************************************************************
+ *					main
+ */
+int _WinMain(int argc, char **argv)
+{
+	int segment;
+	char *p;
+	char *sysresname;
+	char filename[256];
+	HANDLE		hTaskMain;
+	HINSTANCE	hInstMain;
+#ifdef WINESTAT
+	char * cp;
+#endif
+	struct w_files * wpnt;
+	int cs_reg, ds_reg, ss_reg, ip_reg, sp_reg;
+	int rv;
+
+	Argc = argc - 1;
+	Argv = argv + 1;
+
+	if (strchr(Argv[0], '\\') || strchr(Argv[0],'/')) {
+            for (p = Argv[0] + strlen(Argv[0]); *p != '\\' && *p !='/'; p--)
+		/* NOTHING */;
+		
+	    strncpy(filename, Argv[0], p - Argv[0]);
+	    filename[p - Argv[0]] = '\0';
+	    strcat(WindowsPath, ";");
+	    strcat(WindowsPath, filename);
+	}
+	
+	if ((hInstMain = LoadImage(Argv[0], EXE, 1)) < 32) {
+		fprintf(stderr, "wine: can't load %s!.\n", Argv[0]);
+		exit(1);
+	}
+	hTaskMain = CreateNewTask(hInstMain);
+	printf("_WinMain // hTaskMain=%04X hInstMain=%04X !\n", hTaskMain, hInstMain);
+
+	GetPrivateProfileString("wine", "SystemResources", "sysres.dll", 
+				filename, sizeof(filename), WINE_INI);
+
+	hSysRes = LoadImage(filename, DLL, 0);
+	if (hSysRes < 32) {
+		fprintf(stderr, "wine: can't load %s!.\n", filename);
+		exit(1);
+	} else
+ 	    printf("System Resources Loaded // hSysRes='%04X'\n", hSysRes);
+	
+    /*
+     * Fixup references.
+     */
+/*    wpnt = wine_files;
+    for(wpnt = wine_files; wpnt; wpnt = wpnt->next)
+	for (segment = 0; segment < wpnt->ne_header->n_segment_tab; segment++)
+	    if (FixupSegment(wpnt, segment) < 0)
+		myerror("fixup failed.");
+*/
+
+#ifdef WINESTAT
+    cp = strrchr(argv[0], '/');
+    if(!cp) cp = argv[0];
+	else cp++;
+    if(strcmp(cp,"winestat") == 0) {
+	    winestat();
+	    exit(0);
+    };
+#endif
+
+    /*
+     * Initialize signal handling.
+     */
+    init_wine_signals();
+
+    /*
+     * Fixup stack and jump to start.
+     */
+    WIN_StackSize = wine_files->ne_header->stack_length;
+    WIN_HeapSize = wine_files->ne_header->local_heap_length;
+
+    ds_reg = (wine_files->
+	      selector_table[wine_files->ne_header->auto_data_seg-1].selector);
+    cs_reg = wine_files->selector_table[wine_files->ne_header->cs-1].selector;
+    ip_reg = wine_files->ne_header->ip;
+    ss_reg = wine_files->selector_table[wine_files->ne_header->ss-1].selector;
+    sp_reg = wine_files->ne_header->sp;
+
+    if (Options.debug) wine_debug(0, NULL);
+
+    rv = CallToInit16(cs_reg << 16 | ip_reg, ss_reg << 16 | sp_reg, ds_reg);
+    printf ("rv = %x\n", rv);
+}
+
+void InitDLL(struct w_files *wpnt)
+{
+	int cs_reg, ds_reg, ip_reg, rv;
+	/* 
+	 * Is this a library? 
+	 */
+	if (wpnt->ne_header->format_flags & 0x8000)
+	{
+	    if (!(wpnt->ne_header->format_flags & 0x0001))
+	    {
+		/* Not SINGLEDATA */
+		fprintf(stderr, "Library is not marked SINGLEDATA\n");
+		exit(1);
+	    }
+
+	    ds_reg = wpnt->selector_table[wpnt->
+					  ne_header->auto_data_seg-1].selector;
+	    cs_reg = wpnt->selector_table[wpnt->ne_header->cs-1].selector;
+	    ip_reg = wpnt->ne_header->ip;
+
+	    if (cs_reg) {
+		fprintf(stderr, "Initializing %s, cs:ip %04x:%04x, ds %04x\n", 
+		    wpnt->name, cs_reg, ip_reg, ds_reg);
+	    	    
+		rv = CallTo16(cs_reg << 16 | ip_reg, ds_reg);
+		printf ("rv = %x\n", rv);
+	    } else
+		printf("%s skipped\n");
+	}
+}
+
+void InitializeLoadedDLLs(struct w_files *wpnt)
+{
+    static flagReadyToRun = 0;
+    struct w_files *final_wpnt;
+    struct w_files * wpnt;
+
+    if (wpnt == NULL)
+    {
+	flagReadyToRun = 1;
+	fprintf(stderr, "Initializing DLLs\n");
+    }
+    
+    if (!flagReadyToRun)
+	return;
+
+#if 1
+    if (wpnt != NULL)
+	fprintf(stderr, "Initializing %s\n", wpnt->name);
+#endif
+
+    /*
+     * Initialize libraries
+     */
+    if (!wpnt)
+    {
+	wpnt = wine_files;
+	final_wpnt = NULL;
+    }
+    else
+    {
+	final_wpnt = wpnt->next;
+    }
+    
+    for( ; wpnt != final_wpnt; wpnt = wpnt->next)
+	InitDLL(wpnt);
+}
+#endif
diff --git a/loader/ne_image.c b/loader/ne_image.c
new file mode 100644
index 0000000..98b3059
--- /dev/null
+++ b/loader/ne_image.c
@@ -0,0 +1,461 @@
+static char RCSId[] = "$Id: wine.c,v 1.2 1993/07/04 04:04:21 root Exp root $";
+static char Copyright[] = "Copyright  Robert J. Amstadt, 1993";
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
+#ifdef linux
+#include <linux/unistd.h>
+#include <linux/head.h>
+#include <linux/ldt.h>
+#include <linux/segment.h>
+#endif
+#include <string.h>
+#include <errno.h>
+#include "neexe.h"
+#include "segmem.h"
+#include "prototypes.h"
+#include "dlls.h"
+#include "wine.h"
+#include "windows.h"
+#include "wineopts.h"
+#include "arch.h"
+#include "options.h"
+
+/* #define DEBUG_FIXUP /* */
+
+extern HANDLE CreateNewTask(HINSTANCE hInst);
+extern int CallToInit16(unsigned long csip, unsigned long sssp, 
+			unsigned short ds);
+extern void InitializeLoadedDLLs(struct w_files *wpnt);
+extern void FixupFunctionPrologs(struct w_files * wpnt);
+
+char * GetModuleName(struct w_files * wpnt, int index, char *buffer);
+extern char WindowsPath[256];
+char *WIN_ProgramName;
+
+HINSTANCE hSysRes;
+
+#ifndef WINELIB
+
+/**********************************************************************/
+
+void load_ne_header (int fd, struct ne_header_s *ne_header)
+{
+    if (read(fd, ne_header, sizeof(struct ne_header_s)) 
+	!= sizeof(struct ne_header_s))
+    {
+	myerror("Unable to read NE header from file");
+    }
+}
+
+/**********************************************************************
+ *			LoadNEImage
+ * Load one NE format executable into memory
+ */
+HINSTANCE LoadNEImage(struct w_files *wpnt)
+{
+    unsigned int read_size, status, segment;
+    int i;
+    char buffer[256];
+    char *fullname;
+    HANDLE t;
+
+    wpnt->ne_header = (struct ne_header_s *) malloc(sizeof(struct ne_header_s));
+    status = lseek(wpnt->fd, wpnt->mz_header->ne_offset, SEEK_SET);
+    load_ne_header (wpnt->fd, wpnt->ne_header);
+
+    /*
+     * Create segment selectors.
+     */
+    status = lseek(wpnt->fd, wpnt->mz_header->ne_offset + 
+		   wpnt->ne_header->segment_tab_offset,
+		   SEEK_SET);
+    read_size  = wpnt->ne_header->n_segment_tab *
+	sizeof(struct ne_segment_table_entry_s);
+    wpnt->seg_table = (struct ne_segment_table_entry_s *) malloc(read_size);
+    if (read(wpnt->fd, wpnt->seg_table, read_size) != read_size)
+	myerror("Unable to read segment table header from file");
+    wpnt->selector_table = CreateSelectors(wpnt);
+    wpnt->hinstance = (wpnt->
+		       selector_table[wpnt->ne_header->auto_data_seg-1].
+		       selector);
+
+    /* Get the lookup  table.  This is used for looking up the addresses
+       of functions that are exported */
+
+    read_size  = wpnt->ne_header->entry_tab_length;
+    wpnt->lookup_table = (char *) malloc(read_size);
+    lseek(wpnt->fd, wpnt->mz_header->ne_offset + 
+	  wpnt->ne_header->entry_tab_offset, SEEK_SET);
+    if (read(wpnt->fd, wpnt->lookup_table, read_size) != read_size)
+	myerror("Unable to read lookup table header from file");
+
+    /* Get the iname table.  This is used for looking up the names
+       of functions that are exported */
+
+    status = lseek(wpnt->fd, wpnt->ne_header->nrname_tab_offset,  SEEK_SET);
+    read_size  = wpnt->ne_header->nrname_tab_length;
+    wpnt->nrname_table = (char *) malloc(read_size);
+    if (read(wpnt->fd, wpnt->nrname_table, read_size) != read_size)
+	myerror("Unable to read nrname table header from file");
+
+    status = lseek(wpnt->fd, wpnt->mz_header->ne_offset + 
+		   wpnt->ne_header->rname_tab_offset,  SEEK_SET);
+    read_size  = wpnt->ne_header->moduleref_tab_offset - 
+	    wpnt->ne_header->rname_tab_offset;
+    wpnt->rname_table = (char *) malloc(read_size);
+    if (read(wpnt->fd, wpnt->rname_table, read_size) != read_size)
+	myerror("Unable to read rname table header from file");
+
+    /* Now get the module name, if the current one is a filename */
+/* nope, name by which dll is loaded is used ! 
+
+    if (strchr(wpnt->name, '\\') || strchr(wpnt->name, '/') ) {
+	wpnt->name  = (char*) malloc(*wpnt->rname_table + 1);
+	memcpy(wpnt->name, wpnt->rname_table+1, *wpnt->rname_table);
+    }
+    wpnt->name[*wpnt->rname_table] =  0;
+*/
+    /*
+     * Now load any DLLs that  this module refers to.
+     */
+    for(i=0; i<wpnt->ne_header->n_mod_ref_tab; i++)
+    {
+      char buff[14];
+      GetModuleName(wpnt, i + 1, buff);
+
+      if (strcasecmp(buff, wpnt->name) != 0 )
+	LoadImage(buff, DLL, 0);
+    }
+    /* fixup references */
+
+    for (segment = 0; segment < wpnt->ne_header->n_segment_tab; segment++)
+	if (FixupSegment(wpnt, segment) < 0)
+		myerror("fixup failed.");
+
+    FixupFunctionPrologs(wpnt);
+    InitializeLoadedDLLs(wpnt);
+
+    return(wpnt->hinstance);
+}
+
+/**********************************************************************
+ *					GetImportedName
+ */
+char *
+GetImportedName(int fd, struct mz_header_s *mz_header, 
+		struct ne_header_s *ne_header, int name_offset, char *buffer)
+{
+    int length;
+    int status;
+    
+    status = lseek(fd, mz_header->ne_offset + ne_header->iname_tab_offset +
+		   name_offset, SEEK_SET);
+    length = 0;
+    read(fd, &length, 1);  /* Get the length byte */
+    length = CONV_CHAR_TO_LONG (length);
+    read(fd, buffer, length);
+    buffer[length] = 0;
+    return buffer;
+}
+
+/**********************************************************************
+ *					GetModuleName
+ */
+char *
+GetModuleName(struct w_files * wpnt, int index, char *buffer)
+{
+    int fd = wpnt->fd;
+    struct mz_header_s *mz_header = wpnt->mz_header; 
+    struct ne_header_s *ne_header = wpnt->ne_header;
+    int length;
+    WORD name_offset, status;
+    int i;
+    
+    status = lseek(fd, mz_header->ne_offset + ne_header->moduleref_tab_offset +
+		   2*(index - 1), SEEK_SET);
+    name_offset = 0;
+    read(fd, &name_offset, 2);
+    name_offset = CONV_SHORT (name_offset);
+    status = lseek(fd, mz_header->ne_offset + ne_header->iname_tab_offset +
+		   name_offset, SEEK_SET);
+    length = 0;
+    read(fd, &length, 1);  /* Get the length byte */
+    length = CONV_CHAR_TO_LONG (length);
+    read(fd, buffer, length);
+    buffer[length] = 0;
+
+    /* Module names  are always upper case */
+    for(i=0; i<length; i++)
+	    if(buffer[i] >= 'a' && buffer[i] <= 'z')  buffer[i] &= ~0x20;
+
+    return buffer;
+}
+
+
+/**********************************************************************
+ *					FixupSegment
+ */
+int
+FixupSegment(struct w_files * wpnt, int segment_num)
+{
+    int fd =  wpnt->fd;
+    struct mz_header_s * mz_header = wpnt->mz_header;
+    struct ne_header_s *ne_header =  wpnt->ne_header;
+    struct ne_segment_table_entry_s *seg_table = wpnt->seg_table;
+    struct segment_descriptor_s *selector_table = wpnt->selector_table;
+    struct relocation_entry_s *rep, *rep1;
+    struct ne_segment_table_entry_s *seg;
+    struct segment_descriptor_s *sel;
+    struct dll_table_entry_s *dll_table;
+    int status;
+    unsigned short *sp;
+    unsigned int selector, address;
+    unsigned int next_addr;
+    int ordinal;
+    char dll_name[257];
+    char func_name[257];
+    int i, n_entries;
+    int additive;
+
+    seg = &seg_table[segment_num];
+    sel = &selector_table[segment_num];
+
+#ifdef DEBUG_FIXUP
+    printf("Segment fixups for %s, segment %d, selector %x\n", 
+	   wpnt->name, segment_num, (int) sel->base_addr >> 16);
+#endif
+
+    if ((seg->seg_data_offset == 0) ||
+	!(seg->seg_flags & NE_SEGFLAGS_RELOC_DATA))
+	return 0;
+
+    /*
+     * Go through the relocation table on entry at a time.
+     */
+    i = seg->seg_data_length;
+    if (i == 0)
+	i = 0x10000;
+
+    status = lseek(fd, seg->seg_data_offset * 
+		       (1 << ne_header->align_shift_count) + i, SEEK_SET);
+    n_entries = 0;
+    read(fd, &n_entries, sizeof(short int));
+    rep = (struct relocation_entry_s *)
+	  malloc(n_entries * sizeof(struct relocation_entry_s));
+
+    if (read(fd,rep, n_entries * sizeof(struct relocation_entry_s)) !=
+        n_entries * sizeof(struct relocation_entry_s))
+    {
+	myerror("Unable to read relocation information");
+    }
+    
+    rep1 = rep;
+
+    for (i = 0; i < n_entries; i++, rep++)
+    {
+	/*
+	 * Get the target address corresponding to this entry.
+	 */
+	additive = 0;
+	
+	switch (rep->relocation_type)
+	{
+	  case NE_RELTYPE_ORDINALADD:
+	    additive = 1;
+	    
+	  case NE_RELTYPE_ORDINAL:
+	    if (GetModuleName(wpnt, rep->target1,
+			      dll_name) == NULL)
+	    {
+	      fprintf(stderr, "NE_RELTYPE_ORDINAL failed");
+		return -1;
+	    }
+	    
+	    ordinal = rep->target2;
+
+  	    status = GetEntryDLLOrdinal(dll_name, ordinal, &selector,
+					&address);
+	    if (status)
+	    {
+		char s[80];
+		
+		sprintf(s, "Bad DLL name '%s.%d'", dll_name, ordinal);
+		myerror(s);
+		return -1;
+	    }
+
+#ifdef DEBUG_FIXUP
+	    printf("%d: %s.%d: %04.4x:%04.4x\n", i + 1, dll_name, ordinal,
+		   selector, address);
+#endif
+	    break;
+	    
+	  case NE_RELTYPE_NAMEADD:
+	    additive = 1;
+	    
+	  case NE_RELTYPE_NAME:
+	    if (GetModuleName(wpnt, rep->target1, dll_name)
+		== NULL)
+	    {
+	      fprintf(stderr,"NE_RELTYPE_NAME failed");
+		return -1;
+	    }
+
+	    if (GetImportedName(fd, mz_header, ne_header, 
+				rep->target2, func_name) == NULL)
+	    {
+	      fprintf(stderr,"getimportedname failed");
+		return -1;
+	    }
+
+  	    status = GetEntryDLLName(dll_name, func_name, &selector, 
+					   &address);
+	    if (status)
+	    {
+		char s[80];
+		
+		sprintf(s, "Bad DLL name '%s (%s)'", dll_name,func_name);
+		myerror(s);
+		return -1;
+	    }
+
+#ifdef DEBUG_FIXUP
+	    printf("%d: %s %s.%d: %04.4x:%04.4x\n", i + 1, func_name,
+		   dll_name, ordinal, selector, address);
+#endif
+	    break;
+	    
+	  case NE_RELTYPE_INTERNAL:
+    	  case NE_RELTYPE_INT1:
+	    if (rep->target1 == 0x00ff)
+	    {
+		address  = GetEntryPointFromOrdinal(wpnt, rep->target2);
+		selector = (address >> 16) & 0xffff;
+		address &= 0xffff;
+	    }
+	    else
+	    {
+		selector = selector_table[rep->target1-1].selector;
+		address  = rep->target2;
+	    }
+	    
+#ifdef DEBUG_FIXUP
+	    printf("%d: %04.4x:%04.4x\n", i + 1, selector, address);
+#endif
+	    break;
+
+	  case 7:
+	    /* Relocation type 7:
+	     *
+	     *    These appear to be used as fixups for the Windows
+	     * floating point emulator.  Let's just ignore them and
+	     * try to use the hardware floating point.  Linux should
+	     * successfully emulate the coprocessor if it doesn't
+	     * exist.
+	     */
+#ifdef DEBUG_FIXUP
+	    printf("%d: ADDR TYPE %d,  TYPE %d,  OFFSET %04.4x,  ",
+		   i + 1, rep->address_type, rep->relocation_type, 
+		   rep->offset);
+	    printf("TARGET %04.4x %04.4x\n", rep->target1, rep->target2);
+#endif
+	    continue;
+	    
+	  default:
+	    fprintf(stderr,"%d: ADDR TYPE %d,  TYPE %d,  OFFSET %04.4x,  ",
+		   i + 1, rep->address_type, rep->relocation_type, 
+		   rep->offset);
+	    fprintf(stderr,"TARGET %04.4x %04.4x\n", 
+		    rep->target1, rep->target2);
+	    free(rep1);
+	    return -1;
+	}
+
+	/*
+	 * Stuff the right size result in.
+	 */
+	sp = (unsigned short *) ((char *) sel->base_addr + rep->offset);
+	if (additive)
+	{
+	    if (FindDLLTable(dll_name) == NULL)
+		additive = 2;
+
+	    fprintf(stderr,"%d: ADDR TYPE %d,  TYPE %d,  OFFSET %04.4x,  ",
+		   i + 1, rep->address_type, rep->relocation_type, 
+		   rep->offset);
+	    fprintf(stderr,"TARGET %04.4x %04.4x\n", 
+		    rep->target1, rep->target2);
+	    fprintf(stderr, "    Additive = %d\n", additive);
+	}
+	
+	switch (rep->address_type)
+	{
+	  case NE_RADDR_OFFSET16:
+	    do {
+#ifdef DEBUG_FIXUP
+		printf("    %04.4x:%04.4x:%04.4x OFFSET16\n",
+		       (unsigned long) sp >> 16, (int) sp & 0xFFFF, *sp);
+#endif
+		next_addr = *sp;
+		*sp = (unsigned short) address;
+		if (additive == 2)
+		    *sp += next_addr;
+		sp = (unsigned short *) ((char *) sel->base_addr + next_addr);
+	    } 
+	    while (next_addr != 0xffff && !additive);
+
+	    break;
+	    
+	  case NE_RADDR_POINTER32:
+	    do {
+#ifdef DEBUG_FIXUP
+		printf("    %04.4x:%04.4x:%04.4x POINTER32\n",
+		       (unsigned long) sp >> 16, (int) sp & 0xFFFF, *sp);
+#endif
+		next_addr = *sp;
+		*sp     = (unsigned short) address;
+		if (additive == 2)
+		    *sp += next_addr;
+		*(sp+1) = (unsigned short) selector;
+		sp = (unsigned short *) ((char *) sel->base_addr + next_addr);
+	    } 
+	    while (next_addr != 0xffff && !additive);
+
+	    break;
+	    
+	  case NE_RADDR_SELECTOR:
+	    do {
+#ifdef DEBUG_FIXUP
+		printf("    %04.4x:%04.4x:%04.4x SELECTOR\n",
+		       (unsigned long) sp >> 16, (int) sp & 0xFFFF, *sp);
+#endif
+		next_addr = *sp;
+		*sp     = (unsigned short) selector;
+		sp = (unsigned short *) ((char *) sel->base_addr + next_addr);
+		if (rep->relocation_type == NE_RELTYPE_INT1) 
+		    break;
+	    } 
+	    while (next_addr != 0xffff && !additive);
+
+	    break;
+	    
+	  default:
+	    printf("%d: ADDR TYPE %d,  TYPE %d,  OFFSET %04.4x,  ",
+		   i + 1, rep->address_type, rep->relocation_type, 
+		   rep->offset);
+	    printf("TARGET %04.4x %04.4x\n", rep->target1, rep->target2);
+	    free(rep1);
+	    return -1;
+	}
+    }
+
+    free(rep1);
+    return 0;
+}
+
+#endif
diff --git a/loader/resource.c b/loader/resource.c
index a4f9c1f..902242f 100644
--- a/loader/resource.c
+++ b/loader/resource.c
@@ -16,6 +16,7 @@
 #include "wine.h"
 #include "icon.h"
 #include "accel.h"
+#include "dlls.h"
 
 /* #define DEBUG_RESOURCE  */
 
@@ -922,14 +923,14 @@
     if (image_size_ret != NULL)
 	*image_size_ret = image_size;
     hmem = GlobalAlloc(GMEM_MOVEABLE, image_size);
-    image = GlobalLock(hmem);
+    image = GlobalLinearLock(hmem);
     if (image == NULL || read(ResourceFd, image, image_size) != image_size)
     {
 	GlobalFree(hmem);
 	return 0;
     }
 
-    GlobalUnlock(hmem);
+    GlobalLinearUnlock(hmem);
     return hmem;
 }
 
@@ -1021,7 +1022,7 @@
 	printf("LoadBitmap / BitMap %04X not Found !\n", bmp_name);
 	return 0;
 	}
-    lp = (long *) GlobalLock(rsc_mem);
+    lp = (long *) GlobalLinearLock(rsc_mem);
     if (lp == NULL)
     {
 	GlobalFree(rsc_mem);
diff --git a/loader/selector.c b/loader/selector.c
index 9573c7a..b9b66bd 100644
--- a/loader/selector.c
+++ b/loader/selector.c
@@ -22,14 +22,14 @@
 #include <sys/mman.h>
 #include <machine/segments.h>
 #endif
-
+#include "dlls.h"
 #include "neexe.h"
 #include "segmem.h"
 #include "wine.h"
 #include "windows.h"
 #include "prototypes.h"
 
-/* #define DEBUG_SELECTORS */
+/* #define DEBUG_SELECTORS /* */
 
 #ifdef linux
 #define DEV_ZERO
@@ -579,7 +579,7 @@
 	/* We need a means  of determining the ordinal for the function. */
 	/* Not a builtin symbol, look to see what the file has for us */
 	for(wpnt = wine_files; wpnt; wpnt = wpnt->next){
-		if(strcmp(wpnt->name, dll_name)) continue;
+		if(strcasecmp(wpnt->name, dll_name)) continue;
 		cpnt  = wpnt->nrname_table;
 		while(1==1){
 			if( ((int) cpnt)  - ((int)wpnt->nrname_table) >  
@@ -618,7 +618,7 @@
 
 	/* Not a builtin symbol, look to see what the file has for us */
 	for(wpnt = wine_files; wpnt; wpnt = wpnt->next){
-		if(strcmp(wpnt->name, dll_name)) continue;
+		if(strcasecmp(wpnt->name, dll_name)) continue;
 		j = GetEntryPointFromOrdinal(wpnt, ordinal);
 		*addr  = j & 0xffff;
 		j = j >> 16;
@@ -699,6 +699,73 @@
 }
 
 /**********************************************************************
+ */
+void
+FixupFunctionPrologs(struct w_files * wpnt)
+{
+    struct mz_header_s *mz_header = wpnt->mz_header;   
+    struct ne_header_s *ne_header = wpnt->ne_header;   
+    union lookup entry_tab_pointer;
+    struct entry_tab_header_s *eth;
+    struct entry_tab_movable_s *etm;
+    struct entry_tab_fixed_s *etf;
+    unsigned char *fixup_ptr;
+    int i;
+
+    if (!(ne_header->format_flags & 0x0001))
+	return;
+
+    entry_tab_pointer.cpnt = wpnt->lookup_table;
+    /*
+     * Let's walk through the table and fixup prologs as we go.
+     */
+    while (1)
+    {
+	/* Get bundle header */
+	eth = entry_tab_pointer.eth++;
+
+	/* Check for end of table */
+	if (eth->n_entries == 0)
+	    return;
+
+	/* Check for empty bundle */
+	if (eth->seg_number == 0)
+	    continue;
+
+	/* Examine each bundle */
+	for (i = 0; i < eth->n_entries; i++)
+	{
+	    /* Moveable segment */
+	    if (eth->seg_number >= 0xfe)
+	    {
+		etm = entry_tab_pointer.etm++;
+		fixup_ptr = (wpnt->selector_table[etm->seg_number-1].base_addr
+			     + etm->offset);
+	    }
+	    else
+	    {
+		etf = entry_tab_pointer.etf++;
+		fixup_ptr = (wpnt->selector_table[eth->seg_number-1].base_addr
+			     + (int) etf->offset[0] 
+			     + ((int) etf->offset[1] << 8));
+
+	    }
+
+	    /* Verify the signature */
+	    if (((fixup_ptr[0] == 0x1e && fixup_ptr[1] == 0x58)
+		 || (fixup_ptr[0] == 0x8c && fixup_ptr[1] == 0xd8))
+		&& fixup_ptr[2] == 0x90)
+	    {
+		fixup_ptr[0] = 0xb8;	/* MOV AX, */
+		fixup_ptr[1] = wpnt->hinstance;
+		fixup_ptr[2] = (wpnt->hinstance >> 8);
+	    }
+	}
+    }
+}
+
+
+/**********************************************************************
  *					GetDOSEnvironment
  */
 LPSTR GetDOSEnvironment(void)
@@ -897,10 +964,21 @@
 		read_only = 1;
 	}
 
+#if 0
 	stmp = CreateNewSegments(!(s->flags & NE_SEGFLAGS_DATA), read_only,
 				s->length, 1);
 	s->base_addr = stmp->base_addr;
 	s->selector = stmp->selector;
+#endif
+	s->selector = GlobalAlloc(GMEM_FIXED, s->length);
+	if (s->selector == 0)
+	    myerror("CreateSelectors: GlobalAlloc() failed");
+
+	s->base_addr = (void *) ((LONG) s->selector << 16);
+	if (!(s->flags & NE_SEGFLAGS_DATA))
+	    PrestoChangoSelector(s->selector, s->selector);
+	else
+	    memset(s->base_addr, 0, s->length);
 	
 	if (seg_table[i].seg_data_offset != 0)
 	{
@@ -942,4 +1020,41 @@
 
     return selectors;
 }
+
+/***********************************************************************
+ *	GetSelectorBase (KERNEL.186)
+ */
+DWORD GetSelectorBase(WORD wSelector)
+{
+	fprintf(stderr, "GetSelectorBase(selector %4X) stub!\n", wSelector);
+}
+
+/***********************************************************************
+ *	SetSelectorBase (KERNEL.187)
+ */
+void SetSelectorBase(WORD wSelector, DWORD dwBase)
+{
+	fprintf(stderr, "SetSelectorBase(selector %4X, base %8X) stub!\n",
+			wSelector, dwBase);
+}
+
+/***********************************************************************
+ *	GetSelectorLimit (KERNEL.188)
+ */
+DWORD GetSelectorLimit(WORD wSelector)
+{
+	fprintf(stderr, "GetSelectorLimit(selector %4X) stub!\n", wSelector);
+
+	return 0xffff;
+}
+
+/***********************************************************************
+ *	SetSelectorLimit (KERNEL.189)
+ */
+void SetSelectorLimit(WORD wSelector, DWORD dwLimit)
+{
+	fprintf(stderr, "SetSelectorLimit(selector %4X, base %8X) stub!\n", 
+			wSelector, dwLimit);
+}
+
 #endif /* ifndef WINELIB */
diff --git a/loader/signal.c b/loader/signal.c
index 7de7064..7e8bc0f 100644
--- a/loader/signal.c
+++ b/loader/signal.c
@@ -42,6 +42,39 @@
 	return -1;
 }
 
+int do_int(int intnum, struct sigcontext_struct *scp)
+{
+	switch(intnum)
+	{
+	      case 0x10: return do_int10(scp);
+
+	      case 0x11:  
+		scp->sc_eax = (scp->sc_eax & 0xffff0000L) | DOS_GetEquipment();
+		return 1;
+
+	      case 0x12:               
+		scp->sc_eax = (scp->sc_eax & 0xffff0000L) | 640L; 
+		return 1;	/* get base mem size */                
+
+	      case 0x15: return do_int15(scp);
+	      case 0x1A: return do_int1A(scp);
+	      case 0x21: return do_int21(scp);
+
+	      case 0x22:
+		scp->sc_eax = 0x1234;
+		scp->sc_ebx = 0x5678;
+		scp->sc_ecx = 0x9abc;
+		scp->sc_edx = 0xdef0;
+		return 1;
+
+	      case 0x25: return do_int25(scp);
+	      case 0x26: return do_int26(scp);
+	      case 0x2f: return do_int2f(scp);
+	      case 0x31: return do_int31(scp);
+	}
+	return 0;
+}
+
 #ifdef linux
 static void win_fault(int signal, struct sigcontext_struct context)
 {
@@ -90,54 +123,7 @@
     {
       case 0xcd: /* int <XX> */
             instr++;
-	    switch(*instr)
-	    {
-	      case 0x10:
-		if(!do_int10(scp)) 
-		    goto oops;
-		break;
-
-	      case 0x11:  
-		scp->sc_eax = (scp->sc_eax & 0xffff0000L) | DOS_GetEquipment();
-		break;
-
-	      case 0x12:               
-		scp->sc_eax = (scp->sc_eax & 0xffff0000L) | 640L; 
-		break;				/* get base mem size */                
-
-	      case 0x1A:
-		if(!do_int1A(scp)) 
-		    goto oops;
-		break;
-
-	      case 0x21:
-		if (!do_int21(scp)) 
-		    goto oops;
-		break;
-
-	      case 0x22:
-		scp->sc_eax = 0x1234;
-		scp->sc_ebx = 0x5678;
-		scp->sc_ecx = 0x9abc;
-		scp->sc_edx = 0xdef0;
-		break;
-
-	      case 0x25:
-		if (!do_int25(scp)) 
-		    goto oops;
-		break;
-
-	      case 0x26:
-		if (!do_int26(scp)) 
-		    goto oops;
-		break;
-
-	      case 0x2f:
-		if (!do_int2f(scp)) 
-		    goto oops;
-		break;
-		
-	      default:
+	    if (!do_int(*instr, scp)) {
 		fprintf(stderr,"Unexpected Windows interrupt %x\n", *instr);
 		goto oops;
 	    }
diff --git a/memory/global.c b/memory/global.c
index ef4e170..7509868 100644
--- a/memory/global.c
+++ b/memory/global.c
@@ -187,7 +187,7 @@
      */
     if (size > 0x8000 || !(flags & GLOBAL_FLAGS_MOVEABLE))
     {
-	int segments = (size >> 16) + 1;
+	int segments = ((size - 1) >> 16) + 1;
 
 	g = GlobalGetFreeSegments(flags, segments);
 	if (g == NULL)
@@ -666,14 +666,25 @@
 	else if (n_segments < g->length)
 	{
 	    GDESC *g_free;
+	    int old_length = g->length;
 	    
 	    g_free = g;
 	    for (i = 0; i < n_segments; i++)
 	    {
 		if (g_free->sequence != i + 1)
 		    return 0;
+		g_free->length = n_segments;
 		g_free = g_free->next;
 	    }
+
+	    for ( ; i < old_length; i++)
+	    {
+		g_free->length = 0x10000;
+		g_free->sequence = -1;
+		g_free = g_free->next;
+	    }
+
+	    return g->handle;
 	}
 	
 	/*
diff --git a/memory/heap.c b/memory/heap.c
index d6535f3..ceaa85b 100644
--- a/memory/heap.c
+++ b/memory/heap.c
@@ -13,6 +13,16 @@
 
 LHEAP *LocalHeaps = NULL;
 
+void
+HEAP_CheckHeap(MDESC **free_list)
+{
+    MDESC *m;
+
+    for (m = *free_list; m != NULL; m = m->next)
+	if (((int) m & 0xffff0000) != ((int) *free_list & 0xffff0000))
+	    *(char *)0 = 0;
+}
+
 /**********************************************************************
  *					HEAP_Init
  */
@@ -23,8 +33,8 @@
 	return;
     
     *free_list = (MDESC *) start;
-    (*free_list)->prev = NULL;
-    (*free_list)->next = NULL;
+    (*free_list)->prev   = NULL;
+    (*free_list)->next   = NULL;
     (*free_list)->length = length - sizeof(MDESC);
 }
 
@@ -39,6 +49,7 @@
 #ifdef DEBUG_HEAP
     printf("HeapAlloc: free_list %08x, flags %x, bytes %d\n", 
 	   free_list, flags, bytes);
+    HEAP_CheckHeap(free_list);
 #endif
 
     /*
@@ -74,6 +85,7 @@
 		memset(m + 1, 0, bytes);
 #ifdef DEBUG_HEAP
 	    printf("HeapAlloc: returning %08x\n", (m + 1));
+	    HEAP_CheckHeap(free_list);
 #endif
 	    return (void *) (m + 1);
 	}
@@ -97,12 +109,14 @@
 	    memset(m + 1, 0, bytes);
 #ifdef DEBUG_HEAP
 	printf("HeapAlloc: returning %08x\n", (m + 1));
+	HEAP_CheckHeap(free_list);
 #endif
 	return (void *) (m + 1);
     }
 
 #ifdef DEBUG_HEAP
     printf("HeapAlloc: returning %08x\n", 0);
+    HEAP_CheckHeap(free_list);
 #endif
     return 0;
 }
@@ -133,6 +147,7 @@
     printf("HEAP_ReAlloc m->prev=%08X !\n", m->prev);
     printf("HEAP_ReAlloc m->next=%08X !\n", m->next);
     printf("HEAP_ReAlloc *free_list=%08X !\n", *free_list);
+    HEAP_CheckHeap(free_list);
 #endif
 
     if (m->prev != m || m->next != m || 
@@ -141,6 +156,7 @@
 #ifdef DEBUG_HEAP
 	printf("Attempt to resize bad pointer, m = %08x, *free_list = %08x\n",
 	       m, free_list);
+	HEAP_CheckHeap(free_list);
 #endif
 	return NULL;
     }
@@ -164,6 +180,9 @@
 		return NULL;
 	    memcpy(new_p, old_block, m->length);
 	    HEAP_Free(free_list, old_block);
+#ifdef DEBUG_HEAP
+	    HEAP_CheckHeap(free_list);
+#endif
 	    return new_p;
 	}
 
@@ -199,6 +218,9 @@
 	HEAP_Free(free_list, m_free + 1);
     }
     
+#ifdef DEBUG_HEAP
+    HEAP_CheckHeap(free_list);
+#endif
     return old_block;
 }
 
@@ -213,6 +235,12 @@
     MDESC *m;
     MDESC *m_prev;
 
+#ifdef DEBUG_HEAP
+    printf("HeapFree: free_list %08x, block %08x\n", 
+	   free_list, block);
+    HEAP_CheckHeap(free_list);
+#endif
+
     /*
      * Validate pointer.
      */
@@ -300,6 +328,9 @@
 	m_free->next = NULL;
     }
 
+#ifdef DEBUG_HEAP
+    HEAP_CheckHeap(free_list);
+#endif
     return 0;
 }
 
@@ -347,6 +378,7 @@
     lh->next        = LocalHeaps;
     lh->selector    = owner;
     lh->local_table = NULL;
+    lh->delta       = 0x20;
     HEAP_Init(&lh->free_list, start, length);
     LocalHeaps = lh;
 }
@@ -521,6 +553,24 @@
 }
 
 /**********************************************************************
+ *					WIN16_LocalHandleDelta
+ */
+unsigned int
+WIN16_LocalHandleDelta(unsigned int new_delta)
+{
+    LHEAP *lh;
+    
+    lh = HEAP_LocalFindHeap(HEAP_OWNER);
+    if (lh == NULL)
+	return 0;
+    
+    if (new_delta)
+	lh->delta = new_delta;
+
+    return lh->delta;
+}
+
+/**********************************************************************
  *                      GetFreeSystemResources (user.284)
 
  */
diff --git a/misc/Imakefile b/misc/Imakefile
index 6cfa02f..5967031 100644
--- a/misc/Imakefile
+++ b/misc/Imakefile
@@ -11,6 +11,7 @@
 	dos_fs.c \
 	driver.c \
 	exec.c \
+	escape.c \
 	file.c \
 	keyboard.c \
 	lstr.c \
diff --git a/misc/audio.c b/misc/audio.c
index 97a2e60..008029f 100644
--- a/misc/audio.c
+++ b/misc/audio.c
@@ -15,9 +15,9 @@
 
 
 /**************************************************************************
-* 				DriverProc			[sample driver]
+* 				AUDIO_DriverProc		[sample driver]
 */
-LRESULT DriverProc(DWORD dwDevID, HDRVR hDriv, WORD wMsg, 
+LRESULT AUDIO_DriverProc(DWORD dwDevID, HDRVR hDriv, WORD wMsg, 
 						DWORD dwParam1, DWORD dwParam2)
 {
 	switch(wMsg) {
diff --git a/misc/cursor.c b/misc/cursor.c
index 15bc145..91e88ef 100644
--- a/misc/cursor.c
+++ b/misc/cursor.c
@@ -127,6 +127,13 @@
 		break;
 	    }
 	}
+
+#if 1
+    lpcur->xcursor = XCreateFontCursor(XT_display, XC_top_left_arrow);
+    GlobalUnlock(hCursor);
+    return hCursor;
+#endif
+
     if (!(hdc = GetDC(GetDesktopWindow()))) return 0;
     rsc_mem = RSC_LoadResource(instance, cursor_name, NE_RSCTYPE_GROUP_CURSOR, 
 			       &image_size);
diff --git a/misc/dos_fs.c b/misc/dos_fs.c
index 83ed2b5..dc3b1bb 100644
--- a/misc/dos_fs.c
+++ b/misc/dos_fs.c
@@ -128,17 +128,13 @@
 			continue;
 		}
 		ExpandTildeString(temp);
-		if ((ptr = (char *) malloc(strlen(temp)+1)) == NULL) {
-			fprintf(stderr,"DOSFS: can't malloc for drive info!");
-			continue;
-		}
-			ChopOffSlash(temp);
-			DosDrives[x].rootdir = ptr;
-			strcpy(DosDrives[x].rootdir, temp);
-			strcpy(DosDrives[x].cwd, "/windows/");
-			strcpy(DosDrives[x].label, "DRIVE-");
-			strcat(DosDrives[x].label, drive);
-			DosDrives[x].disabled = 0;
+		ChopOffSlash(temp);
+		DosDrives[x].rootdir = strdup(temp);
+		strcpy(DosDrives[x].rootdir, temp);
+		strcpy(DosDrives[x].cwd, "/windows/");
+		strcpy(DosDrives[x].label, "DRIVE-");
+		strcat(DosDrives[x].label, drive);
+		DosDrives[x].disabled = 0;
 	}
 	DOS_SetDefaultDrive(2);
 
@@ -393,19 +389,22 @@
 char *GetDosFileName(char *unixfilename)
 { 
 	int i;
-	static char temp[256];
+	static char temp[256], rootdir[256];
 	/*   /dos/windows/system.ini => c:\windows\system.ini */
 	
 	for (i = 0 ; i != MAX_DOS_DRIVES; i++) {
 		if (DosDrives[i].rootdir != NULL) {
-		   if (strncmp(DosDrives[i].rootdir, unixfilename, strlen(DosDrives[i].rootdir)) == 0) {
-			sprintf(temp, "%c:\\%s", 'A' + i, unixfilename + strlen(DosDrives[i].rootdir) + 1);
-			ToDos(temp);
-			return temp;
-		   }	
+ 			strcpy(rootdir, DosDrives[i].rootdir);
+ 			strcat(rootdir, "/");
+                	ToUnix(rootdir);
+ 			if (strncmp(rootdir, unixfilename, strlen(rootdir)) == 0) {
+ 				sprintf(temp, "%c:\\%s", 'A' + i, unixfilename + strlen(rootdir));
+				ToDos(temp);
+				return temp;
+			}	
 		}
 	}
-	strcpy(temp, unixfilename);
+	sprintf(temp, "UNIX:%s", unixfilename);
 	ToDos(temp);
 	return(temp);
 }
@@ -534,7 +533,11 @@
     {
 	strncpy(buffer, GetUnixFileName(filename), buflen);
 	ToUnix(buffer);
-	return buffer;
+	stat( buffer, &filestat);
+	if (S_ISREG(filestat.st_mode))
+	    return buffer;
+	else
+	    return NULL;
     }
 
     if (strchr(filename, '/') != NULL)
diff --git a/misc/driver.c b/misc/driver.c
index a3e4975..28888b5 100644
--- a/misc/driver.c
+++ b/misc/driver.c
@@ -6,10 +6,11 @@
 
 static char Copyright[] = "Copyright  Martin Ayotte, 1994";
 
-#include "stdio.h"
+#include <stdio.h>
 #include "windows.h"
 #include "win.h"
 #include "user.h"
+#include "dlls.h"
 #include "driver.h"
 
 LPDRIVERITEM lpDrvItemList = NULL;
@@ -47,7 +48,7 @@
 	lpnewdrv = (LPDRIVERITEM) GlobalLock(hDrvr);
 	if (lpnewdrv == NULL) return 0;
 	lpnewdrv->dis.length = sizeof(DRIVERINFOSTRUCT);
-	lpnewdrv->dis.hModule = LoadImage("DrvName", DLL);
+	lpnewdrv->dis.hModule = LoadImage("DrvName", DLL, 0);
 	if (lpnewdrv->dis.hModule == 0) {
 		GlobalUnlock(hDrvr);
 		GlobalFree(hDrvr);
diff --git a/misc/escape.c b/misc/escape.c
new file mode 100644
index 0000000..a4f6a6f
--- /dev/null
+++ b/misc/escape.c
@@ -0,0 +1,18 @@
+/*
+ * Escape() function.
+ *
+ * Copyright 1994  Bob Amstadt
+ */
+
+static char Copyright[] = "Copyright  Bob Amstadt, 1994";
+
+#include <stdlib.h>
+#include <stdio.h>
+#include "windows.h"
+
+int Escape(HDC hdc, int nEscape, int cbInput, 
+	   LPSTR lpszInData, LPSTR lpvOutData)
+{
+    fprintf(stderr, "Escape(nEscape = %04x)\n", nEscape);
+    return 0;
+}
diff --git a/misc/main.c b/misc/main.c
index fca16e6..ab3c2e7 100644
--- a/misc/main.c
+++ b/misc/main.c
@@ -342,6 +342,7 @@
     MAIN_SaveSetup();
     DOS_InitFS();
     Comm_Init();
+    INT21_Init();
     
 #ifndef sunos
     atexit(called_at_exit);
@@ -557,3 +558,13 @@
 	return 0;	/* don't swap */
 }
 
+/***********************************************************************
+*	ISROMMODULE (KERNEL.323)
+*/
+BOOL IsRomModule(HANDLE x)
+{
+	/* I don't know the prototype, I assume that it returns true
+	   if the dll is located in rom */
+	   
+	return FALSE;
+}
diff --git a/misc/message.c b/misc/message.c
index 9d754e3..d9669b6 100644
--- a/misc/message.c
+++ b/misc/message.c
@@ -270,14 +270,21 @@
 			lpmb->rectStr.left += 64;
 			}
 	    break;
+	case WM_SHOWWINDOW:
+		if (!(wParam == 0 && lParam == 0L)) {
+			InvalidateRect(hWnd, NULL, TRUE);
+			}
+	    break;
 	case WM_PAINT:
 #ifdef DEBUG_MSGBOX
-		printf("MessageBox WM_PAINT !\n");
+		printf("MessageBox WM_PAINT hWnd=%04X !\n", hWnd);
 #endif
 		lpmb = MsgBoxGetStorageHeader(hWnd);
 		if (lpmb == NULL) break;
-		CopyRect(&rect, &lpmb->rectStr);
 		hDC = BeginPaint(hWnd, &ps);
+		GetClientRect(hWnd, &rect);
+		FillRect(hDC, &rect, GetStockObject(WHITE_BRUSH));
+		CopyRect(&rect, &lpmb->rectStr);
 		OldTextColor = SetTextColor(hDC, 0x00000000);
 		if (lpmb->hIcon) 
 			DrawIcon(hDC, lpmb->rectIcon.left,
diff --git a/misc/mmsystem.c b/misc/mmsystem.c
index 09304df..6e22c5c 100644
--- a/misc/mmsystem.c
+++ b/misc/mmsystem.c
@@ -8,6 +8,7 @@
 
 #include "stdio.h"
 #include "win.h"
+#include "driver.h"
 #include "mmsystem.h"
 
 static WORD		mciActiveDev = 0;
@@ -17,7 +18,10 @@
 UINT WINAPI waveGetErrorText(UINT uError, LPSTR lpText, UINT uSize);
 
 
-int MCI_LibMain(HANDLE hInstance, WORD wDataSeg,
+/**************************************************************************
+* 				MMSYSTEM_WEP		[MMSYSTEM.1]
+*/
+int MMSYSTEM_WEP(HANDLE hInstance, WORD wDataSeg,
 		 WORD cbHeapSize, LPSTR lpCmdLine)
 {
 	printf("MMSYSTEM DLL INIT ... hInst=%04X \n", hInstance);
@@ -29,7 +33,7 @@
 */
 BOOL WINAPI sndPlaySound(LPCSTR lpszSoundName, UINT uFlags)
 {
-	printf("sndPlaySound // lpszSoundName='%s' uFlags=%04X !\n", 
+	printf("EMPTY STUB !!! sndPlaySound // SoundName='%s' uFlags=%04X !\n", 
 										lpszSoundName, uFlags);
 	return 0;
 }
@@ -44,14 +48,107 @@
 }
 
 /**************************************************************************
+* 				DriverProc	[MMSYSTEM.6]
+*/
+LRESULT DriverProc(DWORD dwDevID, HDRVR hDriv, WORD wMsg, 
+						DWORD dwParam1, DWORD dwParam2)
+{
+	return DrvDefDriverProc(dwDevID, hDriv, wMsg, dwParam1, dwParam2);
+}
+
+/**************************************************************************
 * 				OutputDebugStr		[MMSYSTEM.30]
 */
 void WINAPI OutputDebugStr(LPCSTR str)
 {
-	printf("OutputDebugStr('%s');\n", str);
+	printf("EMPTY STUB !!! OutputDebugStr('%s');\n", str);
 }
 
 /**************************************************************************
+* 				DriverCallback	[MMSYSTEM.31]
+*/
+BOOL DriverCallback(DWORD dwCallBack, UINT uFlags, HANDLE hDev, 
+		WORD wMsg, DWORD dwUser, DWORD dwParam1, DWORD dwParam2)
+{
+	printf("EMPTY STUB !!! DriverCallback() !\n");
+}
+
+/**************************************************************************
+* 				JoyGetNumDevs		[MMSYSTEM.101]
+*/
+WORD JoyGetNumDevs()
+{
+	printf("EMPTY STUB !!! JoyGetNumDevs();\n");
+	return 0;
+}
+
+/**************************************************************************
+* 				JoyGetDevCaps		[MMSYSTEM.102]
+*/
+WORD JoyGetDevCaps(WORD wID, LPJOYCAPS lpCaps, WORD wSize)
+{
+	printf("EMPTY STUB !!! JoyGetDevCaps(%04X, %08X, %d);\n", 
+										wID, lpCaps, wSize);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoyGetPos			[MMSYSTEM.103]
+*/
+WORD JoyGetPos(WORD wID, LPJOYINFO lpInfo)
+{
+	printf("EMPTY STUB !!! JoyGetPos(%04X, %08X);\n", wID, lpInfo);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoyGetThreshold		[MMSYSTEM.104]
+*/
+WORD JoyGetThreshold(WORD wID, LPWORD lpThreshold)
+{
+	printf("EMPTY STUB !!! JoyGetThreshold(%04X, %08X);\n", wID, lpThreshold);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoyReleaseCapture	[MMSYSTEM.105]
+*/
+WORD JoyReleaseCapture(WORD wID)
+{
+	printf("EMPTY STUB !!! JoyReleaseCapture(%04X);\n", wID);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoySetCapture		[MMSYSTEM.106]
+*/
+WORD JoySetCapture(HWND hWnd, WORD wID, WORD wPeriod, BOOL bChanged)
+{
+	printf("EMPTY STUB !!! JoySetCapture(%04X, %04X, %d, %d);\n", 
+							hWnd, wID, wPeriod, bChanged);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoySetThreshold		[MMSYSTEM.107]
+*/
+WORD JoySetThreshold(WORD wID, WORD wThreshold)
+{
+	printf("EMPTY STUB !!! JoySetThreshold(%04X, %d);\n", wID, wThreshold);
+	return MMSYSERR_NODRIVER;
+}
+
+/**************************************************************************
+* 				JoySetCalibration	[MMSYSTEM.109]
+*/
+WORD JoySetCalibration(WORD wID)
+{
+	printf("EMPTY STUB !!! JoySetCalibration(%04X);\n", wID);
+	return MMSYSERR_NODRIVER;
+}
+
+
+/**************************************************************************
 * 				auxGetNumDevs		[MMSYSTEM.350]
 */
 UINT WINAPI auxGetNumDevs()
@@ -1511,6 +1608,17 @@
 
 
 /**************************************************************************
+* 				mmioRename			[MMSYSTEM.1226]
+*/
+UINT WINAPI mmioRename(LPCSTR szFileName, LPCSTR szNewFileName,
+     MMIOINFO FAR* lpmmioinfo, DWORD dwRenameFlags)
+{
+	printf("mmioRename('%s', '%s', %08X, %08X);\n",
+			szFileName, szNewFileName, lpmmioinfo, dwRenameFlags);
+	return 0;
+}
+
+/**************************************************************************
 * 				DrvOpen				[MMSYSTEM.1100]
 */
 HDRVR DrvOpen(LPSTR lpDriverName, LPSTR lpSectionName, LPARAM lParam)
diff --git a/misc/property.c b/misc/property.c
index 18119c6..92f57a4 100644
--- a/misc/property.c
+++ b/misc/property.c
@@ -62,7 +62,7 @@
 				((LPPROPENTRY)lpProp->lpNextProp)->lpPrevProp = 
 											lpProp->lpPrevProp;
 			if (lpProp->PropName != NULL) free(lpProp->PropName);
-			free(lpProp);
+			GlobalFree(lpProp);
 			GlobalUnlock(wndPtr->hProp);
 			return hOldData;
 			}
diff --git a/misc/shell.c b/misc/shell.c
index 19977ca..d55368d 100644
--- a/misc/shell.c
+++ b/misc/shell.c
@@ -14,7 +14,6 @@
 
 LPKEYSTRUCT	lphRootKey = NULL;
 
-typedef FAR LONG *LPWORD;
 DECLARE_HANDLE(HDROP);
 
 extern HINSTANCE hSysRes;
diff --git a/misc/user.c b/misc/user.c
index ed0045b..cce820e 100644
--- a/misc/user.c
+++ b/misc/user.c
@@ -80,11 +80,9 @@
       /* Create desktop window */
     if (!WIN_CreateDesktopWindow()) return 0;
 
-#if 1
 #ifndef WINELIB
     /* Initialize DLLs */
-    InitializeLoadedDLLs();
-#endif
+    InitializeLoadedDLLs(NULL);
 #endif
         
     return 1;
diff --git a/miscemu/Imakefile b/miscemu/Imakefile
index 4b258c4..65c043f 100644
--- a/miscemu/Imakefile
+++ b/miscemu/Imakefile
@@ -5,11 +5,13 @@
 SRCS = \
 	emulate.c \
 	int10.c \
+	int15.c \
 	int1a.c \
 	int21.c \
 	int25.c \
 	int26.c \
 	int2f.c \
+	int31.c \
 	ioports.c \
 	kernel.c
 
diff --git a/miscemu/int10.c b/miscemu/int10.c
index 9ecc0d5..1d49f5e 100644
--- a/miscemu/int10.c
+++ b/miscemu/int10.c
@@ -3,12 +3,12 @@
 #include "msdos.h"
 #include "wine.h"
 
-static void Barf(struct sigcontext_struct *context)
+void IntBarf(int i, struct sigcontext_struct *context)
 {
-	fprintf(stderr, "int10: unknown/not implemented parameters:\n");
-	fprintf(stderr, "int10: AX %04x, BX %04x, CX %04x, DX %04x, "
+	fprintf(stderr, "int%x: unknown/not implemented parameters:\n", i);
+	fprintf(stderr, "int%x: AX %04x, BX %04x, CX %04x, DX %04x, "
 	       "SI %04x, DI %04x, DS %04x, ES %04x\n",
-	       AX, BX, CX, DX, SI, DI, DS, ES);
+	       i, AX, BX, CX, DX, SI, DI, DS, ES);
 }
 
 int do_int10(struct sigcontext_struct *context)
@@ -31,7 +31,7 @@
 		break;
 		
 	default:
-		Barf(context);
+		IntBarf(0x10, context);
 	};
 	return 1;
 }
diff --git a/miscemu/int15.c b/miscemu/int15.c
new file mode 100644
index 0000000..054a7e3
--- /dev/null
+++ b/miscemu/int15.c
@@ -0,0 +1,16 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include "msdos.h"
+#include "wine.h"
+
+int do_int15(struct sigcontext_struct *context)
+{
+	switch((context->sc_eax >> 8) & 0xff)
+	{
+	case 0xc0:
+		
+	default:
+		IntBarf(0x15, context);
+	};
+	return 1;
+}
diff --git a/miscemu/int1a.c b/miscemu/int1a.c
index ee2f27f..235138e 100644
--- a/miscemu/int1a.c
+++ b/miscemu/int1a.c
@@ -53,7 +53,7 @@
 		break;
 
 	default:
-		fprintf(stderr,"Unable to handle int 0x1A AX %04x\n", context->sc_eax & 0xffffL);
+		IntBarf(0x1a, context);
 		return 1;
 	};
 	return 1;
diff --git a/miscemu/int21.c b/miscemu/int21.c
index 865bd49..3cc4080 100644
--- a/miscemu/int21.c
+++ b/miscemu/int21.c
@@ -1,3 +1,7 @@
+/*
+ * (c) 1993, 1994 Erik Bos
+ */
+
 #include <time.h>
 #include <fcntl.h>
 #include <errno.h>
@@ -7,7 +11,6 @@
 #include <sys/stat.h>
 #include <unistd.h>
 #include <utime.h>
-
 #include "prototypes.h"
 #include "regfunc.h"
 #include "windows.h"
@@ -15,14 +18,17 @@
 #include "msdos.h"
 #include "options.h"
 
-/* #define DEBUG_FIND /* */
-
-static char Copyright[] = "copyright Erik Bos, 1993";
-
 WORD ExtendedError, CodePage = 437;
 BYTE ErrorClass, Action, ErrorLocus;
 BYTE *dta;
 
+struct DosHeap {
+	BYTE dta[256];
+	BYTE InDosFlag;
+	BYTE biosdate[8];
+};
+static struct DosHeap *heap;
+
 extern char TempDirectory[];
 
 static int Error(int e, int class, int el)
@@ -35,6 +41,46 @@
 	return e;
 }
 
+static void errno_to_doserr(void)
+{
+	switch (errno) {
+		case EAGAIN:
+			Error (ShareViolation, EC_Temporary, EL_Unknown);
+			break;
+		case EBADF:
+			Error (InvalidHandle, EC_AppError, EL_Unknown);
+			break;
+		case ENOSPC:
+			Error (DiskFull, EC_MediaError, EL_Disk);
+			break;				
+		case EACCES:
+		case EPERM:
+		case EROFS:
+			Error (WriteProtected, EC_AccessDenied, EL_Unknown);
+			break;
+		case EBUSY:
+			Error (LockViolation, EC_AccessDenied, EL_Unknown);
+			break;		
+		case ENOENT:
+			Error (FileNotFound, EC_NotFound, EL_Unknown);
+			break;				
+		case EISDIR:
+			Error (CanNotMakeDir, EC_AccessDenied, EL_Unknown);
+			break;
+		case ENFILE:
+		case EMFILE:
+			Error (NoMoreFiles, EC_MediaError, EL_Unknown);
+			break;
+		case EEXIST:
+			Error (FileExists, EC_Exists, EL_Disk);
+			break;				
+		default:
+			fprintf(stderr, "int21: unknown errno %d!\n", errno);
+			Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
+			break;
+	}
+}
+
 static void Barf(struct sigcontext_struct *context)
 {
 	fprintf(stderr, "int21: unknown/not implemented parameters:\n");
@@ -92,10 +138,10 @@
 	int drive;
 	long size,available;
 
-	if (!(EDX & 0xffL))
+	if (!(EDX & 0xff))
 		drive = DOS_GetDefaultDrive();
 	else
-		drive = (EDX & 0xffL) - 1;
+		drive = (EDX & 0xff) - 1;
 	
 	if (!DOS_ValidDrive(drive)) {
 		Error(InvalidDrive, EC_MediaError , EL_Disk);
@@ -109,33 +155,11 @@
 		return;
 	}
 
-	EAX = (EAX & 0xffff0000L) | 4;	
-	ECX = (ECX & 0xffff0000L) | 512;
+	EAX = (EAX & 0xffff0000) | 4;	
+	ECX = (ECX & 0xffff0000) | 512;
 
-	EBX = (EBX & 0xffff0000L) | (available / (CX * AX));
-	EDX = (EDX & 0xffff0000L) | (size / (CX * AX));
-	Error (0,0,0);
-}
-
-static void SetDefaultDrive(struct sigcontext_struct *context)
-{
-	int drive;
-
-	drive = EDX & 0xffL;
-
-	if (!DOS_ValidDrive(drive)) {
-		Error (InvalidDrive, EC_MediaError, EL_Disk);
-		return;
-	} else {
-		DOS_SetDefaultDrive(drive);
-		EAX = (EAX &0xffffff00L) | MAX_DOS_DRIVES; 
-		Error (0,0,0);
-	}
-}
-
-static void GetDefaultDrive(struct sigcontext_struct *context)
-{
-	EAX = (EAX & 0xffffff00L) | DOS_GetDefaultDrive();
+	EBX = (EBX & 0xffff0000) | (available / (CX * AX));
+	EDX = (EDX & 0xffff0000) | (size / (CX * AX));
 	Error (0,0,0);
 }
 
@@ -148,9 +172,9 @@
 	drive = EDX & 0xffL;
 	
 	if (!DOS_ValidDrive(drive)) {
-		EAX = (EAX & 0xffff0000L) | 4;
-		ECX = (ECX & 0xffff0000L) | 512;
-		EDX = (EDX & 0xffff0000L);
+		EAX = (EAX & 0xffff0000) | 4;
+		ECX = (ECX & 0xffff0000) | 512;
+		EDX = (EDX & 0xffff0000);
 		Error (InvalidDrive, EC_MediaError, EL_Disk);
 		return;
 	}
@@ -161,9 +185,9 @@
 		return;
 	}
 	
-	EAX = (EAX & 0xffff0000L) | 4;	
-	ECX = (ECX & 0xffff0000L) | 512;
-	EDX = (EDX & 0xffff0000L) | (size / (CX * AX));
+	EAX = (EAX & 0xffff0000) | 4;	
+	ECX = (ECX & 0xffff0000) | 512;
+	EDX = (EDX & 0xffff0000) | (size / (CX * AX));
 
 	mediaID = 0xf0;
 
@@ -181,7 +205,7 @@
 static void GetDrivePB(struct sigcontext_struct *context)
 {
 	Error (InvalidDrive, EC_MediaError, EL_Disk);
-	EAX = (EAX & 0xffff0000L) | 0xffL; 
+	EAX = (EAX & 0xffff0000) | 0xffL; 
 		/* I'm sorry but I only got networked drives :-) */
 }
 
@@ -191,48 +215,30 @@
 	int size;
 
 	/* can't read from stdout / stderr */
-
 	if ((BX == 1) || (BX == 2)) {
 		Error (InvalidHandle, EL_Unknown, EC_Unknown);
-		EAX = (EAX & 0xffff0000L) | InvalidHandle;
+		EAX = (EAX & 0xffff0000) | InvalidHandle;
 		SetCflag;
 		return;
 	}
 
 	ptr = pointer (DS,DX);
-
 	if (BX == 0) {
 		*ptr = EOF;
 		Error (0,0,0);
-		EAX = (EAX & 0xffff0000L) | 1;
+		EAX = (EAX & 0xffff0000) | 1;
 		ResetCflag;
 		return;
 	} else {
 		size = read(BX, ptr, CX);
-		if (size == 0) {
-			Error (ReadFault, EC_Unknown, EL_Unknown);
-			EAX = (EAX & 0xffffff00L) | ExtendedError;
-			return;
-		}
-
 		if (size == -1) {
-			switch (errno) {
-				case EAGAIN:
-					Error (ShareViolation, EC_Temporary, EL_Unknown);
-					break;
-				case EBADF:
-					Error (InvalidHandle, EC_AppError, EL_Unknown);
-					break;
-				default:
-					Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-					break;
-			}
-			EAX = (EAX & 0xffffff00L) | ExtendedError;
+			errno_to_doserr();
+			EAX = (EAX & 0xffffff00) | ExtendedError;
 			SetCflag;
 			return;
 		}		
 		Error (0,0,0);
-		EAX = (EAX & 0xffff0000L) | size;
+		EAX = (EAX & 0xffff0000) | size;
 		ResetCflag;
 	}
 }
@@ -258,75 +264,33 @@
 		fflush(stderr);
 
 		Error (0,0,0);
-		EAX = (EAX & 0xffffff00L) | CX;
+		EAX = (EAX & 0xffffff00) | CX;
 		ResetCflag;
 	} else {
 		size = write(BX, ptr , CX);
 		if (size == 0) {
 			Error (WriteFault, EC_Unknown, EL_Unknown);
-			EAX = (EAX & 0xffffff00L) | ExtendedError;
+			EAX = (EAX & 0xffffff00) | ExtendedError;
 			return;
 		}
 
 		if (size == -1) {
-			switch (errno) {
-				case EAGAIN:
-					Error (ShareViolation, EC_Temporary, EL_Unknown);
-					break;
-				case EBADF:
-					Error (InvalidHandle, EC_AppError, EL_Unknown);
-					break;
-				case ENOSPC:
-					Error (DiskFull, EC_MediaError, EL_Disk);
-					break;				
-				default:
-					Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-					break;
-			}
-			EAX = (EAX & 0xffffff00L) | ExtendedError;
+			errno_to_doserr();
+			EAX = (EAX & 0xffffff00) | ExtendedError;
 			SetCflag;
 			return;
 		}		
 		Error (0,0,0);
-		EAX = (EAX & 0xffff0000L) | size;
+		EAX = (EAX & 0xffff0000) | size;
 		ResetCflag;
 	}
 }
 
-static void UnlinkFile(struct sigcontext_struct *context)
-{
-	if (unlink( GetUnixFileName( pointer(DS,DX)) ) == -1) {
-		switch (errno) {
-			case EACCES:
-			case EPERM:
-			case EROFS:
-				Error (WriteProtected, EC_AccessDenied, EL_Unknown);
-				break;
-			case EBUSY:
-				Error (LockViolation, EC_AccessDenied, EL_Unknown);
-				break;		
-			case EAGAIN:
-				Error (ShareViolation, EC_Temporary, EL_Unknown);
-				break;
-			case ENOENT:
-				Error (FileNotFound, EC_NotFound, EL_Unknown);
-				break;				
-			default:
-				Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-				break;
-		}
-		EAX = (EAX & 0xffffff00L) | ExtendedError;			SetCflag;
-		return;
-	}		
-	Error (0,0,0);
-	ResetCflag;
-}
-
 static void SeekFile(struct sigcontext_struct *context)
 {
-	int status, fileoffset;
+	off_t status, fileoffset;
 	
-	switch (EAX & 0xffL) {
+	switch (EAX & 0xff) {
 		case 1: fileoffset = SEEK_CUR;
 			break;
 		case 2: fileoffset = SEEK_END;
@@ -337,65 +301,45 @@
 		}
 	status = lseek(BX, (CX * 0x100) + DX, fileoffset);
 	if (status == -1) {
-		switch (errno) {
-			case EBADF:
-				Error (InvalidHandle, EC_AppError, EL_Unknown);
-				break;
-			case EINVAL:
-				Error (DataInvalid, EC_AppError, EL_Unknown);
-				break;
-			default:
-				Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-				break;
-		}
-		EAX = (EAX & 0xffffff00L) | ExtendedError;			SetCflag;
+		errno_to_doserr();
+		EAX = (EAX & 0xffffff00) | ExtendedError;			SetCflag;
 		return;
 	}		
 	Error (0,0,0);
-	ResetCflag;
-}
-
-static void GetFileAttributes(struct sigcontext_struct *context)
-{
-	EAX &= 0xfffff00L;
-	ResetCflag;
-}
-
-static void SetFileAttributes(struct sigcontext_struct *context)
-{
+	EAX = (EAX & 0xffff0000L) | (status & 0xffff);
+	EDX = (EDX & 0xffff0000L) | ((status >> 16) & 0xffff);
+	
 	ResetCflag;
 }
 
 static void ioctlGetDeviceInfo(struct sigcontext_struct *context)
 {
-    WORD handle = EBX & 0xffff;
-    
-    switch (handle) 
-    {
-      case 0:
-      case 1:
-      case 2:
-	EDX = (EDX & 0xffff0000) | 0x80d3;
-	break;
-	
-      default:
-	{
-	    struct stat sbuf;
+	WORD handle = EBX & 0xffff;
+
+	switch (handle) {
+		case 0:
+		case 1:
+		case 2:
+			EDX = (EDX & 0xffff0000) | 0x80d3;
+			break;
+
+		default:
+		{
+		    struct stat sbuf;
 	    
-	    if (fstat(handle, &sbuf) < 0)
-	    {
-		Barf(context);
-		EDX = (EDX & 0xffff0000) | 0x50;
-		SetCflag;
-		return;
-	    }
+		    if (fstat(handle, &sbuf) < 0)
+		    {
+			IntBarf(0x21, context);
+			EDX = (EDX & 0xffff0000) | 0x50;
+			SetCflag;
+			return;
+		    }
 	    
-	    /* This isn't the right answer, but should be close enough. */
-	    EDX = (EDX & 0xffff0000) | 0x0943;
+		    /* This isn't the right answer, but should be close enough. */
+		    EDX = (EDX & 0xffff0000) | 0x0943;
+		}
 	}
-    }
-    
-    ResetCflag;
+	ResetCflag;
 }
 
 static void ioctlGenericBlkDevReq(struct sigcontext_struct *context)
@@ -403,16 +347,16 @@
 	BYTE *dataptr = pointer(DS, DX);
 	int drive;
 
-	if (!(EBX & 0xffL))
+	if (!(EBX & 0xff))
 		drive = DOS_GetDefaultDrive();
 	else
-		drive = (EBX & 0xffL) - 1;
+		drive = (EBX & 0xff) - 1;
 
-	if ((ECX & 0xff00L) != 0x0800) {
-		Barf(context);
+	if ((ECX & 0xff00) != 0x0800) {
+		IntBarf(0x21, context);
 		return;
 	}
-	switch (ECX & 0xffL) {
+	switch (ECX & 0xff) {
 		case 0x60: /* get device parameters */
 			   /* used by w4wgrp's winfile */
 			dataptr[0] = 0x04;
@@ -430,20 +374,14 @@
 				setword(&dataptr[4], 80); /* # of cylinders */
 			}
 			CreateBPB(drive, &dataptr[7]);			
-			EAX = (EAX & 0xfffff00L);
+			EAX = (EAX & 0xfffff00);
 			ResetCflag;
 			return;
 		default:
-			Barf(context);
+			IntBarf(0x21, context);
 	}
 }
 
-static void DupeFileHandle(struct sigcontext_struct *context)
-{
-	EAX = (EAX & 0xffff0000L) | dup(BX);
-	ResetCflag;
-}
-
 static void GetSystemDate(struct sigcontext_struct *context)
 {
 	struct tm *now;
@@ -452,9 +390,9 @@
 	ltime = time(NULL);
 	now = localtime(&ltime);
 
-	ECX = (ECX & 0xffff0000L) | (now->tm_year + 1900);
-	EDX = (EDX & 0xffff0000L) | ((now->tm_mon + 1) << 8) | now->tm_mday;
-	EAX = (EAX & 0xffff0000L) | now->tm_wday;
+	ECX = (ECX & 0xffff0000) | (now->tm_year + 1900);
+	EDX = (EDX & 0xffff0000) | ((now->tm_mon + 1) << 8) | now->tm_mday;
+	EAX = (EAX & 0xffff0000) | now->tm_wday;
 }
 
 static void GetSystemTime(struct sigcontext_struct *context)
@@ -465,23 +403,15 @@
 	ltime = time(NULL);
 	now = localtime(&ltime);
 	 
-	ECX = (ECX & 0xffffff00L) | (now->tm_hour << 8) | now->tm_min;
-	EDX = (EDX & 0xffffff00L) | now->tm_sec << 8;
+	ECX = (ECX & 0xffffff00) | (now->tm_hour << 8) | now->tm_min;
+	EDX = (EDX & 0xffffff00) | now->tm_sec << 8;
 }
 
 static void GetExtendedErrorInfo(struct sigcontext_struct *context)
 {
-	EAX = (EAX & 0xffffff00L) | ExtendedError;
-	EBX = (EBX & 0xffff0000L) | (0x100 * ErrorClass) | Action;
-	ECX = (ECX & 0xffff00ffL) | (0x100 * ErrorLocus);
-}
-
-static void GetInDosFlag(struct sigcontext_struct *context)
-{
-	const BYTE InDosFlag = 0;
-	
-	ES  = (ES & 0xffff0000L) | segment(InDosFlag);
-	EBX = (EBX & 0xffff0000L) | offset(InDosFlag);
+	EAX = (EAX & 0xffffff00) | ExtendedError;
+	EBX = (EBX & 0xffff0000) | (ErrorClass << 8) | Action;
+	ECX = (ECX & 0xffff00ff) | (ErrorLocus << 8);
 }
 
 static void CreateFile(struct sigcontext_struct *context)
@@ -489,96 +419,60 @@
 	int handle;
 
 	if ((handle = open(GetUnixFileName( pointer(DS,DX)), O_CREAT | O_TRUNC)) == -1) {
-		switch (errno) {
-			case EACCES:
-			case EPERM:
-			case EROFS:
-				Error (WriteProtected, EC_AccessDenied, EL_Unknown);
-				break;
-			case EISDIR:
-				Error (CanNotMakeDir, EC_AccessDenied, EL_Unknown);
-				break;
-			case ENFILE:
-			case EMFILE:
-				Error (NoMoreFiles, EC_MediaError, EL_Unknown);
-			case EEXIST:
-				Error (FileExists, EC_Exists, EL_Disk);
-				break;				
-			case ENOSPC:
-				Error (DiskFull, EC_MediaError, EL_Disk);
-				break;				
-			default:
-				Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-				break;
-			}			
-		EAX = (EAX & 0xffffff00L) | ExtendedError;
+		errno_to_doserr();
+		EAX = (EAX & 0xffffff00) | ExtendedError;
 		SetCflag;
 		return;
 		}			
 	Error (0,0,0);
-	EBX = (EBX & 0xffff0000L) | handle;
-	EAX = (EAX & 0xffffff00L) | NoError;
+	EBX = (EBX & 0xffff0000) | handle;
+	EAX = (EAX & 0xffffff00) | NoError;
 	ResetCflag;
 }
 
 static void OpenExistingFile(struct sigcontext_struct *context)
 {
 	int handle;
+	int mode;
+	
+	switch (AX & 0x0007)
+	{
+	  case 0:
+	    mode = O_RDONLY;
+	    break;
+	    
+	  case 1:
+	    mode = O_WRONLY;
+	    break;
+	    
+	  default:
+	    mode = O_RDWR;
+	    break;
+	}
 
 	fprintf(stderr,"OpenExistingFile (%s)\n", pointer(DS,DX));
 	
-	if ((handle = open(GetUnixFileName(pointer(DS,DX)), O_RDWR)) == -1) {
-		switch (errno) {
-			case EACCES:
-			case EPERM:
-			case EROFS:
-				Error (WriteProtected, EC_AccessDenied, EL_Unknown);
-				break;
-			case EISDIR:
-				Error (CanNotMakeDir, EC_AccessDenied, EL_Unknown);
-				break;
-			case ENFILE:
-			case EMFILE:
-				Error (NoMoreFiles, EC_MediaError, EL_Unknown);
-			case EEXIST:
-				Error (FileExists, EC_Exists, EL_Disk);
-				break;				
-			case ENOSPC:
-				Error (DiskFull, EC_MediaError, EL_Disk);
-				break;				
-			case ENOENT:
-				Error (FileNotFound, EC_MediaError, EL_Disk);
-				break;
-			default:
-				Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-				break;
-		}
-		EAX = (EAX & 0xffffff00L) | ExtendedError;
+	if ((handle = open(GetUnixFileName(pointer(DS,DX)), mode)) == -1) {
+		errno_to_doserr();
+		EAX = (EAX & 0xffffff00) | ExtendedError;
 		SetCflag;
 		return;
 	}		
 	Error (0,0,0);
-	EAX = (EAX & 0xffff0000L) | handle;
+	EAX = (EBX & 0xffff0000) | handle;
 	ResetCflag;
 }
 
 static void CloseFile(struct sigcontext_struct *context)
 {
 	if (close(BX) == -1) {
-		switch (errno) {
-			case EBADF:
-				Error (InvalidHandle, EC_AppError, EL_Unknown);
-				break;
-			default:
-				Error (GeneralFailure, EC_SystemFailure, EL_Unknown);
-				break;
-		}
-		EAX = (EAX & 0xffffff00L) | ExtendedError;
+		errno_to_doserr();
+		EAX = (EAX & 0xffffff00) | ExtendedError;
 		SetCflag;
 		return;
-	}		
+	}
 	Error (0,0,0);
-	EAX = (EAX & 0xffffff00L) | NoError;
+	EAX = (EAX & 0xffffff00) | NoError;
 	ResetCflag;
 }
 
@@ -596,13 +490,6 @@
 	ResetCflag;
 }
 
-static void GetTrueFileName(struct sigcontext_struct *context)
-{
-	fprintf(stderr,"int21: GetTrueFileName of %s\n", pointer(DS,SI) );
-	
-	strncpy(pointer(ES,DI), pointer(DS,SI), strlen(pointer(DS,SI)) & 0x7f);
-	ResetCflag;
-}
 
 static void MakeDir(struct sigcontext_struct *context)
 {
@@ -611,13 +498,13 @@
 	fprintf(stderr,"int21: makedir %s\n", pointer(DS,DX) );
 	
 	if ((dirname = GetUnixFileName( pointer(DS,DX) ))== NULL) {
-		EAX = (EAX & 0xffffff00L) | CanNotMakeDir;
+		EAX = (EAX & 0xffffff00) | CanNotMakeDir;
 		SetCflag;
 		return;
 	}
 
 	if (mkdir(dirname,0) == -1) {
-		EAX = (EAX & 0xffffff00L) | CanNotMakeDir;
+		EAX = (EAX & 0xffffff00) | CanNotMakeDir;
 		SetCflag;
 		return;
 	}
@@ -644,96 +531,40 @@
 	fprintf(stderr,"int21: removedir %s\n", pointer(DS,DX) );
 
 	if ((dirname = GetUnixFileName( pointer(DS,DX) ))== NULL) {
-		EAX = (EAX & 0xffffff00L) | CanNotMakeDir;
+		EAX = (EAX & 0xffffff00) | CanNotMakeDir;
 		SetCflag;
 		return;
 	}
 
 /*
 	if (strcmp(unixname,DosDrives[drive].CurrentDirectory)) {
-		EAX = (EAX & 0xffffff00L) | CanNotRemoveCwd;
+		EAX = (EAX & 0xffffff00) | CanNotRemoveCwd;
 		SetCflag;
 	}
 */	
 	if (rmdir(dirname) == -1) {
-		EAX = (EAX & 0xffffff00L) | CanNotMakeDir; 
+		EAX = (EAX & 0xffffff00) | CanNotMakeDir; 
 		SetCflag;
 	} 
 	ResetCflag;
 }
 
-static void AllocateMemory(struct sigcontext_struct *context)
-{
-	char *ptr;
-	
-	fprintf(stderr,"int21: malloc %d bytes\n", BX * 0x10 );
-	
-/*	if ((ptr = (void *) memalign((size_t) (BX * 0x10), 0x10)) == NULL) {
-		EAX = (EAX & 0xffffff00L) | OutOfMemory;
-		EBX = (EBX & 0xffffff00L);
-		SetCflag;
-	}
-	fprintf(stderr,"int21: malloc (ptr = %d)\n", ptr );
-
-	EAX = (EAX & 0xffff0000L) | segment(ptr);
-*/
-	Barf(context);
-	SetCflag;
-}
-
-static void FreeMemory(struct sigcontext_struct *context)
-{
-	fprintf(stderr,"int21: freemem (ptr = %d)\n", ES * 0x10 );
-/*
-	free((void *)(ES * 0x10));
-*/	Barf(context);
-	ResetCflag;
-}
-
-static void ResizeMemoryBlock(struct sigcontext_struct *context)
-{
-	char *ptr;
-
-	fprintf(stderr,"int21: realloc (ptr = %d)\n", ES * 0x10 );
-	
-/*	if ((ptr = (void *) realloc((void *)(ES * 0x10), (size_t) BX * 0x10)) == NULL) {
-		EAX = (EAX & 0xffffff00L) | OutOfMemory;
-		EBX = (EBX & 0xffffff00L);
-		SetCflag;
-	}
-	EBX = (EBX & 0xffff0000L) | segment(ptr);
-*/	Barf(context);
-	SetCflag;
-}
-
 static void ExecProgram(struct sigcontext_struct *context)
 {
 	execl("wine", GetUnixFileName( pointer(DS,DX)) );
 }
 
-static void GetReturnCode(struct sigcontext_struct *context)
-{
-	EAX = (EAX & 0xffffff00L) | NoError; /* normal exit */
-}
-
 static void FindNext(struct sigcontext_struct *context)
 {
 	struct dosdirent *dp;
 	
-#ifdef DEBUG_FIND
-	fprintf(stderr, "FindNext: ");
-#endif
-	
-	dp = *(struct dosdirent **)(dta + 0x0d);
+	dp = (struct dosdirent *)(dta + 0x0d);
 
 	do {
 		if ((dp = DOS_readdir(dp)) == NULL) {
 			Error(NoMoreFiles, EC_MediaError , EL_Disk);
-			EAX = (EAX & 0xffffff00L) | NoMoreFiles;
+			EAX = (EAX & 0xffffff00) | NoMoreFiles;
 			SetCflag;
-#ifdef DEBUG_FIND
-			fprintf(stderr, "\n");
-#endif
 			return;
 		}
 	} while (*(dta + 0x0c) != dp->attribute);
@@ -743,14 +574,8 @@
 	setdword(&dta[0x1a], dp->filesize);
 	strncpy(dta + 0x1e, dp->filename, 13);
 
-	EAX = (EAX & 0xffffff00L);
+	EAX = (EAX & 0xffffff00);
 	ResetCflag;
-
-#ifdef DEBUG_FIND
-	fprintf(stderr, 
-		"DTA: drive %c, template %11.11s, size %d, name %-13.13s\n",
-		dta[0] + 'A', &dta[1], *(LONG *)(&dta[0x1a]), &dta[0x1e]);
-#endif
 	return;
 }
 
@@ -797,16 +622,6 @@
 	FindNext(context);
 }
 
-static void GetSysVars(struct sigcontext_struct *context)
-{
-	/* return a null pointer, to encourage anyone who tries to
-	   use the pointer */
-
-	ES = 0x0;
-	EBX = (EBX & 0xffff0000L);
-	Barf(context);
-}
-
 static void GetFileDateTime(struct sigcontext_struct *context)
 {
 	char *filename;
@@ -814,7 +629,7 @@
 	struct tm *now;
 
 	if ((filename = GetUnixFileName( pointer(DS,DX) ))== NULL) {
-		EAX = (EAX & 0xffffff00L) | FileNotFound;
+		EAX = (EAX & 0xffffff00) | FileNotFound;
 		SetCflag;
 		return;
 	}
@@ -822,8 +637,8 @@
 	 	
 	now = localtime (&filestat.st_mtime);
 	
-	ECX = (ECX & 0xffff0000L) | ((now->tm_hour * 0x2000) + (now->tm_min * 0x20) + now->tm_sec/2);
-	EDX = (EDX & 0xffff0000L) | ((now->tm_year * 0x200) + (now->tm_mon * 0x20) + now->tm_mday);
+	ECX = (ECX & 0xffff0000) | ((now->tm_hour * 0x2000) + (now->tm_min * 0x20) + now->tm_sec/2);
+	EDX = (EDX & 0xffff0000) | ((now->tm_year * 0x200) + (now->tm_mon * 0x20) + now->tm_mday);
 
 	ResetCflag;
 }
@@ -854,14 +669,14 @@
 	handle = open(GetUnixFileName(temp), O_CREAT | O_TRUNC | O_RDWR);
 
 	if (handle == -1) {
-		EAX = (EAX & 0xffffff00L) | WriteProtected;
+		EAX = (EAX & 0xffffff00) | WriteProtected;
 		SetCflag;
 		return;
 	}
 
 	strcpy(pointer(DS,DX), temp);
 	
-	EAX = (EAX & 0xffff0000L) | handle;
+	EAX = (EAX & 0xffff0000) | handle;
 	ResetCflag;
 }
 
@@ -870,22 +685,12 @@
 	int handle;
 	
 	if ((handle = open(GetUnixFileName( pointer(DS,DX) ), O_CREAT | O_TRUNC | O_RDWR)) == -1) {
-		EAX = (EAX & 0xffffff00L) | WriteProtected;
+		EAX = (EAX & 0xffffff00) | WriteProtected;
 		SetCflag;
 		return;
 	}
 
-	EAX = (EAX & 0xffff0000L) | handle;
-	ResetCflag;
-}
-
-static void FileLock(struct sigcontext_struct *context)
-{
-	fprintf(stderr, "int21: flock()\n");
-}
-
-static void GetExtendedCountryInfo(struct sigcontext_struct *context)
-{
+	EAX = (EAX & 0xffff0000) | handle;
 	ResetCflag;
 }
 
@@ -893,13 +698,13 @@
 {
 	int drive;
 
-	if ((EDX & 0xffL) == 0)
+	if ((EDX & 0xff) == 0)
 		drive = DOS_GetDefaultDrive();
 	else
-		drive = (EDX & 0xffL)-1;
+		drive = (EDX & 0xff)-1;
 
 	if (!DOS_ValidDrive(drive)) {
-		EAX = (EAX & 0xffffff00L) | InvalidDrive;
+		EAX = (EAX & 0xffffff00) | InvalidDrive;
 		SetCflag;
 		return;
 	}
@@ -908,24 +713,19 @@
 	ResetCflag;
 }
 
-static void GetCurrentPSP(struct sigcontext_struct *context)
-{
-	Barf(context);
-}
-
 static void GetDiskSerialNumber(struct sigcontext_struct *context)
 {
 	int drive;
 	BYTE *dataptr = pointer(DS, DX);
 	DWORD serialnumber;
 	
-	if ((EBX & 0xffL) == 0)
+	if ((EBX & 0xff) == 0)
 		drive = DOS_GetDefaultDrive();
 	else
-		drive = (EBX & 0xffL) - 1;
+		drive = (EBX & 0xff) - 1;
 
 	if (!DOS_ValidDrive(drive)) {
-		EAX = (EAX & 0xffffff00L) |InvalidDrive;
+		EAX = (EAX & 0xffffff00) |InvalidDrive;
 		SetCflag;
 		return;
 	}
@@ -937,7 +737,7 @@
 	strncpy(dataptr + 6, DOS_GetVolumeLabel(drive), 8);
 	strncpy(dataptr + 0x11, "FAT16   ", 8);
 	
-	EAX = (EAX & 0xffffff00L);
+	EAX = (EAX & 0xffffff00);
 	ResetCflag;
 }
 
@@ -947,13 +747,13 @@
 	BYTE *dataptr = pointer(DS, DX);
 	DWORD serialnumber;
 
-	if ((EBX & 0xffL) == 0)
+	if ((EBX & 0xff) == 0)
 		drive = DOS_GetDefaultDrive();
 	else
-		drive = (EBX & 0xffL) - 1;
+		drive = (EBX & 0xff) - 1;
 
 	if (!DOS_ValidDrive(drive)) {
-		EAX = (EAX & 0xffffff00L) | InvalidDrive;
+		EAX = (EAX & 0xffffff00) | InvalidDrive;
 		SetCflag;
 		return;
 	}
@@ -962,7 +762,7 @@
 			(dataptr[4] << 24);
 
 	DOS_SetSerialNumber(drive, serialnumber);
-	EAX = (EAX & 0xffffff00L) | 1L;
+	EAX = (EAX & 0xffffff00) | 1L;
 	ResetCflag;
 }
 
@@ -1003,11 +803,11 @@
 				strncpy(dta, DOS_GetVolumeLabel(drive), 8);
 			*(dta + 0x0b) = FA_DIREC;
 
-			EAX = (EAX & 0xffffff00L);
+			EAX = (EAX & 0xffffff00);
 			return;
 		}
 	}
-	Barf(context);
+	IntBarf(0x21, context);
 }
 
 static void DeleteFileFCB(struct sigcontext_struct *context)
@@ -1033,7 +833,7 @@
 
 	if ((dp = DOS_opendir(temp)) == NULL) {
 		Error(InvalidDrive, EC_MediaError , EL_Disk);
-		EAX = (EAX & 0xffffff00L) | 0xffL;
+		EAX = (EAX & 0xffffff00) | 0xffL;
 		return;
 	}
 
@@ -1049,7 +849,7 @@
 		/* unlink(GetUnixFileName(temp)); */
 	}
 	DOS_closedir(dp);
-	EAX = (EAX & 0xffffff00L);
+	EAX = (EAX & 0xffffff00);
 }
 
 static void RenameFileFCB(struct sigcontext_struct *context)
@@ -1075,7 +875,7 @@
 
 	if ((dp = DOS_opendir(temp)) == NULL) {
 		Error(InvalidDrive, EC_MediaError , EL_Disk);
-		EAX = (EAX & 0xffffff00L) | 0xffL;
+		EAX = (EAX & 0xffffff00) | 0xffL;
 		return;
 	}
 
@@ -1094,7 +894,7 @@
 		fprintf(stderr, "int21: renamefile %s -> %s\n", oldname, newname);
 	}
 	DOS_closedir(dp);
-	EAX = (EAX & 0xffffff00L);
+	EAX = (EAX & 0xffffff00);
 }
 
 /************************************************************************/
@@ -1152,7 +952,7 @@
 	  case 0x28: /* RANDOM BLOCK WRITE TO FCB FILE */
 	  case 0x29: /* PARSE FILENAME INTO FCB */
 	  case 0x2e: /* SET VERIFY FLAG */
-	    Barf(context);
+	    IntBarf(0x21, context);
 	    break;
 
 	  case 0x18: /* NULL FUNCTIONS FOR CP/M COMPATIBILITY */
@@ -1165,9 +965,8 @@
 			"SWITCHAR" - SET SWITCH CHARACTER
 			"AVAILDEV" - SPECIFY \DEV\ PREFIX USE */
 	  case 0x54: /* GET VERIFY FLAG */
-	  case 0x61: /* UNUSED */
 	  case 0x6b: /* NULL FUNCTION */
-            Barf(context);
+            IntBarf(0x21, context);
 	    EAX &= 0xff00;
 	    break;
 	
@@ -1176,8 +975,15 @@
             break;
 
 	  case 0x0e: /* SELECT DEFAULT DRIVE */
-	    SetDefaultDrive(context);
-	    break;
+		if (!DOS_ValidDrive(EDX & 0xff)) {
+			Error (InvalidDrive, EC_MediaError, EL_Disk);
+			return;
+		} else {
+			DOS_SetDefaultDrive(EDX & 0xff);
+			EAX = (EAX &0xffffff00) | MAX_DOS_DRIVES; 
+			Error(0,0,0);
+		}
+		break;
 
 	  case 0x11: /* FIND FIRST MATCHING FILE USING FCB */
             FindFirstFCB(context);
@@ -1192,7 +998,8 @@
             break;
 
 	  case 0x19: /* GET CURRENT DEFAULT DRIVE */
-	    GetDefaultDrive(context);
+		EAX = (EAX & 0xffffff00) | DOS_GetDefaultDrive();
+		Error (0,0,0);
 	    break;
 	    
 	  case 0x1a: /* SET DISK TRANSFER AREA ADDRESS */
@@ -1226,17 +1033,17 @@
 
 	  case 0x2f: /* GET DISK TRANSFER AREA ADDRESS */
             ES = segment(dta);
-            EBX = (EBX & 0xffff0000L) | offset(dta);
+            EBX = (EBX & 0xffff0000) | offset(dta);
             break;
             
 	  case 0x30: /* GET DOS VERSION */
-	    EAX = (EAX & 0xffff0000L) | DOSVERSION;
-	    EBX = (EBX & 0xffff0000L) | 0x0012;     /* 0x123456 is Wine's serial # */
-	    ECX = (ECX & 0xffff0000L) | 0x3456;
+	    EAX = (EAX & 0xffff0000) | DOSVERSION;
+	    EBX = (EBX & 0xffff0000) | 0x0012;     /* 0x123456 is Wine's serial # */
+	    ECX = (ECX & 0xffff0000) | 0x3456;
 	    break;
 
 	  case 0x31: /* TERMINATE AND STAY RESIDENT */
-            Barf(context);
+            IntBarf(0x21, context);
 	    break;
 
 	  case 0x32: /* GET DOS DRIVE PARAMETER BLOCK FOR SPECIFIC DRIVE */
@@ -1246,7 +1053,7 @@
 	  case 0x33: /* MULTIPLEXED */
 	    switch (EAX & 0xff) {
 	      case 0x00: /* GET CURRENT EXTENDED BREAK STATE */
-		if (!(EAX & 0xffL)) 
+		if (!(EAX & 0xff)) 
 		    EDX &= 0xff00L;
 		break;
 
@@ -1258,7 +1065,7 @@
 		break;
 
 	      case 0x05: /* GET BOOT DRIVE */
-		EDX = (EDX & 0xff00L) | 2;
+		EDX = (EDX & 0xff00) | 2;
 		/* c: is Wine's bootdrive */
 		break;
 				
@@ -1268,13 +1075,14 @@
 		break;
 
 	      default:
-		Barf(context);
+		IntBarf(0x21, context);
 		break;			
 	    }
 	    break;	
 	    
 	  case 0x34: /* GET ADDRESS OF INDOS FLAG */
-	    GetInDosFlag(context);
+		ES  = (ES & 0xffff0000) | segment(heap->InDosFlag);
+		EBX = (EBX & 0xffff0000) | offset(heap->InDosFlag);
 	    break;
 
 	  case 0x35: /* GET INTERRUPT VECTOR */
@@ -1328,21 +1136,29 @@
 	    break;
 	
 	  case 0x41: /* "UNLINK" - DELETE FILE */
-	    UnlinkFile(context);
-	    break;
+		if (unlink( GetUnixFileName( pointer(DS,DX)) ) == -1) {
+			errno_to_doserr();
+			EAX = (EAX & 0xffffff00) | ExtendedError;
+			SetCflag;
+			return;
+		}		
+		Error(0,0,0);
+		ResetCflag;
+		break;
 	
 	  case 0x42: /* "LSEEK" - SET CURRENT FILE POSITION */
 	    SeekFile(context);
 	    break;
 	    
 	  case 0x43: /* FILE ATTRIBUTES */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x00:
-		GetFileAttributes(context);
+			EAX &= 0xfffff00L;
+			ResetCflag;
 		break;
 	      case 0x01:
-		SetFileAttributes(context);
+			ResetCflag;
 		break;
 	    }
 	    break;
@@ -1359,33 +1175,27 @@
                 break;
                 
 	      default:
-                Barf(context);
+                IntBarf(0x21, context);
 		break;
 	    }
 	    break;
 
-
 	  case 0x45: /* "DUP" - DUPLICATE FILE HANDLE */
 	  case 0x46: /* "DUP2", "FORCEDUP" - FORCE DUPLICATE FILE HANDLE */
-	    DupeFileHandle(context);
+		EAX = (EAX & 0xffff0000) | dup(BX);
+		ResetCflag;
 	    break;
 
 	  case 0x47: /* "CWD" - GET CURRENT DIRECTORY */	
 	    GetCurrentDirectory(context);
-	    EAX = (EAX & 0xffff0000L) | 0x0100; 
+	    EAX = (EAX & 0xffff0000) | 0x0100; 
 	    /* intlist: many Microsoft products for Windows rely on this */
 	    break;
 	
 	  case 0x48: /* ALLOCATE MEMORY */
-	    AllocateMemory(context);
-	    break;
-	
 	  case 0x49: /* FREE MEMORY */
-	    FreeMemory(context);
-	    break;
-	
 	  case 0x4a: /* RESIZE MEMORY BLOCK */
-	    ResizeMemoryBlock(context);
+	    IntBarf(0x21, context);
 	    break;
 	
 	  case 0x4b: /* "EXEC" - LOAD AND/OR EXECUTE PROGRAM */
@@ -1393,11 +1203,11 @@
 	    break;		
 	
 	  case 0x4c: /* "EXIT" - TERMINATE WITH RETURN CODE */
-	    exit(EAX & 0xffL);
+	    exit(EAX & 0xff);
 	    break;
 		
 	  case 0x4d: /* GET RETURN CODE */
-	    GetReturnCode(context);
+	    EAX = (EAX & 0xffffff00) | NoError; /* normal exit */
 	    break;
 
 	  case 0x4e: /* "FINDFIRST" - FIND FIRST MATCHING FILE */
@@ -1409,7 +1219,9 @@
 	    break;
 			
 	  case 0x52: /* "SYSVARS" - GET LIST OF LISTS */
-	    GetSysVars(context);
+		ES = 0x0;
+		EBX = (EBX & 0xffff0000);
+		IntBarf(0x21, context);
 	    break;
 		
 	  case 0x56: /* "RENAME" - RENAME FILE */
@@ -1417,7 +1229,7 @@
 	    break;
 	
 	  case 0x57: /* FILE DATE AND TIME */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x00:
 		GetFileDateTime(context);
@@ -1429,10 +1241,10 @@
 	    break;
 
 	  case 0x58: /* GET OR SET MEMORY/UMB ALLOCATION STRATEGY */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x00:
-		EAX = (EAX & 0xffffff00L) | 0x01L;
+		EAX = (EAX & 0xffffff00) | 0x01L;
 		break;
 	      case 0x02:
 		EAX &= 0xff00L;
@@ -1453,24 +1265,24 @@
 	    break;
 	
 	  case 0x5c: /* "FLOCK" - RECORD LOCKING */
-	    FileLock(context);
+		IntBarf(0x21, context);
 	    break;	
 
 	  case 0x5d: /* NETWORK */
 	  case 0x5e:
 	    /* network software not installed */
-	    EAX = (EAX & 0xfffff00L) | NoNetwork;
+	    EAX = (EAX & 0xfffff00) | NoNetwork;
 	    SetCflag;
 	    break;
 	
 	  case 0x5f: /* NETWORK */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x07: /* ENABLE DRIVE */
-		if (!DOS_EnableDrive(EDX & 0xffL)) 
+		if (!DOS_EnableDrive(EDX & 0xff)) 
 		{
 		    Error(InvalidDrive, EC_MediaError , EL_Disk);
-		    EAX = (EAX & 0xfffff00L) | InvalidDrive;
+		    EAX = (EAX & 0xfffff00) | InvalidDrive;
 		    SetCflag;
 		    break;
 		} 
@@ -1480,10 +1292,10 @@
 		    break;
 		}
 	      case 0x08: /* DISABLE DRIVE */
-		if (!DOS_DisableDrive(EDX & 0xffL)) 
+		if (!DOS_DisableDrive(EDX & 0xff)) 
 		{
 		    Error(InvalidDrive, EC_MediaError , EL_Disk);
-		    EAX = (EAX & 0xfffff00L) | InvalidDrive;
+		    EAX = (EAX & 0xfffff00) | InvalidDrive;
 		    SetCflag;
 		    break;
 		} 
@@ -1494,26 +1306,27 @@
 		}
 	      default:
 		/* network software not installed */
-		EAX = (EAX & 0xfffff00L) | NoNetwork; 
+		EAX = (EAX & 0xfffff00) | NoNetwork; 
 		SetCflag;
 		break;
 	    }
 	    break;
 
 	  case 0x60: /* "TRUENAME" - CANONICALIZE FILENAME OR PATH */
-	    GetTrueFileName(context);
+		strncpy(pointer(ES,DI), pointer(DS,SI), strlen(pointer(DS,SI)) & 0x7f);
+		ResetCflag;
 	    break;
 
+	  case 0x61: /* UNUSED */
 	  case 0x62: /* GET CURRENT PSP ADDRESS */
-	    GetCurrentPSP(context);
-	    break;
-	
+	  case 0x63: /* UNUSED */
+	  case 0x64: /* OS/2 DOS BOX */
 	  case 0x65: /* GET EXTENDED COUNTRY INFORMATION */
-	    GetExtendedCountryInfo(context);
+		IntBarf(0x21, context);
 	    break;
 	
 	  case 0x66: /* GLOBAL CODE PAGE TABLE */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x01:
 		EBX = CodePage;
@@ -1536,7 +1349,7 @@
 	    break;		
 	
 	  case 0x69: /* DISK SERIAL NUMBER */
-	    switch (EAX & 0xffL) 
+	    switch (EAX & 0xff) 
 	    {
 	      case 0x00:
 		GetDiskSerialNumber(context);
@@ -1551,9 +1364,8 @@
 	    ResetCflag;
 	    break;		
 
-
 	  default:
-            Barf(context);
+            IntBarf(0x21, context);
 	    return 1;
 	}
     }
@@ -1568,3 +1380,19 @@
     do_int21((struct sigcontext_struct *) _CONTEXT);
     ReturnFromRegisterFunc();
 }
+
+void INT21_Init(void)
+{
+	int handle;
+	MDESC *DosHeapDesc;
+
+	if ((handle = GlobalAlloc(GMEM_FIXED,sizeof(struct DosHeap))) == 0)
+		myerror("out of memory");
+
+	heap = (struct DosHeap *) GlobalLock(handle);
+	HEAP_Init(&DosHeapDesc, heap, sizeof(struct DosHeap));
+
+	dta = heap->dta;
+	heap->InDosFlag = 0;
+	strcpy(heap->biosdate, "01/01/80");
+}
diff --git a/miscemu/int2f.c b/miscemu/int2f.c
index 4780766..8c50267 100644
--- a/miscemu/int2f.c
+++ b/miscemu/int2f.c
@@ -3,14 +3,6 @@
 #include "msdos.h"
 #include "wine.h"
 
-static void Barf(struct sigcontext_struct *context)
-{
-	fprintf(stderr, "int2f: unknown/not implemented parameters:\n");
-	fprintf(stderr, "int2f: AX %04x, BX %04x, CX %04x, DX %04x, "
-	       "SI %04x, DI %04x, DS %04x, ES %04x\n",
-	       AX, BX, CX, DX, SI, DI, DS, ES);
-}
-
 int do_int2f(struct sigcontext_struct *context)
 {
 	switch(context->sc_eax & 0xffff)
@@ -20,7 +12,7 @@
 		break;
 
 	default:
-		Barf(context);
+		IntBarf(0x2f, context);
 	};
 	return 1;
 }
diff --git a/miscemu/int31.c b/miscemu/int31.c
new file mode 100644
index 0000000..eaee326
--- /dev/null
+++ b/miscemu/int31.c
@@ -0,0 +1,14 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include "msdos.h"
+#include "wine.h"
+
+int do_int31(struct sigcontext_struct *context)
+{
+	switch((context->sc_eax >> 8) & 0xff)
+	{
+	default:
+		IntBarf(0x31, context);
+	};
+	return 1;
+}
diff --git a/miscemu/ioports.c b/miscemu/ioports.c
index bb2c877..35560a2 100644
--- a/miscemu/ioports.c
+++ b/miscemu/ioports.c
@@ -46,7 +46,7 @@
 	switch (EDX & 0xffff)
 	{
 		case 0x70:
-			cmosaddress = EAX & 0xff;
+			cmosaddress = EAX & 0x7f;
 			break;
 		case 0x71:
 			cmosimage[cmosaddress & 0x3f] = EAX & 0xff;
diff --git a/objects/font.c b/objects/font.c
index 07e4d21..5963b96 100644
--- a/objects/font.c
+++ b/objects/font.c
@@ -586,6 +586,7 @@
 				if (lpFaceList[j] == NULL) break;
 				if (strcmp(lpFaceList[j], lpLogFontList[i]->lfFaceName) == 0) {
 					i++; j = 0;
+					if (lpLogFontList[i] == NULL) break;
 					}
 				}
 			if (lpLogFontList[i] == NULL) break;
diff --git a/objects/gdiobj.c b/objects/gdiobj.c
index 9248c32..4f7fa67 100644
--- a/objects/gdiobj.c
+++ b/objects/gdiobj.c
@@ -553,13 +553,3 @@
 	printf("EnumObjects // End of enumeration !\n");
 	return 0;
 }
-
-/***********************************************************************
- *           SetObjectOwner    (GDI.461)
- */
-int SetObjectOwner(HANDLE hObj)
-{
-	printf("EMPTY STUB !!! SetObjectOwner() (I don't know its prototype !\n");
-	return 0;
-}
-
diff --git a/objects/text.c b/objects/text.c
index e7d3cdb..d4448a9 100644
--- a/objects/text.c
+++ b/objects/text.c
@@ -62,14 +62,15 @@
 		return (&str[i]);
 	    }
 	    dest[j++] = str[i++];
-	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX))
+	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
+		(format & DT_WORDBREAK))
 	    {
 		if (!GetTextExtentPoint(hdc, &dest[j-1], 1, &size))
 		    return NULL;
 		plen += size.cx;
 	    }
 	    break;
-
+	    
 	case PREFIX:
 	    if (!(format & DT_NOPREFIX))
 	    {
@@ -79,7 +80,7 @@
 	    else
 	    {
 		dest[j++] = str[i++];
-		if (!(format & DT_NOCLIP))
+		if (!(format & DT_NOCLIP) || (format & DT_WORDBREAK))
 		{
 		    if (!GetTextExtentPoint(hdc, &dest[j-1], 1, &size))
 			return NULL;
@@ -87,7 +88,7 @@
 		}
 	    }
 	    break;
-
+	    
 	case TAB:
 	    if (format & DT_EXPANDTABS)
 	    {
@@ -108,7 +109,8 @@
 	    else
 	    {
 		dest[j++] = str[i++];
-		if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX))
+		if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
+		    (format & DT_WORDBREAK))
 		{
 		    if (!GetTextExtentPoint(hdc, &dest[j-1], 1, &size))
 			return NULL;
@@ -119,7 +121,8 @@
 
 	case SPACE:
 	    dest[j++] = str[i++];
-	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX))
+	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
+		(format & DT_WORDBREAK))
 	    {
 		wb_i = i;
 		wb_j = j - 1;
@@ -132,7 +135,8 @@
 
 	default:
 	    dest[j++] = str[i++];
-	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX))
+	    if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
+		(format & DT_WORDBREAK))
 	    {
 		if (!GetTextExtentPoint(hdc, &dest[j-1], 1, &size))
 		    return NULL;
@@ -148,7 +152,7 @@
 		if (format & DT_WORDBREAK)
 		{
 		    *len = wb_j;
-		    *count = wb_count;
+		    *count = wb_count - 1;
 		    return (&str[wb_i]);
 		}
 		else
@@ -178,6 +182,11 @@
     int x = rect->left, y = rect->top;
     int width = rect->right - rect->left;
 
+#ifdef DEBUG_TEXT
+    printf( "DrawText: '%s', %d , [(%d,%d),(%d,%d)]\n", str, count,
+	   rect->left, rect->top, rect->right, rect->bottom);
+#endif
+
     if (count == -1) count = strlen(str);
     strPtr = str;
 
@@ -423,5 +432,3 @@
 	return FALSE;
 }
 
-
-
diff --git a/tools/build.c b/tools/build.c
index 85a4b20..096c1d6 100644
--- a/tools/build.c
+++ b/tools/build.c
@@ -27,7 +27,8 @@
 #define EQUATETYPE_ABS	18
 #define TYPE_RETURN	20
 
-#define MAX_ORDINALS	1024
+/*#define MAX_ORDINALS	1024*/
+#define MAX_ORDINALS	1299
 
 #define PUSH_0		"\tpushl\t$0\n"
 #define PUSH_SS		"\tpushw\t$0\n\tpushw\t%%ss\n"
diff --git a/windows/mdi.c b/windows/mdi.c
index b2aadff..00c02f1 100644
--- a/windows/mdi.c
+++ b/windows/mdi.c
@@ -6,6 +6,7 @@
  */
 #include <stdlib.h>
 #include <stdio.h>
+#include <math.h>
 #include "windows.h"
 #include "win.h"
 #include "mdi.h"
diff --git a/windows/nonclient.c b/windows/nonclient.c
index 45ca0d8..d8fedc0 100644
--- a/windows/nonclient.c
+++ b/windows/nonclient.c
@@ -69,7 +69,6 @@
 
     if ((style & WS_CAPTION) == WS_CAPTION)
 	rect->top -= SYSMETRICS_CYCAPTION - 1;
-
     if (menu) rect->top -= SYSMETRICS_CYMENU + 1;
 
     if (style & WS_VSCROLL) rect->right  += SYSMETRICS_CXVSCROLL;
@@ -592,15 +591,24 @@
 
     if (wndPtr->wIDmenu != 0 &&
 	(wndPtr->dwStyle & WS_CHILD) != WS_CHILD) {
-	int oldbottom;
-	CopyRect(&rect2, &rect);
-	/* Default MenuBar height */
-	oldbottom = rect2.bottom = rect2.top + SYSMETRICS_CYMENU; 
-	StdDrawMenuBar(hdc, &rect2, (LPPOPUPMENU)GlobalLock(wndPtr->wIDmenu),
-		       suppress_menupaint);
-	GlobalUnlock(wndPtr->wIDmenu);
-	/* Reduce ClientRect according to MenuBar height */
-	rect.top += rect2.bottom - oldbottom;
+	LPPOPUPMENU	lpMenu = (LPPOPUPMENU) GlobalLock(wndPtr->wIDmenu);
+	if (lpMenu != NULL) {
+		int oldHeight;
+		CopyRect(&rect2, &rect);
+		/* Default MenuBar height */
+		if (lpMenu->Height == 0) lpMenu->Height = SYSMETRICS_CYMENU + 1;
+		oldHeight = lpMenu->Height;
+		rect2.bottom = rect2.top + oldHeight; 
+/*		printf("NC_DoNCPaint // menubar old Height=%d\n", oldHeight); */
+		StdDrawMenuBar(hdc, &rect2, lpMenu, suppress_menupaint);
+		GlobalUnlock(wndPtr->wIDmenu);
+/*		printf("NC_DoNCPaint // menubar new Height=%d\n", lpMenu->Height); */
+		if (oldHeight != lpMenu->Height) {
+			/* Reduce ClientRect according to MenuBar height */
+			wndPtr->rectClient.top -= oldHeight;
+			wndPtr->rectClient.top += lpMenu->Height;
+			}
+		}
 	}
 
     if (wndPtr->dwStyle & (WS_VSCROLL | WS_HSCROLL)) {
@@ -611,7 +619,7 @@
 	    	rect.top, rect.right, bottom); 
 	    if (wndPtr->dwStyle & WS_CAPTION) rect.top += SYSMETRICS_CYSIZE;
 	    if (wndPtr->wIDmenu != 0 && (wndPtr->dwStyle & WS_CHILD) != WS_CHILD) 
-	    	rect2.top += SYSMETRICS_CYMENU;
+	    	rect2.top += SYSMETRICS_CYMENU + 1;
  	    StdDrawScrollBar(hwnd, hdc, SB_VERT, &rect2, (LPHEADSCROLL)wndPtr->VScroll);
  	    }
 	if (wndPtr->dwStyle & WS_HSCROLL) {
diff --git a/windows/utility.c b/windows/utility.c
index a1e0d0e..32f1e59 100644
--- a/windows/utility.c
+++ b/windows/utility.c
@@ -301,10 +301,10 @@
 
 		/* skip width/precision */
 		while (*ptr == '-' || *ptr == '+' || *ptr == '.' ||
-		       *ptr == ' ' || isdigit(*ptr))
+		       *ptr == ' ' || isdigit(*ptr) || *ptr == '#')
 			ptr++;
 			
-		switch (*ptr++) {
+		switch (*ptr) {
 			case 's':
 				*(DWORD*)stack_ptr = *(DWORD*)win_stack;
 				stack_ptr += 4;
diff --git a/windows/win.c b/windows/win.c
index 73b5ac1..1f0a8f7 100644
--- a/windows/win.c
+++ b/windows/win.c
@@ -290,6 +290,7 @@
     wndPtr = (WND *) USER_HEAP_ADDR( hwnd );
     wndPtr->hwndNext   = 0;
     wndPtr->hwndChild  = 0;
+	wndPtr->window 	   = 0;
     wndPtr->dwMagic    = WND_MAGIC;
     wndPtr->hwndParent = (style & WS_CHILD) ? parent : hwndDesktop;
     wndPtr->hwndOwner  = (style & WS_CHILD) ? 0 : parent;
@@ -312,22 +313,7 @@
     wndPtr->lpfnWndProc       = classPtr->wc.lpfnWndProc;
     wndPtr->dwStyle           = style;
     wndPtr->dwExStyle         = exStyle;
-#ifdef DEBUG_MENU
-    printf("CreateWindowEx // menu=%04X instance=%04X classmenu=%08X !\n", 
-    	menu, instance, classPtr->wc.lpszMenuName); 
-#endif
-	if ((style & WS_CAPTION) && (style & WS_CHILD) == 0) {
-		if (menu != 0)
-			SetMenu(hwnd, menu);
-		else {
-			if (classPtr->wc.lpszMenuName != NULL)
-				SetMenu(hwnd, LoadMenu(instance, classPtr->wc.lpszMenuName));
-			else
-				wndPtr->wIDmenu   = 0;
-			}
-		}
-	else
-		wndPtr->wIDmenu   = menu;
+	wndPtr->wIDmenu   		  = 0;
     wndPtr->hText             = 0;
     wndPtr->flags             = 0;
     wndPtr->VScroll           = NULL;
@@ -390,6 +376,21 @@
 		   CWSaveUnder | CWBackingStore, &win_attr );
     XStoreName( display, wndPtr->window, windowName );
 
+#ifdef DEBUG_MENU
+    printf("CreateWindowEx // menu=%04X instance=%04X classmenu=%08X !\n", 
+    	menu, instance, classPtr->wc.lpszMenuName); 
+#endif
+	if ((style & WS_CAPTION) && (style & WS_CHILD) == 0) {
+		if (menu != 0)
+			SetMenu(hwnd, menu);
+		else {
+			if (classPtr->wc.lpszMenuName != NULL)
+				SetMenu(hwnd, LoadMenu(instance, classPtr->wc.lpszMenuName));
+			}
+		}
+	else
+		wndPtr->wIDmenu   = menu;
+
       /* Send the WM_CREATE message */
 
     hcreateStruct = USER_HEAP_ALLOC( GMEM_MOVEABLE, sizeof(CREATESTRUCT) );
diff --git a/windows/winpos.c b/windows/winpos.c
index 98cfa11..a9fe9a6 100644
--- a/windows/winpos.c
+++ b/windows/winpos.c
@@ -604,8 +604,8 @@
 	wndPtr->dwStyle |= WS_VISIBLE;
 	XMapWindow( display, wndPtr->window );
 	MSG_Synchronize();
-	if (winPos->flags & SWP_NOREDRAW)
-	    RedrawWindow( hwnd, NULL, 0, RDW_VALIDATE );
+/*	if (winPos->flags & SWP_NOREDRAW)
+	    RedrawWindow( hwnd, NULL, 0, RDW_VALIDATE ); */
     }
     else if (winPos->flags & SWP_HIDEWINDOW)
     {
@@ -639,6 +639,10 @@
 	(!(winPos->flags & SWP_NOACTIVATE)) ||
 	(!(winPos->flags & SWP_NOZORDER)))
 	    SendMessage( hwnd, WM_NCPAINT, 1, 0L );
+    if ((winPos->flags & (SWP_FRAMECHANGED | SWP_SHOWWINDOW)) &&
+		(!(winPos->flags & SWP_NOREDRAW)) && 
+		(wndPtr->dwStyle & WS_VISIBLE) && IsWindowVisible(hwnd))
+		InvalidateRect(hwnd, NULL, TRUE);
 
       /* Finally send the WM_WINDOWPOSCHANGED message */
     wndPtr->rectWindow = newWindowRect;