Commit 808cb043 authored by Alexandre Julliard's avatar Alexandre Julliard

Release 950817

Thu Aug 17 19:30:14 1995 Alexandre Julliard <julliard@sunsite.unc.edu> * [*/Makefile.in] Removed winelibclean target, as it doesn't work anyway. * [controls/button.c] Avoid drawing the focus rectangle outside of the button. * [controls/widgets.c] Fixed bug with the size of the reserved bytes for the Edit control (caused Eudora to crash). * [debugger/*] [include/debugger.h] Unified debugger address handling. Segmented and linear addresses are no grouped in a single type DBG_ADDR. All commands now accept seg:off addresses. Module entry points are now loaded upon first entry to the debugger, so that entry points of the loaded executable also appear in the symbol table. * [include/registers.h] [miscemu/*.c] Register macros are now of the form 'AX_reg(context)' instead of 'AX'. This makes code less readable, but will prevent a lot of name clashes with other definitions. It also avoids a hidden reference to the 'context' variable. * [ipc/dde_atom.c] [misc/atom.c] All *AddAtom and *FindAtom functions now take a SEGPTR parameter, to allow supporting integer atoms. Moved atom.c to memory/ directory. * [loader/task.c] Fixed environment allocation to compute the size dynamically. Added 'windir' environment variable. Fixed GetDOSEnvironment() to return the current task environment. * [windows/message.c] Fixed bug in MSG_GetWindowForEvent(). Wed Aug 9 11:40:43 1995 Marcus Meissner <msmeissn@faui01.informatik.uni-erlangen.de> * [include/ole.h] Added a lot of structures from my Borland Manual. Neither complete, nor 100% right (check please) * [misc/shell.c] Fixed some of the Reg* functions. Enhanced ShellExecute. Please test: wine "regedit.exe /v" mplayer.exe soundrec.exe Do YOU know the format of \WINDOWS\REG.DAT? Mail me please :) * [misc/dos_fs.c] Make umsdos mounted windows dirs work again. * [miscemu/emulate.c] Added some comments, preimplementation of subfunction 7. * [multimedia/mmsystem.c] Implemented mciSendString. not complete, not clean, not necessarily working (only checked with a program which uses 'cdaudio' (one working program is cool.exe, a shareware waveditor with cdaudio play facilities.) * [multimedia/mcicda.c] Segptr fixes in DriverProc Default cdrom drive in Linux is /dev/cdrom ... usually a symbolic link to your real cdrom device. Tue Aug 8 19:41:50 CDT 1995 Daniel Schepler <dks2@cec.wustl.edu> * [loader/resource.c] Don't crash in a LoadString to NULL * [loader/resource.c] Fixed accelerators to work with modifiers. (ALT-x modifiers still won't work unless the ALT keypress exited the menu.) * [misc/file.c] Expand a file to the current offset with an _lwrite of size zero. * [misc/file.c] Set a newly created file to read-write instead of write-only. Sun Aug 6 20:28:35 1995 Anand Kumria <akumria@ozemail.com.au> * [misc/main.c] [include/msdos.h] Fixed to return DOS version 6.22, and the correct byte order for Windows programs. Wed Aug 2 12:36:33 1995 Bernd Schmidt <crux@pool.informatik.rwth-aachen.de> * [include/options.h] [memory/global.c] [misc/main.c] Make the new IPC run-time selectible, disabling it by default. (I think it's only useful for libwine, anyway.) * [loader/task.c] [memory/selector.c] In FreeSelector(), walk up the stack and fix the frames. * [objects/dib.c] Missing break statement in DIB_SetImageBits_RLE8(). In GetDIBits(), set the compression flag in the bitmap info to zero. * [windows/dialog.c] GetNextDlgGroupItem() needs to treat the first child as if it had an implicit WS_GROUP bit set. Mon Jul 31 15:44:47 EDT 1995 Louis-D. Dubeau <ldd@step.polymtl.ca> * [misc/dos_fs.c] Quick'n dirty fix for the initialisation of the Z: information structure.
parent e2991ea7
This is release 950727 of Wine the MS Windows emulator. This is still a
This is release 950817 of Wine the MS Windows emulator. This is still a
developer's only release. There are many bugs and many unimplemented API
features. Most applications still do not work.
Patches should be submitted to "wine-new@amscons.com". Please don't forget
to include a ChangeLog entry. I'll make a new release every other Sunday.
WHAT'S NEW with Wine-950727: (see ChangeLog for details)
- New configuration scheme based on autoconf (please test it).
- DDE communication between separate Wine processes.
- Lots of file handling fixes.
- Fixes to built-in WINSOCK.DLL.
WHAT'S NEW with Wine-950817: (see ChangeLog for details)
- Built-in debugger improvements.
- Multimedia fixes.
- IPC can be disabled at run-time.
- Lots of bug fixes.
See the README file in the distribution for installation instructions.
......@@ -18,11 +17,11 @@ Because of lags created by using mirror, this message may reach you before
the release is available at the ftp sites. The sources will be available
from the following locations:
sunsite.unc.edu:/pub/Linux/ALPHA/wine/Wine-950727.tar.gz
tsx-11.mit.edu:/pub/linux/ALPHA/Wine/development/Wine-950727.tar.gz
ftp.infomagic.com:/pub/mirrors/linux/wine/development/Wine-950727.tar.gz
ftp.funet.fi:/pub/OS/Linux/ALPHA/Wine/Wine-950727.tar.gz
aris.com:/pub/linux/ALPHA/Wine/development/Wine-950727.tar.gz
sunsite.unc.edu:/pub/Linux/ALPHA/wine/Wine-950817.tar.gz
tsx-11.mit.edu:/pub/linux/ALPHA/Wine/development/Wine-950817.tar.gz
ftp.infomagic.com:/pub/mirrors/linux/wine/development/Wine-950817.tar.gz
ftp.funet.fi:/pub/OS/Linux/ALPHA/Wine/Wine-950817.tar.gz
aris.com:/pub/linux/ALPHA/Wine/development/Wine-950817.tar.gz
It should also be available from any site that mirrors tsx-11 or sunsite.
......
----------------------------------------------------------------------
Thu Aug 17 19:30:14 1995 Alexandre Julliard <julliard@sunsite.unc.edu>
* [*/Makefile.in]
Removed winelibclean target, as it doesn't work anyway.
* [controls/button.c]
Avoid drawing the focus rectangle outside of the button.
* [controls/widgets.c]
Fixed bug with the size of the reserved bytes for the Edit
control (caused Eudora to crash).
* [debugger/*] [include/debugger.h]
Unified debugger address handling. Segmented and linear addresses
are no grouped in a single type DBG_ADDR.
All commands now accept seg:off addresses.
Module entry points are now loaded upon first entry to the
debugger, so that entry points of the loaded executable also
appear in the symbol table.
* [include/registers.h] [miscemu/*.c]
Register macros are now of the form 'AX_reg(context)' instead of 'AX'.
This makes code less readable, but will prevent a lot of name
clashes with other definitions. It also avoids a hidden reference
to the 'context' variable.
* [ipc/dde_atom.c] [misc/atom.c]
All *AddAtom and *FindAtom functions now take a SEGPTR parameter,
to allow supporting integer atoms.
Moved atom.c to memory/ directory.
* [loader/task.c]
Fixed environment allocation to compute the size dynamically.
Added 'windir' environment variable.
Fixed GetDOSEnvironment() to return the current task environment.
* [windows/message.c]
Fixed bug in MSG_GetWindowForEvent().
Wed Aug 9 11:40:43 1995 Marcus Meissner <msmeissn@faui01.informatik.uni-erlangen.de>
* [include/ole.h]
Added a lot of structures from my Borland Manual. Neither complete,
nor 100% right (check please)
* [misc/shell.c]
Fixed some of the Reg* functions.
Enhanced ShellExecute.
Please test: wine "regedit.exe /v" mplayer.exe soundrec.exe
Do YOU know the format of \WINDOWS\REG.DAT? Mail me please :)
* [misc/dos_fs.c]
Make umsdos mounted windows dirs work again.
* [miscemu/emulate.c]
Added some comments, preimplementation of subfunction 7.
* [multimedia/mmsystem.c]
Implemented mciSendString. not complete, not clean, not
necessarily working (only checked with a program which uses
'cdaudio' (one working program is cool.exe, a shareware waveditor
with cdaudio play facilities.)
* [multimedia/mcicda.c]
Segptr fixes in DriverProc
Default cdrom drive in Linux is /dev/cdrom ... usually a symbolic
link to your real cdrom device.
Tue Aug 8 19:41:50 CDT 1995 Daniel Schepler <dks2@cec.wustl.edu>
* [loader/resource.c]
Don't crash in a LoadString to NULL
* [loader/resource.c]
Fixed accelerators to work with modifiers. (ALT-x modifiers still
won't work unless the ALT keypress exited the menu.)
* [misc/file.c]
Expand a file to the current offset with an _lwrite of size zero.
* [misc/file.c]
Set a newly created file to read-write instead of write-only.
Sun Aug 6 20:28:35 1995 Anand Kumria <akumria@ozemail.com.au>
* [misc/main.c] [include/msdos.h]
Fixed to return DOS version 6.22, and the correct byte order
for Windows programs.
Wed Aug 2 12:36:33 1995 Bernd Schmidt <crux@pool.informatik.rwth-aachen.de>
* [include/options.h] [memory/global.c] [misc/main.c]
Make the new IPC run-time selectible, disabling it by default.
(I think it's only useful for libwine, anyway.)
* [loader/task.c] [memory/selector.c]
In FreeSelector(), walk up the stack and fix the frames.
* [objects/dib.c]
Missing break statement in DIB_SetImageBits_RLE8().
In GetDIBits(), set the compression flag in the bitmap info to zero.
* [windows/dialog.c]
GetNextDlgGroupItem() needs to treat the first child as if it had
an implicit WS_GROUP bit set.
Mon Jul 31 15:44:47 EDT 1995 Louis-D. Dubeau <ldd@step.polymtl.ca>
* [misc/dos_fs.c]
Quick'n dirty fix for the initialisation of the Z: information
structure.
----------------------------------------------------------------------
Sat Jul 22 22:39:09 IDT 1995 Michael Veksler <e1678223@tochnapc2.technion.ac.il>
* [ipc/*]
......@@ -48,7 +161,7 @@ Sun Jul 16 18:17:17 1995 Gregory Trubetskoy <grisha@mira.com>
Added LoadIconHandler. It doesn't do anything yet, but now you
can use borland help files with winhelp.exe.
Sun Jul 16 11:58:45 1996 Anand Kumria <akumria@ozemail.com.au>
Sun Jul 16 11:58:45 1995 Anand Kumria <akumria@ozemail.com.au>
* [misc/main.c]
Fixed to return 386 Enhanced mode correctly. Also return the same
......
......@@ -5,8 +5,6 @@
# distclean: also remove all files created by configure
# countryclean: remove all files which have to be remade if
# a different LANGuage is selected
# winelibclean: remove all files which differ for the emulator
# and the library
# depend: create the dependencies
#
# Author: Michael Patra <micky@marie.physik.tu-berlin.de>
......@@ -41,47 +39,41 @@ EMUOBJS = debugger/debugger.o if1632/if1632.o memory/memory.o miscemu/miscemu.o
LIBOBJS = toolkit/toolkit.o
SUBDIRS = $(COMMONSUBDIRS) $(EMUSUBDIRS)
OBJS = $(COMMONOBJS) $(EMUOBJS)
all:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)' 'LANG=$(LANG)'); \
done
$(CC) -o wine $(OBJS) $(LDOPTIONS) $(XDIR) $(XPM_LIB) $(XLIB) $(LDLIBS)
all: wine wine.sym
wine.sym: wine
nm wine | grep -v _compiled | sort >wine.sym
wine: $(SUBDIRS) dummy
$(CC) -o wine $(OBJS) $(LDOPTIONS) $(XDIR) $(XPM_LIB) $(XLIB) $(LDLIBS)
$(SUBDIRS): dummy
@cd $@; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)' 'LANG=$(LANG)'
depend:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) depend); \
done
for i in $(SUBDIRS); do (cd $$i; $(MAKE) depend); done
etags:
etags `find . -name '*.[chS]' -print`
clean:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) clean); \
done
rm -f *.o \#*\# *~ wine wine.sym
for i in $(SUBDIRS); do (cd $$i; $(MAKE) clean); done
rm -f *.o \#*\# *~ wine wine.sym TAGS
distclean:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) distclean); \
done
for i in $(SUBDIRS); do (cd $$i; $(MAKE) distclean); done
echo "/* autoconf.h generated automatically. Run Configure */" >autoconf.h
echo "#error You must run Configure before you can build the makefiles." >>autoconf.h
rm -f *.o \#*\# *~ wine wine.sym
rm -f stamp-config config.* include/config.h Makefile
countryclean:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) countryclean); \
done
for i in $(SUBDIRS); do (cd $$i; $(MAKE) countryclean); done
rm -f wine wine.sym
winelibclean:
for i in $(SUBDIRS); do \
( cd $(TOPSRC)/$$i; $(MAKE) winelibclean); \
done
dummy:
......@@ -32,7 +32,6 @@ AC_SUBST(LDCOMBINEFLAGS)
AC_CHECK_FUNCS(tcgetattr)
AC_CHECK_HEADERS(stdlib.h)
AC_HEADER_DIRENT()
AC_HEADER_STAT()
AC_C_CONST()
AC_TYPE_SIZE_T()
......
......@@ -24,26 +24,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -313,14 +313,15 @@ static void PB_Paint( HWND hButton, HDC hDC, WORD action )
/* do we have the focus? */
if (infoPtr->state & BUTTON_HASFOCUS)
{
dwTextSize = GetTextExtent(hDC, text, strlen(text) );
delta = ((rc.right - rc.left) - LOWORD(dwTextSize) - 1) >> 1;
rc.left += delta;
rc.right -= delta;
GetTextMetrics(hDC, &tm);
delta = ((rc.bottom - rc.top) - tm.tmHeight - 1) >> 1;
rc.top += delta; rc.bottom -= delta;
DrawFocusRect(hDC, &rc);
short xdelta, ydelta;
dwTextSize = GetTextExtent( hDC, text, strlen(text) );
GetTextMetrics( hDC, &tm );
xdelta = ((rc.right - rc.left) - LOWORD(dwTextSize) - 1) / 2;
ydelta = ((rc.bottom - rc.top) - tm.tmHeight - 1) / 2;
if (xdelta < 0) xdelta = 0;
if (ydelta < 0) ydelta = 0;
InflateRect( &rc, -xdelta, -ydelta );
DrawFocusRect( hDC, &rc );
}
}
......@@ -378,10 +379,13 @@ static void CB_Paint( HWND hWnd, HDC hDC, WORD action )
((action == ODA_DRAWENTIRE) && (infoPtr->state & BUTTON_HASFOCUS)))
{
GetTextExtentPoint(hDC, text, textlen, &size);
rc.top += delta - 1;
rc.bottom -= delta + 1;
if (delta > 1)
{
rc.top += delta - 1;
rc.bottom -= delta + 1;
}
rc.left--;
rc.right = rc.left + size.cx + 2;
rc.right = min( rc.left + size.cx + 2, rc.right );
DrawFocusRect(hDC, &rc);
}
}
......
......@@ -105,6 +105,8 @@ static LONG CBCreate(HWND hwnd, WORD wParam, LONG lParam)
LONG style = 0;
LONG cstyle = GetWindowLong(hwnd,GWL_STYLE);
RECT rect,lboxrect;
char className[] = "COMBOLBOX"; /* Hack so that class names are > 0x10000 */
char editName[] = "EDIT";
/* translate combo into listbox styles */
if (cstyle & CBS_OWNERDRAWFIXED) style |= LBS_OWNERDRAWFIXED;
......@@ -125,7 +127,7 @@ static LONG CBCreate(HWND hwnd, WORD wParam, LONG lParam)
dprintf_combo(stddeb,"CBS_SIMPLE\n");
SetRectEmpty(&lphc->RectButton);
lphc->LBoxTop = lphl->StdItemHeight;
lphc->hWndEdit = CreateWindow("EDIT", "",
lphc->hWndEdit = CreateWindow(editName, "",
WS_CHILD | WS_CLIPCHILDREN | WS_VISIBLE | SS_LEFT,
0, 0, rect.right, lphl->StdItemHeight,
hwnd, 1, GetWindowWord(hwnd,GWW_HINSTANCE), 0L);
......@@ -139,7 +141,7 @@ static LONG CBCreate(HWND hwnd, WORD wParam, LONG lParam)
SetWindowPos(hwnd, 0, 0, 0, rect.right - rect.left + 2*SYSMETRICS_CXBORDER,
lphl->StdItemHeight + 2*SYSMETRICS_CYBORDER,
SWP_NOMOVE | SWP_NOZORDER);
lphc->hWndEdit = CreateWindow("EDIT", "",
lphc->hWndEdit = CreateWindow(editName, "",
WS_CHILD | WS_CLIPCHILDREN | WS_VISIBLE | SS_LEFT,
0, 0, lphc->RectButton.left, lphl->StdItemHeight,
hwnd, 1, GetWindowWord(hwnd,GWW_HINSTANCE), 0L);
......@@ -159,7 +161,7 @@ static LONG CBCreate(HWND hwnd, WORD wParam, LONG lParam)
/* FIXME: WinSight says these should be CHILD windows with the TOPMOST flag
* set. Wine doesn't support TOPMOST, and simply setting the WS_CHILD
* flag doesn't work. */
lphc->hWndLBox = CreateWindow("COMBOLBOX", "",
lphc->hWndLBox = CreateWindow(className, "",
WS_POPUP | WS_BORDER | WS_VSCROLL,
lboxrect.left, lboxrect.top,
lboxrect.right - lboxrect.left,
......
......@@ -14,6 +14,7 @@
#include "local.h"
#include "win.h"
#include "class.h"
#include "stackframe.h" /* for MAKE_SEGPTR */
#include "user.h"
#include "stddebug.h"
#include "debug.h"
......@@ -2303,8 +2304,11 @@ static long EDIT_WM_Create(HWND hwnd, LONG lParam)
es->BlankLine[(es->ClientWidth / es->CharWidths[32]) + 1] = 0;
/* set up text cursor for edit class */
CLASS_FindClassByName("EDIT", 0, &classPtr);
classPtr->wc.hCursor = LoadCursor(0, IDC_IBEAM);
{
char editname[] = "EDIT";
CLASS_FindClassByName( MAKE_SEGPTR(editname), 0, &classPtr);
classPtr->wc.hCursor = LoadCursor(0, IDC_IBEAM);
}
/* paint background on first WM_PAINT */
es->PaintBkgd = TRUE;
......
......@@ -673,7 +673,7 @@ static BOOL MENU_ShowPopup(HWND hwndOwner, HMENU hmenu, WORD id, int x, int y)
{
WND *wndPtr = WIN_FindWndPtr( hwndOwner );
if (!wndPtr) return FALSE;
menu->hWnd = CreateWindow( POPUPMENU_CLASS_NAME, "",
menu->hWnd = CreateWindow( (LPSTR)POPUPMENU_CLASS_ATOM, "",
WS_POPUP | WS_BORDER, x, y,
menu->Width + 2*SYSMETRICS_CXBORDER,
menu->Height + 2*SYSMETRICS_CYBORDER,
......
......@@ -15,31 +15,30 @@
#include "selectors.h"
#include "stackframe.h"
static WNDCLASS WIDGETS_BuiltinClasses[] =
{
{ CS_GLOBALCLASS | CS_PARENTDC, (WNDPROC)"ButtonWndProc", 0,
sizeof(BUTTONINFO), 0, 0, 0, 0, NULL, "BUTTON" },
sizeof(BUTTONINFO), 0, 0, 0, 0, 0, (SEGPTR)"BUTTON" },
{ CS_GLOBALCLASS | CS_PARENTDC, (WNDPROC)"StaticWndProc", 0,
sizeof(STATICINFO), 0, 0, 0, 0, NULL, "STATIC" },
sizeof(STATICINFO), 0, 0, 0, 0, 0, (SEGPTR)"STATIC" },
{ CS_GLOBALCLASS | CS_PARENTDC, (WNDPROC)"ScrollBarWndProc", 0,
sizeof(SCROLLINFO), 0, 0, 0, 0, NULL, "SCROLLBAR" },
sizeof(SCROLLINFO), 0, 0, 0, 0, 0, (SEGPTR)"SCROLLBAR" },
{ CS_GLOBALCLASS | CS_PARENTDC | CS_DBLCLKS, (WNDPROC)"ListBoxWndProc", 0,
8, 0, 0, 0, 0, NULL, "LISTBOX" },
{ CS_GLOBALCLASS | CS_PARENTDC, (WNDPROC)"ComboBoxWndProc", 0,
8, 0, 0, 0, 0, NULL, "COMBOBOX" },
{ CS_GLOBALCLASS | CS_PARENTDC | CS_DBLCLKS, (WNDPROC)"ComboLBoxWndProc", 0,
8, 0, 0, 0, 0, NULL, "COMBOLBOX" },
{ CS_GLOBALCLASS, (WNDPROC)"EditWndProc", 0,
sizeof(WORD), 0, 0, 0, 0, NULL, "EDIT" },
{ CS_GLOBALCLASS | CS_SAVEBITS, (WNDPROC)"PopupMenuWndProc", 0,
8, 0, 0, 0, 0, NULL, POPUPMENU_CLASS_NAME },
{ CS_GLOBALCLASS, (WNDPROC)"DesktopWndProc", 0,
sizeof(DESKTOPINFO), 0, 0, 0, 0, NULL, DESKTOP_CLASS_NAME },
{ CS_GLOBALCLASS | CS_SAVEBITS, (WNDPROC)"DefDlgProc", 0,
DLGWINDOWEXTRA, 0, 0, 0, 0, NULL, DIALOG_CLASS_NAME },
{ CS_GLOBALCLASS, (WNDPROC)"MDIClientWndProc", 0,
sizeof(MDICLIENTINFO), 0, 0, 0, STOCK_LTGRAY_BRUSH, NULL, "MDICLIENT" }
8, 0, 0, 0, 0, 0, (SEGPTR)"LISTBOX" },
{ CS_GLOBALCLASS | CS_PARENTDC, (WNDPROC)"ComboBoxWndProc", 0, 8,
0, 0, 0, 0, 0, (SEGPTR)"COMBOBOX" },
{ CS_GLOBALCLASS | CS_PARENTDC | CS_DBLCLKS, (WNDPROC)"ComboLBoxWndProc",
0, 8, 0, 0, 0, 0, 0, (SEGPTR)"COMBOLBOX" },
{ CS_GLOBALCLASS, (WNDPROC)"EditWndProc", 0, sizeof(DWORD),
0, 0, 0, 0, 0, (SEGPTR)"EDIT" },
{ CS_GLOBALCLASS | CS_SAVEBITS, (WNDPROC)"PopupMenuWndProc", 0, 8,
0, 0, 0, 0, 0, (SEGPTR)POPUPMENU_CLASS_NAME },
{ CS_GLOBALCLASS, (WNDPROC)"DesktopWndProc", 0, sizeof(DESKTOPINFO),
0, 0, 0, 0, 0, (SEGPTR)DESKTOP_CLASS_NAME },
{ CS_GLOBALCLASS | CS_SAVEBITS, (WNDPROC)"DefDlgProc", 0, DLGWINDOWEXTRA,
0, 0, 0, 0, 0, (SEGPTR)DIALOG_CLASS_NAME },
{ CS_GLOBALCLASS, (WNDPROC)"MDIClientWndProc", 0, sizeof(MDICLIENTINFO),
0, 0, 0, STOCK_LTGRAY_BRUSH, 0, (SEGPTR)"MDICLIENT" }
};
#define NB_BUILTIN_CLASSES \
......@@ -59,8 +58,8 @@ BOOL WIDGETS_Init(void)
for (i = 0; i < NB_BUILTIN_CLASSES; i++, class++)
{
strcpy( name, class->lpszClassName );
class->lpszClassName = (LPSTR)MAKE_SEGPTR(name);
strcpy( name, (char *)class->lpszClassName );
class->lpszClassName = MAKE_SEGPTR(name);
class->hCursor = LoadCursor( 0, IDC_ARROW );
class->lpfnWndProc = GetWndProcEntry16( (char *)class->lpfnWndProc );
if (!RegisterClass( class )) return FALSE;
......
......@@ -17,6 +17,7 @@ SRCS = \
hash.c \
info.c \
lex.yy.c \
memory.c \
registers.c \
stack.c
......
......@@ -13,53 +13,42 @@ LDCOMBINEFLAGS = @LDCOMBINEFLAGS@
MODULE = debugger
SRCS = break.c db_disasm.c hash.c info.c registers.c stack.c
SRCS = break.c db_disasm.c hash.c info.c memory.c registers.c stack.c
OBJS = $(SRCS:.c=.o) dbg.tab.o lex.yy.o
all: $(MODULE).o dbg.tab.o lex.yy.o
dbg.tab.c: dbg.y
dbg.tab.c dbg.tab.h: dbg.y
$(BISON) -b dbg -d dbg.y
dbg.tab.h: dbg.y
$(BISON) -b dbg -d dbg.y
lex.yy.c: debug.l dbg.tab.h dbg.tab.h
lex.yy.c: debug.l dbg.tab.h
$(FLEX) -8 -I debug.l
.c.o:
$(COMPILE) -c -o $*.o $<
$(MODULE).o: $(OBJS)
(cd readline; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)')
$(MODULE).o: $(OBJS) readline
$(LD) $(LDCOMBINEFLAGS) $(OBJS) readline/readline.o -o $(MODULE).o
readline: dummy
cd readline; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)'
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
(cd readline; $(MAKE) clean)
rm -f *.o \#*\# *~ dbg.tab.c dbg.tab.h lex.yy.c y.tab.c y.tab.h tmp_make
distclean: clean
distclean:
(cd readline; $(MAKE) distclean)
rm Makefile
rm -f *.o \#*\# *~ dbg.tab.c dbg.tab.h lex.yy.c y.tab.c y.tab.h tmp_make Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dbg.tab.o: dbg.tab.c
lex.yy.o: lex.yy.c
......
......@@ -8,9 +8,6 @@
#include <stdio.h>
#include <stdlib.h>
#include <sys/mman.h>
#ifdef linux
#include <sys/utsname.h>
#endif
#include "windows.h"
#include "debugger.h"
......@@ -21,15 +18,14 @@
typedef struct
{
unsigned int segment;
unsigned int addr;
BYTE addrlen;
BYTE opcode;
BOOL enabled;
BOOL in_use;
DBG_ADDR addr;
BYTE addrlen;
BYTE opcode;
BOOL enabled;
BOOL in_use;
} BREAKPOINT;
static BREAKPOINT breakpoints[MAX_BREAKPOINTS] = { { 0, }, };
static BREAKPOINT breakpoints[MAX_BREAKPOINTS];
static int next_bp = 1; /* breakpoint 0 is reserved for step-over */
......@@ -39,11 +35,11 @@ static int next_bp = 1; /* breakpoint 0 is reserved for step-over */
*
* Change the opcode at segment:addr.
*/
static void DEBUG_SetOpcode( unsigned int segment, unsigned int addr, BYTE op )
static void DEBUG_SetOpcode( const DBG_ADDR *addr, BYTE op )
{
if (segment)
if (addr->seg)
{
*(BYTE *)PTR_SEG_OFF_TO_LIN( segment, addr ) = op;
*(BYTE *)PTR_SEG_OFF_TO_LIN( addr->seg, addr->off ) = op;
}
else /* 32-bit code, so we have to change the protection first */
{
......@@ -56,14 +52,15 @@ static void DEBUG_SetOpcode( unsigned int segment, unsigned int addr, BYTE op )
Not that portability matters, this code is i386 only anyways...
How do I get the old protection in order to restore it later on?
*/
if (mprotect((caddr_t)(addr & (~4095)), 4096,
PROT_READ|PROT_WRITE|PROT_EXEC) == -1)
if (mprotect((caddr_t)(addr->off & (~4095)), 4096,
PROT_READ | PROT_WRITE | PROT_EXEC) == -1)
{
perror( "Can't set break point" );
return;
}
*(BYTE *)addr = op;
mprotect((caddr_t)(addr & ~4095), 4096, PROT_READ|PROT_EXEC);
*(BYTE *)addr->off = op;
mprotect((caddr_t)(addr->off & ~4095), 4096,
PROT_READ | PROT_EXEC );
}
}
......@@ -80,7 +77,7 @@ void DEBUG_SetBreakpoints( BOOL set )
for (i = 0; i < MAX_BREAKPOINTS; i++)
{
if (breakpoints[i].in_use && breakpoints[i].enabled)
DEBUG_SetOpcode( breakpoints[i].segment, breakpoints[i].addr,
DEBUG_SetOpcode( &breakpoints[i].addr,
set ? INT3 : breakpoints[i].opcode );
}
}
......@@ -92,15 +89,15 @@ void DEBUG_SetBreakpoints( BOOL set )
* Find the breakpoint for a given address. Return the breakpoint
* number or -1 if none.
*/
int DEBUG_FindBreakpoint( unsigned int segment, unsigned int addr )
int DEBUG_FindBreakpoint( const DBG_ADDR *addr )
{
int i;
for (i = 0; i < MAX_BREAKPOINTS; i++)
{
if (breakpoints[i].in_use && breakpoints[i].enabled &&
breakpoints[i].segment == segment && breakpoints[i].addr == addr)
return i;
breakpoints[i].addr.seg == addr->seg &&
breakpoints[i].addr.off == addr->off) return i;
}
return -1;
}
......@@ -111,13 +108,13 @@ int DEBUG_FindBreakpoint( unsigned int segment, unsigned int addr )
*
* Add a breakpoint.
*/
void DEBUG_AddBreakpoint( unsigned int segment, unsigned int addr )
void DEBUG_AddBreakpoint( const DBG_ADDR *address )
{
DBG_ADDR addr = *address;
int num;
BYTE *p;
if (segment == 0xffffffff) segment = CS;
if (segment == WINE_CODE_SELECTOR) segment = 0;
DBG_FIX_ADDR_SEG( &addr, CS_reg(DEBUG_context) );
if (next_bp < MAX_BREAKPOINTS)
num = next_bp++;
......@@ -131,16 +128,15 @@ void DEBUG_AddBreakpoint( unsigned int segment, unsigned int addr )
return;
}
}
p = segment ? (BYTE *)PTR_SEG_OFF_TO_LIN( segment, addr ) : (BYTE *)addr;
breakpoints[num].segment = segment;
p = DBG_ADDR_TO_LIN( &addr );
breakpoints[num].addr = addr;
breakpoints[num].addrlen = !segment ? 32 :
(GET_SEL_FLAGS(segment) & LDT_FLAGS_32BIT) ? 32 : 16;
breakpoints[num].addrlen = !addr.seg ? 32 :
(GET_SEL_FLAGS(addr.seg) & LDT_FLAGS_32BIT) ? 32 : 16;
breakpoints[num].opcode = *p;
breakpoints[num].enabled = TRUE;
breakpoints[num].in_use = TRUE;
fprintf( stderr, "Breakpoint %d at ", num );
print_address( segment, addr, breakpoints[num].addrlen );
DEBUG_PrintAddress( &breakpoints[num].addr, breakpoints[num].addrlen );
fprintf( stderr, "\n" );
}
......@@ -193,8 +189,7 @@ void DEBUG_InfoBreakpoints(void)
if (breakpoints[i].in_use)
{
fprintf( stderr, "%d: %c ", i, breakpoints[i].enabled ? 'y' : 'n');
print_address( breakpoints[i].segment, breakpoints[i].addr,
breakpoints[i].addrlen );
DEBUG_PrintAddress( &breakpoints[i].addr, breakpoints[i].addrlen );
fprintf( stderr, "\n" );
}
}
......@@ -210,22 +205,24 @@ void DEBUG_InfoBreakpoints(void)
BOOL DEBUG_ShouldContinue( struct sigcontext_struct *context,
enum exec_mode mode )
{
unsigned int segment, addr;
DBG_ADDR addr;
int bpnum;
/* If not single-stepping, back up over the int3 instruction */
if (!(EFL & STEP_FLAG)) EIP--;
if (!(EFL_reg(DEBUG_context) & STEP_FLAG)) EIP_reg(DEBUG_context)--;
segment = (CS == WINE_CODE_SELECTOR) ? 0 : CS;
addr = EIP;
bpnum = DEBUG_FindBreakpoint( segment, addr );
addr.seg = (CS_reg(DEBUG_context) == WINE_CODE_SELECTOR) ?
0 : CS_reg(DEBUG_context);
addr.off = EIP_reg(DEBUG_context);
bpnum = DEBUG_FindBreakpoint( &addr );
breakpoints[0].enabled = 0; /* disable the step-over breakpoint */
if ((bpnum != 0) && (bpnum != -1))
{
fprintf( stderr, "Stopped on breakpoint %d at ", bpnum );
print_address( breakpoints[bpnum].segment, breakpoints[bpnum].addr,
breakpoints[bpnum].addrlen );
DEBUG_PrintAddress( &breakpoints[bpnum].addr,
breakpoints[bpnum].addrlen );
fprintf( stderr, "\n" );
return FALSE;
}
......@@ -243,34 +240,34 @@ BOOL DEBUG_ShouldContinue( struct sigcontext_struct *context,
void DEBUG_RestartExecution( struct sigcontext_struct *context,
enum exec_mode mode, int instr_len )
{
unsigned int segment, addr;
DBG_ADDR addr;
segment = (CS == WINE_CODE_SELECTOR) ? 0 : CS;
addr = EIP;
addr.seg = (CS_reg(DEBUG_context) == WINE_CODE_SELECTOR) ?
0 : CS_reg(DEBUG_context);
addr.off = EIP_reg(DEBUG_context);
if (DEBUG_FindBreakpoint( segment, addr ) != -1)
if (DEBUG_FindBreakpoint( &addr ) != -1)
mode = EXEC_STEP_INSTR; /* If there's a breakpoint, skip it */
switch(mode)
{
case EXEC_CONT: /* Continuous execution */
EFL &= ~STEP_FLAG;
EFL_reg(DEBUG_context) &= ~STEP_FLAG;
DEBUG_SetBreakpoints( TRUE );
break;
case EXEC_STEP_OVER: /* Stepping over a call */
EFL &= ~STEP_FLAG;
breakpoints[0].segment = segment;
breakpoints[0].addr = addr + instr_len;
EFL_reg(DEBUG_context) &= ~STEP_FLAG;
addr.off += instr_len;
breakpoints[0].addr = addr;
breakpoints[0].enabled = TRUE;
breakpoints[0].in_use = TRUE;
breakpoints[0].opcode = segment ?
*(BYTE *)PTR_SEG_OFF_TO_LIN(segment,addr+instr_len) : *(BYTE *)addr;
breakpoints[0].opcode = *(BYTE *)DBG_ADDR_TO_LIN( &addr );
DEBUG_SetBreakpoints( TRUE );
break;
case EXEC_STEP_INSTR: /* Single-stepping an instruction */
EFL |= STEP_FLAG;
EFL_reg(DEBUG_context) |= STEP_FLAG;
break;
}
}
%{
/* Parser for command lines in the Wine debugger
/*
* Parser for command lines in the Wine debugger
*
* Version 1.0
* Eric Youngdale
* 9/93
* Copyright 1993 Eric Youngdale
*/
#include <stdio.h>
......@@ -14,8 +12,6 @@
#include "windows.h"
#include "debugger.h"
#define YYSTYPE int
extern FILE * yyin;
unsigned int dbg_mode = 0;
......@@ -23,35 +19,31 @@ static enum exec_mode dbg_exec_mode = EXEC_CONT;
void issue_prompt(void);
void mode_command(int);
void flush_symbols(void);
int yylex(void);
int yyerror(char *);
%}
%union
{
DBG_ADDR address;
enum debug_regs reg;
char * string;
int integer;
}
%token CONT
%token STEP
%token NEXT
%token QUIT
%token HELP
%token BACKTRACE
%token INFO
%token STACK
%token SEGMENTS
%token REG
%token REGS
%token NUM
%token ENABLE
%token DISABLE
%token BREAK
%token DELETE
%token SET
%token MODE
%token PRINT
%token EXAM
%token IDENTIFIER
%token FORMAT
%token CONT STEP NEXT QUIT HELP BACKTRACE INFO STACK SEGMENTS REGS
%token ENABLE DISABLE BREAK DELETE SET MODE PRINT EXAM DEFINE ABORT
%token NO_SYMBOL
%token SYMBOLFILE
%token DEFINE
%token ABORT
%token <string> IDENTIFIER
%token <integer> NUM FORMAT
%token <reg> REG
%type <integer> expr
%type <address> addr symbol
%%
......@@ -62,19 +54,21 @@ void mode_command(int);
| infocmd '\n'
| error '\n' { yyerrok; }
| QUIT '\n' { exit(0); }
| HELP '\n' { dbg_help(); }
| HELP '\n' { DEBUG_Help(); }
| CONT '\n' { dbg_exec_mode = EXEC_CONT; return 0; }
| STEP '\n' { dbg_exec_mode = EXEC_STEP_INSTR; return 0; }
| NEXT '\n' { dbg_exec_mode = EXEC_STEP_OVER; return 0; }
| ABORT '\n' { kill(getpid(), SIGABRT); }
| SYMBOLFILE IDENTIFIER '\n' { read_symboltable($2); }
| DEFINE IDENTIFIER expr '\n' { add_hash($2, 0, $3); }
| SYMBOLFILE IDENTIFIER '\n' { DEBUG_ReadSymbolTable( $2 ); }
| DEFINE IDENTIFIER addr '\n' { DEBUG_AddSymbol( $2, &$3 ); }
| MODE NUM '\n' { mode_command($2); }
| ENABLE NUM '\n' { DEBUG_EnableBreakpoint( $2, TRUE ); }
| DISABLE NUM '\n' { DEBUG_EnableBreakpoint( $2, FALSE ); }
| BREAK '*' expr '\n' { DEBUG_AddBreakpoint( 0xffffffff, $3 ); }
| BREAK '*' expr ':' expr '\n' { DEBUG_AddBreakpoint( $3, $5); }
| BREAK '\n' { DEBUG_AddBreakpoint( 0xffffffff, EIP ); }
| BREAK '*' addr '\n' { DEBUG_AddBreakpoint( &$3 ); }
| BREAK '\n' { DBG_ADDR addr = { CS_reg(DEBUG_context),
EIP_reg(DEBUG_context) };
DEBUG_AddBreakpoint( &addr );
}
| DELETE BREAK NUM '\n' { DEBUG_DelBreakpoint( $3 ); }
| BACKTRACE '\n' { DEBUG_BackTrace(); }
| x_command
......@@ -82,38 +76,41 @@ void mode_command(int);
| deposit_command
deposit_command:
SET REG '=' expr '\n' { DEBUG_SetRegister( $2, $4 ); }
| SET '*' expr '=' expr '\n' { *((unsigned int *) $3) = $5; }
| SET symbol '=' expr '\n' { *((unsigned int *) $2) = $4; }
SET REG '=' expr '\n' { DEBUG_SetRegister( $2, $4 ); }
| SET '*' addr '=' expr '\n' { DEBUG_WriteMemory( &$3, $5 ); }
| SET IDENTIFIER '=' addr '\n' { if (!DEBUG_SetSymbolValue( $2, &$4 ))
{
fprintf( stderr, "Symbol %s not found\n", $2 );
YYERROR;
}
}
x_command:
EXAM expr '\n' { examine_memory( 0xffffffff, $2, 1, 'x'); }
| EXAM FORMAT expr '\n' { examine_memory( 0xffffffff, $3,
$2 >> 8, $2 & 0xff ); }
| EXAM expr ':' expr '\n' { examine_memory( $2, $4, 1, 'x' ); }
| EXAM FORMAT expr ':' expr'\n' { examine_memory( $3, $5,
$2 >> 8, $2 & 0xff ); }
EXAM addr '\n' { DEBUG_ExamineMemory( &$2, 1, 'x'); }
| EXAM FORMAT addr '\n' { DEBUG_ExamineMemory( &$3, $2>>8, $2&0xff ); }
print_command:
PRINT expr '\n' { examine_memory( 0, ((unsigned int) &$2 ), 1,'x'); }
| PRINT FORMAT expr '\n' { examine_memory( 0, (unsigned int)&$3,
$2 >> 8, $2 & 0xff ); }
PRINT addr '\n' { DEBUG_Print( &$2, 1, 'x' ); }
| PRINT FORMAT addr '\n' { DEBUG_Print( &$3, $2 >> 8, $2 & 0xff ); }
symbol: IDENTIFIER { if (($$ = find_hash($1)) == 0xffffffff)
symbol: IDENTIFIER { if (!DEBUG_GetSymbolValue( $1, &$$ ))
{
fprintf(stderr,"Symbol %s not found\n", (char *)$1);
fprintf( stderr, "Symbol %s not found\n", $1 );
YYERROR;
}
}
addr: expr { $$.seg = 0xffffffff; $$.off = $1; }
| expr ':' expr { $$.seg = $1; $$.off = $3; }
| symbol { $$ = $1; }
expr: NUM { $$ = $1; }
| REG { $$ = DEBUG_GetRegister($1); }
| symbol { $$ = $1; }
| expr '+' NUM { $$ = $1 + $3; }
| expr '-' NUM { $$ = $1 - $3; }
| '(' expr ')' { $$ = $2; }
| '*' expr { $$ = *((unsigned int *) $2); }
| '*' addr { $$ = DEBUG_ReadMemory( &$2 ); }
infocmd: INFO REGS { DEBUG_InfoRegisters(); }
| INFO STACK { DEBUG_InfoStack(); }
......@@ -147,33 +144,39 @@ void wine_debug( int signal, struct sigcontext_struct *regs )
#endif
yyin = stdin;
context = (struct sigcontext_struct *)regs;
DEBUG_context = (struct sigcontext_struct *)regs;
if (CS == WINE_CODE_SELECTOR) newmode = 32;
else newmode = (GET_SEL_FLAGS(CS) & LDT_FLAGS_32BIT) ? 32 : 16;
if (newmode != dbg_mode)
fprintf(stderr,"In %d bit mode.\n", dbg_mode = newmode);
DEBUG_SetBreakpoints( FALSE );
if(dbg_mode == 32 && !loaded_symbols)
if (!loaded_symbols)
{
loaded_symbols++;
GetPrivateProfileString("wine", "SymbolTableFile", "wine.sym",
SymbolTableFile, sizeof(SymbolTableFile), WINE_INI);
read_symboltable(SymbolTableFile);
DEBUG_ReadSymbolTable( SymbolTableFile );
DEBUG_LoadEntryPoints();
}
DEBUG_SetBreakpoints( FALSE );
if ((signal != SIGTRAP) || !DEBUG_ShouldContinue( regs, dbg_exec_mode ))
{
unsigned int segment = (CS == WINE_CODE_SELECTOR) ? 0 : CS;
DBG_ADDR addr;
addr.seg = (CS_reg(DEBUG_context) == WINE_CODE_SELECTOR) ?
0 : CS_reg(DEBUG_context);
addr.off = EIP_reg(DEBUG_context);
if (!addr.seg) newmode = 32;
else newmode = (GET_SEL_FLAGS(addr.seg) & LDT_FLAGS_32BIT) ? 32 : 16;
if (newmode != dbg_mode)
fprintf(stderr,"In %d bit mode.\n", dbg_mode = newmode);
/* Show where we crashed */
print_address( segment, EIP, dbg_mode );
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
instr_len = db_disasm( segment, EIP ) - EIP;
DEBUG_Disasm( &addr );
fprintf(stderr,"\n");
instr_len = addr.off - EIP_reg(DEBUG_context);
issue_prompt();
yyparse();
......
......@@ -9,8 +9,8 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "dbg.tab.h"
#include "debugger.h"
#include "dbg.tab.h"
#ifdef USE_READLINE
#undef YY_INPUT
......@@ -25,7 +25,6 @@ static int dbg_read(char * buf, int size);
static char * make_symbol(char *);
void flush_symbols();
static int syntax_error;
extern int yylval;
%}
DIGIT [0-9]
......@@ -39,37 +38,39 @@ IDENTIFIER [_a-zA-Z\.~][_a-zA-Z0-9\.~]*
[-+=()*:] { return *yytext; }
"0x"{HEXDIGIT}+ { sscanf(yytext, "%x", &yylval); return NUM; }
{DIGIT}+ { sscanf(yytext, "%d", &yylval); return NUM; }
"/"{DIGIT}+{FORMAT} { char *last; yylval = strtol( yytext+1, &last, NULL );
yylval = (yylval << 8) | *last; return FORMAT; }
"/"{FORMAT} { yylval = (1 << 8) | yytext[1]; return FORMAT; }
$pc { yylval = REG_EIP; return REG; }
$flags { yylval = REG_EFL; return REG; }
$eip { yylval = REG_EIP; return REG; }
$ip { yylval = REG_IP; return REG; }
$esp { yylval = REG_ESP; return REG; }
$sp { yylval = REG_SP; return REG; }
$eax { yylval = REG_EAX; return REG; }
$ebx { yylval = REG_EBX; return REG; }
$ecx { yylval = REG_ECX; return REG; }
$edx { yylval = REG_EDX; return REG; }
$esi { yylval = REG_ESI; return REG; }
$edi { yylval = REG_EDI; return REG; }
$ebp { yylval = REG_EBP; return REG; }
$ax { yylval = REG_AX; return REG; }
$bx { yylval = REG_BX; return REG; }
$cx { yylval = REG_CX; return REG; }
$dx { yylval = REG_DX; return REG; }
$si { yylval = REG_SI; return REG; }
$di { yylval = REG_DI; return REG; }
$bp { yylval = REG_BP; return REG; }
$es { yylval = REG_ES; return REG; }
$ds { yylval = REG_DS; return REG; }
$cs { yylval = REG_CS; return REG; }
$ss { yylval = REG_SS; return REG; }
"0x"{HEXDIGIT}+ { sscanf(yytext, "%x", &yylval.integer); return NUM; }
{DIGIT}+ { sscanf(yytext, "%d", &yylval.integer); return NUM; }
"/"{DIGIT}+{FORMAT} { char * last;
yylval.integer = strtol( yytext+1, &last, NULL );
yylval.integer = (yylval.integer << 8) | *last;
return FORMAT; }
"/"{FORMAT} { yylval.integer = (1 << 8) | yytext[1]; return FORMAT; }
$pc { yylval.reg = REG_EIP; return REG; }
$flags { yylval.reg = REG_EFL; return REG; }
$eip { yylval.reg = REG_EIP; return REG; }
$ip { yylval.reg = REG_IP; return REG; }
$esp { yylval.reg = REG_ESP; return REG; }
$sp { yylval.reg = REG_SP; return REG; }
$eax { yylval.reg = REG_EAX; return REG; }
$ebx { yylval.reg = REG_EBX; return REG; }
$ecx { yylval.reg = REG_ECX; return REG; }
$edx { yylval.reg = REG_EDX; return REG; }
$esi { yylval.reg = REG_ESI; return REG; }
$edi { yylval.reg = REG_EDI; return REG; }
$ebp { yylval.reg = REG_EBP; return REG; }
$ax { yylval.reg = REG_AX; return REG; }
$bx { yylval.reg = REG_BX; return REG; }
$cx { yylval.reg = REG_CX; return REG; }
$dx { yylval.reg = REG_DX; return REG; }
$si { yylval.reg = REG_SI; return REG; }
$di { yylval.reg = REG_DI; return REG; }
$bp { yylval.reg = REG_BP; return REG; }
$es { yylval.reg = REG_ES; return REG; }
$ds { yylval.reg = REG_DS; return REG; }
$cs { yylval.reg = REG_CS; return REG; }
$ss { yylval.reg = REG_SS; return REG; }
info|inf|in { return INFO; }
segments|segm { return SEGMENTS; }
......@@ -103,14 +104,14 @@ registers|regs|reg|re { return REGS; }
stack|stac|sta|st { return STACK; }
{IDENTIFIER} {yylval = (int) make_symbol(yytext);
return IDENTIFIER;
}
{IDENTIFIER} { yylval.string = make_symbol(yytext); return IDENTIFIER; }
[ \t]+ /* Eat up whitespace */
. { if(syntax_error == 0) {
syntax_error ++; fprintf(stderr, "Syntax Error\n"); }
. { if (syntax_error == 0)
{
syntax_error ++; fprintf(stderr, "Syntax Error\n");
}
}
%%
......@@ -124,11 +125,6 @@ int yywrap(void) { return 1; }
#define whitespace(c) (((c) == ' ') || ((c) == '\t'))
#endif
#if 0
/* Used only with GNU readline */
#include "readline/readline.h"
#include "readline/chardefs.h"
#endif
/* Strip whitespace from the start and end of STRING. */
static void stripwhite (char *string)
......@@ -161,18 +157,22 @@ static int dbg_read(char * buf, int size)
line = readline ("Wine-dbg>");
if (!line) exit(0);
/* Remove leading and trailing whitespace from the line.
Then, if there is anything left, add it to the history list
and execute it. */
/* Remove leading and trailing whitespace from the line */
stripwhite (line);
/* If there is anything left, add it to the history list
and execute it. Otherwise, re-execute last command. */
if (*line)
{
add_history( line );
strncpy( last_line, line, 255 );
last_line[255] = '\0';
}
else line = last_line; /* Repeat previous command */
free( line );
line = last_line;
if ((len = strlen(line)) > 0)
{
......@@ -184,7 +184,6 @@ static int dbg_read(char * buf, int size)
strcpy(buf, line);
buf[len] = '\n';
buf[len+1] = 0;
free(line);
return len + 1;
}
}
......
/*
* Wine debugger utility routines
* Eric Youngdale
* 9/93
*
* Copyright 1993 Eric Youngdale
* Copyright 1995 Alexandre Julliard
*/
#include <stdio.h>
#include <stdlib.h>
#include "debugger.h"
extern char * find_nearest_symbol( unsigned int seg, unsigned int addr );
void print_address( unsigned int segment, unsigned int addr, int addrlen )
/***********************************************************************
* DEBUG_Print
*
* Implementation of the 'print' command.
*/
void DEBUG_Print( const DBG_ADDR *addr, int count, char format )
{
char *name = find_nearest_symbol( segment, addr );
if (count != 1)
{
fprintf( stderr, "Count other than 1 is meaningless in 'print' command\n" );
return;
}
if (segment) fprintf( stderr, "0x%04x:", segment );
if (addrlen == 16) fprintf( stderr, "0x%04x", addr );
else fprintf( stderr, "0x%08x", addr );
if (name) fprintf( stderr, " (%s)", name );
}
if (addr->seg && (addr->seg != 0xffffffff))
{
switch(format)
{
case 'x':
fprintf( stderr, "0x%04lx:", addr->seg );
break;
case 'd':
fprintf( stderr, "%ld:", addr->seg );
break;
void examine_memory( unsigned int segment, unsigned int addr,
int count, char format )
{
char * pnt;
unsigned int * dump;
unsigned short int * wdump;
int i;
case 'c':
break; /* No segment to print */
if (segment == 0xffffffff) segment = (format == 'i' ? CS : DS);
if ((segment == WINE_CODE_SELECTOR) || (segment == WINE_DATA_SELECTOR))
segment = 0;
case 'i':
case 's':
case 'w':
case 'b':
break; /* Meaningless format */
}
}
if (format != 'i' && count > 1)
switch(format)
{
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
case 'x':
if (addr->seg) fprintf( stderr, "0x%04lx\n", addr->off );
else fprintf( stderr, "0x%08lx\n", addr->off );
break;
case 'd':
fprintf( stderr, "%ld\n", addr->off );
break;
case 'c':
fprintf( stderr, "%d = '%c'\n",
(char)(addr->off & 0xff), (char)(addr->off & 0xff) );
break;
case 'i':
case 's':
case 'w':
case 'b':
fprintf( stderr, "Format specifier '%c' is meaningless in 'print' command\n", format );
break;
}
}
pnt = segment ? (char *)PTR_SEG_OFF_TO_LIN(segment,addr) : (char *)addr;
switch(format)
{
case 's':
if (count == 1) count = 256;
while(*pnt && count) {
fputc( *pnt++, stderr);
count--;
};
fprintf(stderr,"\n");
return;
/***********************************************************************
* DEBUG_PrintAddress
*
* Print an 16- or 32-bit address, with the nearest symbol if any.
*/
void DEBUG_PrintAddress( const DBG_ADDR *addr, int addrlen )
{
const char *name = DEBUG_FindNearestSymbol( addr );
case 'i':
for(i=0; i<count; i++) {
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
addr = db_disasm( segment, addr );
fprintf(stderr,"\n");
};
return;
case 'x':
dump = (unsigned int *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %8.8x", *dump++);
addr += 4;
if ((i % 8) == 7) {
fprintf(stderr,"\n");
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'd':
dump = (unsigned int *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %d", *dump++);
addr += 4;
if ((i % 8) == 7) {
fprintf(stderr,"\n");
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'w':
wdump = (unsigned short *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %04x", *wdump++);
addr += 2;
if ((i % 10) == 7) {
fprintf(stderr,"\n");
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'c':
for(i=0; i<count; i++)
{
if(*pnt < 0x20) {
fprintf(stderr," ");
pnt++;
} else
fprintf(stderr," %c", *pnt++);
addr++;
if ((i % 32) == 7) {
fprintf(stderr,"\n");
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'b':
for(i=0; i<count; i++)
{
fprintf(stderr," %02x", (*pnt++) & 0xff);
addr++;
if ((i % 32) == 7) {
fprintf(stderr,"\n");
print_address( segment, addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
};
/* The rest are fairly straightforward */
fprintf(stderr,"examine mem: %x %d %c\n", addr, count, format);
if (addr->seg) fprintf( stderr, "0x%04lx:", addr->seg );
if (addrlen == 16) fprintf( stderr, "0x%04lx", addr->off );
else fprintf( stderr, "0x%08lx", addr->off );
if (name) fprintf( stderr, " (%s)", name );
}
char * helptext[] = {
/***********************************************************************
* DEBUG_Help
*
* Implementation of the 'help' command.
*/
void DEBUG_Help(void)
{
int i = 0;
static const char * helptext[] =
{
"The commands accepted by the Wine debugger are a small subset",
"of the commands that gdb would accept. The commands currently",
"are:\n",
" break [*<addr>] delete break bpnum",
" disable bpnum enable bpnum",
" help quit",
" x <expr> cont",
" x <addr> cont",
" step next",
" mode [16,32] print <expr>",
" set <reg> = <expr> set *<expr> = <expr>",
" set <reg> = <expr> set *<addr> = <expr>",
" info [reg,stack,break,segments] bt",
" symbolfile <filename> define <identifier> <expr>",
" symbolfile <filename> define <identifier> <addr>",
"",
"The 'x' command accepts repeat counts and formats (including 'i') in the",
"same way that gdb does.",
......@@ -166,10 +120,8 @@ char * helptext[] = {
" symbolfile command. Symbols can also be defined individually with",
" the define command.",
"",
NULL};
NULL
};
void dbg_help(){
int i;
i = 0;
while(helptext[i]) fprintf(stderr,"%s\n", helptext[i++]);
while(helptext[i]) fprintf(stderr,"%s\n", helptext[i++]);
}
/*
* Debugger memory handling
*
* Copyright 1993 Eric Youngdale
* Copyright 1995 Alexandre Julliard
*/
#include <stdio.h>
#include <stdlib.h>
#include "debugger.h"
/***********************************************************************
* DEBUG_ReadMemory
*
* Read a memory value.
*/
int DEBUG_ReadMemory( const DBG_ADDR *address )
{
DBG_ADDR addr = *address;
DBG_FIX_ADDR_SEG( &addr, DS_reg(DEBUG_context) );
return *(int *)DBG_ADDR_TO_LIN( &addr );
}
/***********************************************************************
* DEBUG_WriteMemory
*
* Store a value in memory.
*/
void DEBUG_WriteMemory( const DBG_ADDR *address, int value )
{
DBG_ADDR addr = *address;
DBG_FIX_ADDR_SEG( &addr, DS_reg(DEBUG_context) );
*(int *)DBG_ADDR_TO_LIN( &addr ) = value;
}
/***********************************************************************
* DEBUG_ExamineMemory
*
* Implementation of the 'x' command.
*/
void DEBUG_ExamineMemory( const DBG_ADDR *address, int count, char format )
{
DBG_ADDR addr = *address;
unsigned char * pnt;
unsigned int * dump;
unsigned short int * wdump;
int i;
DBG_FIX_ADDR_SEG( &addr, (format == 'i') ?
CS_reg(DEBUG_context) : DS_reg(DEBUG_context) );
if (format != 'i' && count > 1)
{
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
}
pnt = DBG_ADDR_TO_LIN( &addr );
switch(format)
{
case 's':
if (count == 1) count = 256;
while(*pnt && count--) fputc( *pnt++, stderr );
fprintf(stderr,"\n");
return;
case 'i':
while (count--)
{
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
DEBUG_Disasm( &addr );
fprintf(stderr,"\n");
}
return;
case 'x':
dump = (unsigned int *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %8.8x", *dump++);
addr.off += 4;
if ((i % 8) == 7) {
fprintf(stderr,"\n");
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'd':
dump = (unsigned int *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %d", *dump++);
addr.off += 4;
if ((i % 8) == 7) {
fprintf(stderr,"\n");
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'w':
wdump = (unsigned short *)pnt;
for(i=0; i<count; i++)
{
fprintf(stderr," %04x", *wdump++);
addr.off += 2;
if ((i % 10) == 7) {
fprintf(stderr,"\n");
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'c':
for(i=0; i<count; i++)
{
if(*pnt < 0x20) {
fprintf(stderr," ");
pnt++;
} else
fprintf(stderr," %c", *pnt++);
addr.off++;
if ((i % 32) == 7) {
fprintf(stderr,"\n");
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
case 'b':
for(i=0; i<count; i++)
{
fprintf(stderr," %02x", (*pnt++) & 0xff);
addr.off++;
if ((i % 32) == 7) {
fprintf(stderr,"\n");
DEBUG_PrintAddress( &addr, dbg_mode );
fprintf(stderr,": ");
};
}
fprintf(stderr,"\n");
return;
}
}
......@@ -5,7 +5,7 @@ TOPSRC = @top_srcdir@
DIVINCL = -I$(TOPSRC)/include
LD = @LD@
LDCOMBINEFLAGS = @LDCOMBINEFLAGS@
DIVDEFS = -DHIDE -DANSI_ARROWS
DIVDEFS = @DEFS@ -DHIDE -DANSI_ARROWS
MODULE = readline
......@@ -25,26 +25,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -3,7 +3,10 @@
** Unix system-dependant routines for editline library.
*/
#include "editline.h"
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#if defined(HAVE_TCGETATTR)
#include <termios.h>
......
......@@ -8,7 +8,7 @@
#include "debugger.h"
struct sigcontext_struct *context;
struct sigcontext_struct *DEBUG_context;
......@@ -21,30 +21,30 @@ void DEBUG_SetRegister( enum debug_regs reg, int val )
{
switch(reg)
{
case REG_EAX: EAX = val; break;
case REG_EBX: EBX = val; break;
case REG_ECX: ECX = val; break;
case REG_EDX: EDX = val; break;
case REG_ESI: ESI = val; break;
case REG_EDI: EDI = val; break;
case REG_EBP: EBP = val; break;
case REG_EFL: EFL = val; break;
case REG_EIP: EIP = val; break;
case REG_ESP: ESP = val; break;
case REG_AX: AX = val; break;
case REG_BX: BX = val; break;
case REG_CX: CX = val; break;
case REG_DX: DX = val; break;
case REG_SI: SI = val; break;
case REG_DI: DI = val; break;
case REG_BP: BP = val; break;
case REG_FL: FL = val; break;
case REG_IP: IP = val; break;
case REG_SP: SP = val; break;
case REG_CS: CS = val; break;
case REG_DS: DS = val; break;
case REG_ES: ES = val; break;
case REG_SS: SS = val; break;
case REG_EAX: EAX_reg(DEBUG_context) = val; break;
case REG_EBX: EBX_reg(DEBUG_context) = val; break;
case REG_ECX: ECX_reg(DEBUG_context) = val; break;
case REG_EDX: EDX_reg(DEBUG_context) = val; break;
case REG_ESI: ESI_reg(DEBUG_context) = val; break;
case REG_EDI: EDI_reg(DEBUG_context) = val; break;
case REG_EBP: EBP_reg(DEBUG_context) = val; break;
case REG_EFL: EFL_reg(DEBUG_context) = val; break;
case REG_EIP: EIP_reg(DEBUG_context) = val; break;
case REG_ESP: ESP_reg(DEBUG_context) = val; break;
case REG_AX: AX_reg(DEBUG_context) = val; break;
case REG_BX: BX_reg(DEBUG_context) = val; break;
case REG_CX: CX_reg(DEBUG_context) = val; break;
case REG_DX: DX_reg(DEBUG_context) = val; break;
case REG_SI: SI_reg(DEBUG_context) = val; break;
case REG_DI: DI_reg(DEBUG_context) = val; break;
case REG_BP: BP_reg(DEBUG_context) = val; break;
case REG_FL: FL_reg(DEBUG_context) = val; break;
case REG_IP: IP_reg(DEBUG_context) = val; break;
case REG_SP: SP_reg(DEBUG_context) = val; break;
case REG_CS: CS_reg(DEBUG_context) = val; break;
case REG_DS: DS_reg(DEBUG_context) = val; break;
case REG_ES: ES_reg(DEBUG_context) = val; break;
case REG_SS: SS_reg(DEBUG_context) = val; break;
}
}
......@@ -58,30 +58,30 @@ int DEBUG_GetRegister( enum debug_regs reg )
{
switch(reg)
{
case REG_EAX: return EAX;
case REG_EBX: return EBX;
case REG_ECX: return ECX;
case REG_EDX: return EDX;
case REG_ESI: return ESI;
case REG_EDI: return EDI;
case REG_EBP: return EBP;
case REG_EFL: return EFL;
case REG_EIP: return EIP;
case REG_ESP: return ESP;
case REG_AX: return AX;
case REG_BX: return BX;
case REG_CX: return CX;
case REG_DX: return DX;
case REG_SI: return SI;
case REG_DI: return DI;
case REG_BP: return BP;
case REG_FL: return FL;
case REG_IP: return IP;
case REG_SP: return SP;
case REG_CS: return CS;
case REG_DS: return DS;
case REG_ES: return ES;
case REG_SS: return SS;
case REG_EAX: return EAX_reg(DEBUG_context);
case REG_EBX: return EBX_reg(DEBUG_context);
case REG_ECX: return ECX_reg(DEBUG_context);
case REG_EDX: return EDX_reg(DEBUG_context);
case REG_ESI: return ESI_reg(DEBUG_context);
case REG_EDI: return EDI_reg(DEBUG_context);
case REG_EBP: return EBP_reg(DEBUG_context);
case REG_EFL: return EFL_reg(DEBUG_context);
case REG_EIP: return EIP_reg(DEBUG_context);
case REG_ESP: return ESP_reg(DEBUG_context);
case REG_AX: return AX_reg(DEBUG_context);
case REG_BX: return BX_reg(DEBUG_context);
case REG_CX: return CX_reg(DEBUG_context);
case REG_DX: return DX_reg(DEBUG_context);
case REG_SI: return SI_reg(DEBUG_context);
case REG_DI: return DI_reg(DEBUG_context);
case REG_BP: return BP_reg(DEBUG_context);
case REG_FL: return FL_reg(DEBUG_context);
case REG_IP: return IP_reg(DEBUG_context);
case REG_SP: return SP_reg(DEBUG_context);
case REG_CS: return CS_reg(DEBUG_context);
case REG_DS: return DS_reg(DEBUG_context);
case REG_ES: return ES_reg(DEBUG_context);
case REG_SS: return SS_reg(DEBUG_context);
}
return 0; /* should not happen */
}
......@@ -98,22 +98,30 @@ void DEBUG_InfoRegisters(void)
fprintf(stderr,"Register dump:\n");
/* First get the segment registers out of the way */
fprintf( stderr," CS:%04x SS:%04x DS:%04x ES:%04x\n", CS, SS, DS, ES );
fprintf( stderr," CS:%04x SS:%04x DS:%04x ES:%04x\n",
CS_reg(DEBUG_context), SS_reg(DEBUG_context),
DS_reg(DEBUG_context), ES_reg(DEBUG_context) );
if (dbg_mode == 16)
{
fprintf( stderr," IP:%04x SP:%04x BP:%04x FLAGS:%04x\n",
IP, SP, BP, FL );
IP_reg(DEBUG_context), SP_reg(DEBUG_context),
BP_reg(DEBUG_context), FL_reg(DEBUG_context) );
fprintf( stderr," AX:%04x BX:%04x CX:%04x DX:%04x SI:%04x DI:%04x\n",
AX, BX, CX, DX, SI, DI );
AX_reg(DEBUG_context), BX_reg(DEBUG_context),
CX_reg(DEBUG_context), DX_reg(DEBUG_context),
SI_reg(DEBUG_context), DI_reg(DEBUG_context) );
}
else /* 32-bit mode */
{
fprintf( stderr, " EIP:%08lx ESP:%08lx EBP:%08lx EFLAGS:%08lx\n",
EIP, ESP, EBP, EFL );
EIP_reg(DEBUG_context), ESP_reg(DEBUG_context),
EBP_reg(DEBUG_context), EFL_reg(DEBUG_context) );
fprintf( stderr, " EAX:%08lx EBX:%08lx ECX:%08lx EDX:%08lx\n",
EAX, EBX, ECX, EDX);
fprintf( stderr, " ESI:%08lx EDI:%08lx\n", ESI, EDI);
EAX_reg(DEBUG_context), EBX_reg(DEBUG_context),
ECX_reg(DEBUG_context), EDX_reg(DEBUG_context) );
fprintf( stderr, " ESI:%08lx EDI:%08lx\n",
ESI_reg(DEBUG_context), EDI_reg(DEBUG_context) );
}
}
......@@ -32,15 +32,21 @@ typedef struct
*/
void DEBUG_InfoStack(void)
{
DBG_ADDR addr;
fprintf(stderr,"Stack dump:\n");
if ((SS == WINE_DATA_SELECTOR) ||
(GET_SEL_FLAGS(SS) & LDT_FLAGS_32BIT)) /* 32-bit mode */
{
examine_memory( 0, ESP, 10, 'x' );
if ((SS_reg(DEBUG_context) == WINE_DATA_SELECTOR) ||
(GET_SEL_FLAGS(SS_reg(DEBUG_context)) & LDT_FLAGS_32BIT))
{ /* 32-bit mode */
addr.seg = 0;
addr.off = ESP_reg(DEBUG_context);
DEBUG_ExamineMemory( &addr, 10, 'x' );
}
else /* 16-bit mode */
{
examine_memory( SS, SP, 10, 'w' );
addr.seg = SS_reg(DEBUG_context);
addr.off = SP_reg(DEBUG_context);
DEBUG_ExamineMemory( &addr, 10, 'w' );
}
fprintf(stderr,"\n");
}
......@@ -53,25 +59,29 @@ void DEBUG_InfoStack(void)
*/
void DEBUG_BackTrace(void)
{
int frameno = 0;
DBG_ADDR addr;
int frameno = 0;
fprintf(stderr,"Backtrace:\n");
if (SS == WINE_DATA_SELECTOR) /* 32-bit mode */
if (SS_reg(DEBUG_context) == WINE_DATA_SELECTOR) /* 32-bit mode */
{
FRAME32 *frame = (FRAME32 *)EBP;
FRAME32 *frame = (FRAME32 *)EBP_reg(DEBUG_context);
addr.seg = 0;
while (frame->ip)
{
fprintf(stderr,"%d ",frameno++);
print_address( 0, frame->ip, 32 );
addr.off = frame->ip;
DEBUG_PrintAddress( &addr, 32 );
fprintf( stderr, "\n" );
frame = (FRAME32 *)frame->bp;
}
}
else /* 16-bit mode */
{
FRAME16 *frame = (FRAME16 *)PTR_SEG_OFF_TO_LIN( SS, BP & ~1 );
WORD cs = CS;
if (GET_SEL_FLAGS(SS) & LDT_FLAGS_32BIT)
FRAME16 *frame = (FRAME16 *)PTR_SEG_OFF_TO_LIN( SS_reg(DEBUG_context),
BP_reg(DEBUG_context) & ~1 );
WORD cs = CS_reg(DEBUG_context);
if (GET_SEL_FLAGS(SS_reg(DEBUG_context)) & LDT_FLAGS_32BIT)
{
fprintf( stderr, "Not implemented: 32-bit backtrace on a different stack segment.\n" );
return;
......@@ -80,9 +90,12 @@ void DEBUG_BackTrace(void)
{
if (frame->bp & 1) cs = frame->cs;
fprintf( stderr,"%d ", frameno++ );
print_address( cs, frame->ip, 16 );
addr.seg = cs;
addr.off = frame->ip;
DEBUG_PrintAddress( &addr, 16 );
fprintf( stderr, "\n" );
frame = (FRAME16 *)PTR_SEG_OFF_TO_LIN( SS, frame->bp & ~1 );
frame = (FRAME16 *)PTR_SEG_OFF_TO_LIN( SS_reg(DEBUG_context),
frame->bp & ~1 );
}
}
fprintf( stderr, "\n" );
......
......@@ -31,31 +31,21 @@ SFILES = $(DLLS16:.spec=.S)
.c.o:
$(CC) -c $(CFLAGS) $(XINCL) $(DIVINCL) -o $*.o $<
.spec.S:
$(BUILD) -spec16 $< > $*.S
.S.o:
$(CC) -c -o $*.o $<
all: checkbuild $(MODULE).o
gdi32.c: gdi32.spec
$(BUILD) -spec32 gdi32.spec > gdi32.c
kernel32.c: kernel32.spec
$(BUILD) -spec32 kernel32.spec > kernel32.c
.spec.S:
$(BUILD) -spec16 $< > $*.S
shell32.c: shell32.spec
$(BUILD) -spec32 shell32.spec > shell32.c
.spec.c:
$(BUILD) -spec32 $< > $*.c
user32.c: user32.spec
$(BUILD) -spec32 user32.spec > user32.c
all: checkbuild $(MODULE).o
winprocs32.c: winprocs32.spec
$(BUILD) -spec32 winprocs32.spec > winprocs32.c
$(SFILES): $(TOPSRC)/tools/build
checkbuild:
(cd $(TOPSRC)/tools; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)')
cd $(TOPSRC)/tools; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)' build
call16.S: $(TOPSRC)/include/callback.h
$(TOPSRC)/tools/build -call16 `cat $(TOPSRC)/include/callback.h | grep "extern.*CallTo16_" | sed 's/.*CallTo16_\(.*\)(.*/\1/' | sort | uniq` > call16.S
......@@ -63,26 +53,23 @@ call16.S: $(TOPSRC)/include/callback.h
call32.S: $(SFILES)
$(BUILD) -call32 `cat $(SFILES) | grep CallTo32_ | sed 's/.*CallTo32_\(.*\)/\1/' | sort | uniq` > call32.S
$(MODULE).o: $(OBJS)
$(LD) $(LDCOMBINEFLAGS) $(OBJS) -o $(MODULE).o
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM callback.c relay32.c relay.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM $(SRCS) >> tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ *.S gdi32.c kernel32.c shell32.c user32.c winprocs32.c tmp_make
rm -f *.o \#*\# *~ tmp_make
rm -f $(DLLS16:.spec=.S) $(DLLS32:.spec=.c) call32.S call16.S
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
winelibclean:
dummy:
### Dependencies:
......@@ -76,6 +76,7 @@ int Throw( LPCATCHBUF lpbuf, int retval )
pFrame->bp = lpbuf[6];
pFrame->ip = lpbuf[7];
pFrame->cs = lpbuf[8];
pFrame->es = 0;
return retval;
}
......
......@@ -64,8 +64,8 @@ id 1
66 pascal16 AllocResource(word word long) AllocResource
67 stub SetResourceHandler
68 pascal16 InitAtomTable(word) InitAtomTable
69 pascal16 FindAtom(ptr) FindAtom
70 pascal16 AddAtom(ptr) AddAtom
69 pascal16 FindAtom(segptr) FindAtom
70 pascal16 AddAtom(segptr) AddAtom
71 pascal16 DeleteAtom(word) DeleteAtom
72 pascal16 GetAtomName(word ptr word) GetAtomName
73 pascal16 GetAtomHandle(word) GetAtomHandle
......
......@@ -156,7 +156,9 @@ void RELAY_DebugCall32( int func_type, char *args )
{
struct sigcontext_struct *context = (struct sigcontext_struct *)args16;
printf( " AX=%04x BX=%04x CX=%04x DX=%04x SI=%04x DI=%04x ES=%04x EFL=%08lx\n",
AX, BX, CX, DX, SI, DI, ES, EFL );
AX_reg(context), BX_reg(context), CX_reg(context),
DX_reg(context), SI_reg(context), DI_reg(context),
ES_reg(context), EFL_reg(context) );
}
}
......
......@@ -49,7 +49,7 @@ id 2
47 pascal16 IsWindow(word) IsWindow
48 pascal16 IsChild(word word) IsChild
49 pascal16 IsWindowVisible(word) IsWindowVisible
50 pascal16 FindWindow(ptr ptr) FindWindow
50 pascal16 FindWindow(segptr ptr) FindWindow
#51 BEAR51
52 pascal16 AnyPopup() AnyPopup
53 pascal16 DestroyWindow(word) DestroyWindow
......@@ -115,7 +115,7 @@ id 2
114 pascal DispatchMessage(ptr) DispatchMessage
115 stub ReplyMessage
116 pascal16 PostAppMessage(word word word long) PostAppMessage
118 pascal16 RegisterWindowMessage(ptr) RegisterWindowMessage
118 pascal16 RegisterWindowMessage(long) RegisterWindowMessage
119 pascal GetMessagePos() GetMessagePos
120 pascal GetMessageTime() GetMessageTime
121 pascal SetWindowsHook(s_word segptr) SetWindowsHook
......@@ -269,9 +269,9 @@ id 2
265 pascal16 ShowOwnedPopups(word word) ShowOwnedPopups
266 pascal16 SetMessageQueue(word) SetMessageQueue
267 pascal16 ShowScrollBar(word word word) ShowScrollBar
268 pascal16 GlobalAddAtom(ptr) GlobalAddAtom
268 pascal16 GlobalAddAtom(segptr) GlobalAddAtom
269 pascal16 GlobalDeleteAtom(word) GlobalDeleteAtom
270 pascal16 GlobalFindAtom(ptr) GlobalFindAtom
270 pascal16 GlobalFindAtom(segptr) GlobalFindAtom
271 pascal16 GlobalGetAtomName(word ptr s_word) GlobalGetAtomName
272 pascal16 IsZoomed(word) IsZoomed
273 stub ControlPanelInfo
......@@ -334,7 +334,7 @@ id 2
400 stub FinalUserInit
402 pascal16 GetPriorityClipboardFormat(word ptr s_word)
GetPriorityClipboardFormat
403 pascal16 UnregisterClass(ptr word) UnregisterClass
403 pascal16 UnregisterClass(segptr word) UnregisterClass
404 pascal16 GetClassInfo(word segptr ptr) GetClassInfo
406 pascal16 CreateCursor(word word word word word ptr ptr) CreateCursor
407 pascal16 CreateIcon(word word word byte byte ptr ptr) CreateIcon
......
......@@ -25,20 +25,10 @@ typedef struct
HANDLE entries[1];
} ATOMTABLE;
#ifdef WINELIB
#define LocalAlign(flags,bytes) LocalAlloc (flags|LMEM_WINE_ALIGN,bytes)
#else
#define LocalAlign(flags,bytes) LocalAlloc((flags),(bytes))
#endif
ATOM LocalAddAtom( LPCSTR str );
ATOM LocalAddAtom( SEGPTR str );
ATOM LocalDeleteAtom( ATOM atom );
ATOM LocalFindAtom( LPCSTR str );
WORD LocalGetAtomName( ATOM atom, LPSTR buffer, short count );
ATOM LocalAddAtom( LPCSTR str );
ATOM LocalDeleteAtom( ATOM atom );
ATOM LocalFindAtom( LPCSTR str );
ATOM LocalFindAtom( SEGPTR str );
WORD LocalGetAtomName( ATOM atom, LPSTR buffer, short count );
#endif /* ATOM_H */
......@@ -32,7 +32,7 @@ typedef struct tagCLASS
#endif
HCLASS CLASS_FindClassByName( char * name, WORD hinstance, CLASS **ptr );
HCLASS CLASS_FindClassByName( SEGPTR name, WORD hinstance, CLASS **ptr );
CLASS * CLASS_FindClassPtr( HCLASS hclass );
......
#undef HAVE_STDLIB_H
#undef HAVE_TCGETATTR
#undef HAVE_DIRENT_H
#undef HAVE_SYS_NDIR_H
#undef HAVE_NDIR_H
#undef STAT_MACROS_BROKEN
......@@ -11,6 +11,20 @@
#include "registers.h"
#include "wine.h"
typedef struct
{
DWORD seg; /* 0xffffffff means current default segment (cs or ds) */
DWORD off;
} DBG_ADDR;
#define DBG_FIX_ADDR_SEG(addr,default) \
{ if ((addr)->seg == 0xffffffff) (addr)->seg = (default); \
if (((addr)->seg == WINE_CODE_SELECTOR) || \
(addr)->seg == WINE_DATA_SELECTOR) (addr)->seg = 0; }
#define DBG_ADDR_TO_LIN(addr) \
((addr)->seg ? (char *)PTR_SEG_OFF_TO_LIN((addr)->seg,(addr)->off) \
: (char *)(addr)->off)
enum debug_regs
{
......@@ -29,13 +43,13 @@ enum exec_mode
EXEC_STEP_INSTR /* Single-stepping an instruction */
};
extern struct sigcontext_struct *context; /* debugger/registers.c */
extern struct sigcontext_struct *DEBUG_context; /* debugger/registers.c */
extern unsigned int dbg_mode;
/* debugger/break.c */
extern void DEBUG_SetBreakpoints( BOOL set );
extern int DEBUG_FindBreakpoint( unsigned int segment, unsigned int addr );
extern void DEBUG_AddBreakpoint( unsigned int segment, unsigned int addr );
extern int DEBUG_FindBreakpoint( const DBG_ADDR *addr );
extern void DEBUG_AddBreakpoint( const DBG_ADDR *addr );
extern void DEBUG_DelBreakpoint( int num );
extern void DEBUG_EnableBreakpoint( int num, BOOL enable );
extern void DEBUG_InfoBreakpoints(void);
......@@ -45,6 +59,27 @@ extern BOOL DEBUG_ShouldContinue( struct sigcontext_struct *context,
extern void DEBUG_RestartExecution( struct sigcontext_struct *context,
enum exec_mode mode, int instr_len );
/* debugger/db_disasm.c */
extern void DEBUG_Disasm( DBG_ADDR *addr );
/* debugger/hash.c */
extern void DEBUG_AddSymbol( const char *name, const DBG_ADDR *addr );
extern BOOL DEBUG_GetSymbolValue( const char * name, DBG_ADDR *addr );
extern BOOL DEBUG_SetSymbolValue( const char * name, const DBG_ADDR *addr );
extern const char * DEBUG_FindNearestSymbol( const DBG_ADDR *addr );
extern void DEBUG_ReadSymbolTable( const char * filename );
extern void DEBUG_LoadEntryPoints(void);
/* debugger/info.c */
extern void DEBUG_Print( const DBG_ADDR *addr, int count, char format );
extern void DEBUG_PrintAddress( const DBG_ADDR *addr, int addrlen );
extern void DEBUG_Help(void);
/* debugger/memory.c */
extern int DEBUG_ReadMemory( const DBG_ADDR *address );
extern void DEBUG_WriteMemory( const DBG_ADDR *address, int value );
extern void DEBUG_ExamineMemory( const DBG_ADDR *addr, int count, char format);
/* debugger/registers.c */
extern void DEBUG_SetRegister( enum debug_regs reg, int val );
extern int DEBUG_GetRegister( enum debug_regs reg );
......@@ -57,7 +92,4 @@ extern void DEBUG_BackTrace(void);
/* debugger/dbg.y */
extern void wine_debug( int signal, struct sigcontext_struct * regs );
extern void print_address( unsigned int seg, unsigned int addr, int addrlen );
extern unsigned int db_disasm( unsigned int segment, unsigned int loc );
#endif /* DEBUGGER_H */
......@@ -2,7 +2,7 @@
#define __WINE_MISCEMU_H
#include "wintypes.h"
#include "wine.h"
#include "registers.h"
extern BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context );
......@@ -16,10 +16,12 @@ extern void INT_SetHandler( BYTE intnum, SEGPTR handler );
extern void INT21_Init(void);
#define INT_BARF(num) \
#define INT_BARF(context,num) \
fprintf( stderr, "int%x: unknown/not implemented parameters:\n" \
"int%x: AX %04x, BX %04x, CX %04x, DX %04x, " \
"SI %04x, DI %04x, DS %04x, ES %04x\n", \
(num), (num), AX, BX, CX, DX, SI, DI, DS, ES )
(num), (num), AX_reg(context), BX_reg(context), CX_reg(context), \
DX_reg(context), SI_reg(context), DI_reg(context), \
DS_reg(context), ES_reg(context) )
#endif /* __WINE_MISCEMU_H */
......@@ -31,7 +31,9 @@ struct fcb {
BYTE dummy2[9];
};
#define DOSVERSION 0x0005 /* Major version in low byte: DOS 5.00 */
#define DOSVERSION 0x1606 /* Major version in low byte: DOS 6.22 */
#define WINDOSVER 0x0616 /* Windows reports the DOS version reversed */
#define WINVERSION 0x0a03 /* Windows version 3.10 */
#define MAX_DOS_DRIVES 26
......
......@@ -2,9 +2,11 @@
* ole.h - Declarations for OLESVR and OLECLI
*/
typedef LPCSTR OLE_LPCSTR;
typedef enum
{
OLE_OK,
OLE_OK=0, /* Yes Sir! */
OLE_WAIT_FOR_RELEASE,
OLE_BUSY,
OLE_ERROR_PROTECT_ONLY,
......@@ -66,19 +68,141 @@ typedef enum
typedef enum{
OLE_SERVER_MULTI,
OLE_SERVER_SINGLE
}OLE_SERVER_USE;
} OLE_SERVER_USE;
/* dunno if the values are correct, somebody please check */
typedef enum {
OLE_CHANGED,
OLE_CLOSED,
OLE_QUERY_PAINT,
OLE_QUERY_RETRY,
OLE_RELEASE,
OLE_RENAMED,
OLE_SAVED
} OLE_NOTIFICATION;
typedef LONG LHSERVER;
typedef LONG LHSERVERDOC;
typedef LONG LHCLIENTDOC;
typedef LONG OLECLIPFORMAT;/* dunno about this type, please change/add */
typedef LONG OLEOPT_UPDATE;/* dunno about this type, please change/add */
typedef OLEOPT_UPDATE* LPOLEOPT_UPDATE;/* dunno about this type, please change/add */
typedef LONG *OLE_RELEASE_METHOD;/* dunno */
typedef struct _OLESERVER* LPOLESERVER;
typedef struct _OLETARGETDEVICE {
UINT otdDeviceNameOffset;
UINT otdDriverNameOffset;
UINT otdPortNameOffset;
UINT otdExtDevmodeOffset;
UINT otdExtDevmodeSize;
UINT otdEnvironmentOffset;
UINT otdEnvironmentSize;
BYTE otdData[1];
/* ... */
} OLETARGETDEVICE;
typedef struct _OLESTREAM* LPOLESTREAM;
typedef struct _OLESTREAMVTBL {
DWORD (CALLBACK* Get)(LPOLESTREAM,LPSTR,DWORD);
DWORD (CALLBACK* Put)(LPOLESTREAM,LPSTR,DWORD);
} OLESTREAMVTBL;
typedef OLESTREAMVTBL* LPOLESTREAMVTBL;
typedef struct _OLESTREAM {
LPOLESTREAMVTBL lpstbl;
} OLESTREAM;
typedef struct _OLESERVERDOC* LPOLESERVERDOC;
typedef struct _OLEOBJECT* LPOLEOBJECT;
typedef struct _OLECLIENT* LPOLECLIENT;
typedef struct _OLESERVERDOCVTBL {
OLESTATUS (CALLBACK* Save)(LPOLESERVERDOC);
OLESTATUS (CALLBACK* Close)(LPOLESERVERDOC);
OLESTATUS (CALLBACK* SetHostNames)(LPOLESERVERDOC,OLE_LPCSTR,OLE_LPCSTR);
OLESTATUS (CALLBACK* SetDocDimensions)(LPOLESERVERDOC,LPRECT);
OLESTATUS (CALLBACK* GetObject)(LPOLESERVERDOC,OLE_LPCSTR,LPOLEOBJECT*,LPOLECLIENT);
OLESTATUS (CALLBACK* Release)(LPOLESERVERDOC);
OLESTATUS (CALLBACK* SetColorScheme)(LPOLESERVERDOC,LPLOGPALETTE);
OLESTATUS (CALLBACK* Execute)(LPOLESERVERDOC,HGLOBAL);
} OLESERVERDOCVTBL;
typedef OLESERVERDOCVTBL* LPOLESERVERDOCVTBL;
typedef struct _OLESERVERDOC {
LPOLESERVERDOCVTBL lpvtbl;
/* server provided state info */
} OLESERVERDOC;
typedef struct _OLESERVER* LPOLESERVER;
typedef struct _OLESERVERVTBL {
OLESTATUS (CALLBACK* Open)(LPOLESERVER,LHSERVERDOC,OLE_LPCSTR,LPOLESERVERDOC *);
OLESTATUS (CALLBACK* Create)(LPOLESERVER,LHSERVERDOC,OLE_LPCSTR,OLE_LPCSTR,LPOLESERVERDOC FAR*);
OLESTATUS (CALLBACK* CreateFromTemplate)(LPOLESERVER,LHSERVERDOC,OLE_LPCSTR,OLE_LPCSTR,OLE_LPCSTR,LPOLESERVERDOC *);
OLESTATUS (CALLBACK* Edit)(LPOLESERVER,LHSERVERDOC,OLE_LPCSTR,OLE_LPCSTR,LPOLESERVERDOC *);
OLESTATUS (CALLBACK* Exit)(LPOLESERVER);
OLESTATUS (CALLBACK* Release)(LPOLESERVER);
OLESTATUS (CALLBACK* Execute)(LPOLESERVER);
} OLESERVERVTBL;
typedef OLESERVERVTBL *LPOLESERVERVTBL;
typedef struct _OLESERVER {
LPOLESERVERVTBL lpvtbl;
/* server specific data */
} OLESERVER;
typedef struct _OLECLIENTVTBL {
int (CALLBACK* CallBack)(LPOLECLIENT,OLE_NOTIFICATION,LPOLEOBJECT);
} OLECLIENTVTBL;
typedef OLECLIENTVTBL *LPOLECLIENTVTBL;
typedef struct _OLECLIENT {
LPOLECLIENTVTBL lpvtbl;
/* client data... */
} OLECLIENT;
typedef struct _OLEOBJECTVTBL {
void * (CALLBACK* QueryProtocol)(LPOLEOBJECT,OLE_LPCSTR);
OLESTATUS (CALLBACK* Release)(LPOLEOBJECT);
OLESTATUS (CALLBACK* Show)(LPOLEOBJECT,BOOL);
OLESTATUS (CALLBACK* DoVerb)(LPOLEOBJECT,UINT,BOOL,BOOL);
OLESTATUS (CALLBACK* GetData)(LPOLEOBJECT,OLECLIPFORMAT,HANDLE *);
OLESTATUS (CALLBACK* SetData)(LPOLEOBJECT,OLECLIPFORMAT,HANDLE);
OLESTATUS (CALLBACK* SetTargetDevice)(LPOLEOBJECT,HGLOBAL);
OLESTATUS (CALLBACK* SetBounds)(LPOLEOBJECT,LPRECT);
OLESTATUS (CALLBACK* EnumFormats)(LPOLEOBJECT,OLECLIPFORMAT);
OLESTATUS (CALLBACK* SetColorScheme)(LPOLEOBJECT,LPLOGPALETTE);
OLESTATUS (CALLBACK* Delete)(LPOLEOBJECT);
OLESTATUS (CALLBACK* SetHostNames)(LPOLEOBJECT,OLE_LPCSTR,OLE_LPCSTR);
OLESTATUS (CALLBACK* SaveToStream)(LPOLEOBJECT,LPOLESTREAM);
OLESTATUS (CALLBACK* Clone)(LPOLEOBJECT,LPOLECLIENT,LHCLIENTDOC,OLE_LPCSTR,LPOLEOBJECT *);
OLESTATUS (CALLBACK* CopyFromLink)(LPOLEOBJECT,LPOLECLIENT,LHCLIENTDOC,OLE_LPCSTR,LPOLEOBJECT *);
OLESTATUS (CALLBACK* Equal)(LPOLEOBJECT,LPOLEOBJECT);
OLESTATUS (CALLBACK* CopyToClipBoard)(LPOLEOBJECT);
OLESTATUS (CALLBACK* Draw)(LPOLEOBJECT,HDC,LPRECT,LPRECT,HDC);
OLESTATUS (CALLBACK* Activate)(LPOLEOBJECT,UINT,BOOL,BOOL,HWND,LPRECT);
OLESTATUS (CALLBACK* Execute)(LPOLEOBJECT,HGLOBAL,UINT);
OLESTATUS (CALLBACK* Close)(LPOLEOBJECT);
OLESTATUS (CALLBACK* Update)(LPOLEOBJECT);
OLESTATUS (CALLBACK* Reconnect)(LPOLEOBJECT);
OLESTATUS (CALLBACK* ObjectConvert)(LPOLEOBJECT,OLE_LPCSTR,LPOLECLIENT,LHCLIENTDOC,OLE_LPCSTR,LPOLEOBJECT*);
OLESTATUS (CALLBACK* GetLinkUpdateOptions)(LPOLEOBJECT,LPOLEOPT_UPDATE);
OLESTATUS (CALLBACK* SetLinkUpdateOptions)(LPOLEOBJECT,OLEOPT_UPDATE);
OLESTATUS (CALLBACK* Rename)(LPOLEOBJECT,OLE_LPCSTR);
OLESTATUS (CALLBACK* QueryName)(LPOLEOBJECT,LPSTR,LPUINT);
OLESTATUS (CALLBACK* QueryType)(LPOLEOBJECT,LPLONG);
OLESTATUS (CALLBACK* QueryBounds)(LPOLEOBJECT,LPRECT);
OLESTATUS (CALLBACK* QuerySize)(LPOLEOBJECT,LPDWORD);
OLESTATUS (CALLBACK* QueryOpen)(LPOLEOBJECT);
OLESTATUS (CALLBACK* QueryOutOfDate)(LPOLEOBJECT);
OLESTATUS (CALLBACK* QueryReleaseStatus)(LPOLEOBJECT);
OLESTATUS (CALLBACK* QueryReleaseError)(LPOLEOBJECT);
OLE_RELEASE_METHOD (CALLBACK* QueryReleaseMethod)(LPOLEOBJECT);
OLESTATUS (CALLBACK* RequestData)(LPOLEOBJECT,OLECLIPFORMAT);
OLESTATUS (CALLBACK* ObjectLong)(LPOLEOBJECT,UINT,LPLONG);
} OLEOBJECTVTBL;
typedef OLEOBJECTVTBL* LPOLEOBJECTVTBL;
typedef struct _OLEOBJECT {
LPOLEOBJECTVTBL lpvtbl;
} OLEOBJECT;
OLESTATUS WINAPI OleRegisterServer(LPCSTR,LPOLESERVER,LHSERVER FAR*,HINSTANCE,OLE_SERVER_USE);
OLESTATUS WINAPI OleUnblockServer(LHSERVER,BOOL FAR*);
OLESTATUS WINAPI OleRegisterServerDoc(LHSERVER,LPCSTR,LPOLESERVERDOC,LHSERVERDOC FAR*);
OLESTATUS WINAPI OleRegisterClientDoc(LPCSTR,LPCSTR,LONG,LHCLIENTDOC FAR*);
OLESTATUS WINAPI OleRegisterServer(LPCSTR,LPOLESERVER,LHSERVER *,HINSTANCE,OLE_SERVER_USE);
OLESTATUS WINAPI OleUnblockServer(LHSERVER,BOOL *);
OLESTATUS WINAPI OleRegisterServerDoc(LHSERVER,LPCSTR,LPOLESERVERDOC,LHSERVERDOC *);
OLESTATUS WINAPI OleRegisterClientDoc(LPCSTR,LPCSTR,LONG,LHCLIENTDOC *);
OLESTATUS WINAPI OleRenameClientDoc(LHCLIENTDOC,LPCSTR);
OLESTATUS WINAPI OleRevokeServerDoc(LHSERVERDOC);
OLESTATUS WINAPI OleRevokeClientDoc(LHCLIENTDOC);
......
......@@ -18,7 +18,8 @@ struct options
int debug;
int allowReadOnly; /* Opening a read only file will succeed even
if write access is requested */
int enhanced; /* Start Wine in enhanced mode */
int enhanced; /* Start Wine in enhanced mode */
int ipc; /* Use IPC mechanisms */
};
extern struct options Options;
......
/*
* Register definitions
*
* Copyright 1995 Alexandre Julliard
*/
#ifndef __WINE_REGISTERS_H
#define __WINE_REGISTERS_H
#include <windows.h>
#ifndef PROCEMU
#include "wine.h"
#define EAX (context->sc_eax)
#define EBX (context->sc_ebx)
#define ECX (context->sc_ecx)
#define EDX (context->sc_edx)
#define ESI (context->sc_esi)
#define EDI (context->sc_edi)
#define EBP (context->sc_ebp)
#define AX (*(WORD*)&context->sc_eax)
#define BX (*(WORD*)&context->sc_ebx)
#define CX (*(WORD*)&context->sc_ecx)
#define DX (*(WORD*)&context->sc_edx)
#define SI (*(WORD*)&context->sc_esi)
#define DI (*(WORD*)&context->sc_edi)
#define BP (*(WORD*)&context->sc_ebp)
#define AL (*(BYTE*)&context->sc_eax)
#define AH (*(((BYTE*)&context->sc_eax)+1))
#define BL (*(BYTE*)&context->sc_ebx)
#define BH (*(((BYTE*)&context->sc_ebx)+1))
#define CL (*(BYTE*)&context->sc_ecx)
#define CH (*(((BYTE*)&context->sc_ecx)+1))
#define DL (*(BYTE*)&context->sc_edx)
#define DH (*(((BYTE*)&context->sc_edx)+1))
#define CS (context->sc_cs)
#define DS (context->sc_ds)
#define ES (context->sc_es)
#define SS (context->sc_ss)
#ifdef linux
#define FS (context->sc_fs)
#define GS (context->sc_gs)
#define EAX_reg(context) ((context)->sc_eax)
#define EBX_reg(context) ((context)->sc_ebx)
#define ECX_reg(context) ((context)->sc_ecx)
#define EDX_reg(context) ((context)->sc_edx)
#define ESI_reg(context) ((context)->sc_esi)
#define EDI_reg(context) ((context)->sc_edi)
#define EBP_reg(context) ((context)->sc_ebp)
#define AX_reg(context) (*(WORD*)&((context)->sc_eax))
#define BX_reg(context) (*(WORD*)&((context)->sc_ebx))
#define CX_reg(context) (*(WORD*)&((context)->sc_ecx))
#define DX_reg(context) (*(WORD*)&((context)->sc_edx))
#define SI_reg(context) (*(WORD*)&((context)->sc_esi))
#define DI_reg(context) (*(WORD*)&((context)->sc_edi))
#define BP_reg(context) (*(WORD*)&((context)->sc_ebp))
#define AL_reg(context) (*(BYTE*)(&(context)->sc_eax))
#define AH_reg(context) (*(((BYTE*)(&(context)->sc_eax)+1)))
#define BL_reg(context) (*(BYTE*)(&(context)->sc_ebx))
#define BH_reg(context) (*(((BYTE*)(&(context)->sc_ebx)+1)))
#define CL_reg(context) (*(BYTE*)(&(context)->sc_ecx))
#define CH_reg(context) (*(((BYTE*)(&(context)->sc_ecx)+1)))
#define DL_reg(context) (*(BYTE*)(&(context)->sc_edx))
#define DH_reg(context) (*(((BYTE*)(&(context)->sc_edx)+1)))
#define CS_reg(context) ((context)->sc_cs)
#define DS_reg(context) ((context)->sc_ds)
#define ES_reg(context) ((context)->sc_es)
#define SS_reg(context) ((context)->sc_ss)
#ifdef linux
#define FS_reg(context) ((context)->sc_fs)
#define GS_reg(context) ((context)->sc_gs)
#else /* FIXME: are fs and gs supported under *BSD? */
#define FS 0
#define GS 0
#endif
#ifndef __FreeBSD__
#define EFL (context->sc_eflags)
#define FL (*(WORD*)&context->sc_eflags)
#else
#define EFL (context->sc_efl)
#define FL (*(WORD*)&context->sc_efl)
#endif
#define EIP (context->sc_eip)
#define ESP (context->sc_esp)
#define IP (*(WORD*)&context->sc_eip)
#define SP (*(WORD*)&context->sc_esp)
#define SetCflag (EFL |= 0x00000001)
#define ResetCflag (EFL &= 0xfffffffe)
#else
#include "bx_bochs.h"
#define SetCflag bx_STC()
#define ResetCflag bx_CLC()
#define FS_reg(context) 0
#define GS_reg(context) 0
#endif
#ifndef __FreeBSD__
#define EFL_reg(context) ((context)->sc_eflags)
#define FL_reg(context) (*(WORD*)(&(context)->sc_eflags))
#else
#define EFL_reg(context) ((context)->sc_efl)
#define FL_reg(context) (*(WORD*)(&(context)->sc_efl))
#endif
#define EIP_reg(context) ((context)->sc_eip)
#define ESP_reg(context) ((context)->sc_esp)
#define IP_reg(context) (*(WORD*)(&(context)->sc_eip))
#define SP_reg(context) (*(WORD*)(&(context)->sc_esp))
#define SET_CFLAG(context) (EFL_reg(context) |= 0x0001)
#define RESET_CFLAG(context) (EFL_reg(context) &= 0xfffffffe)
#endif /* PROCEMU */
#endif /* __WINE_REGISTERS_H */
......@@ -21,6 +21,12 @@
#define WINSWITCH_CLASS_NAME "#32771" /* WinSwitch */
#define ICONTITLE_CLASS_NAME "#32772" /* IconTitle */
#define POPUPMENU_CLASS_ATOM MAKEINTATOM(32768) /* PopupMenu */
#define DESKTOP_CLASS_ATOM MAKEINTATOM(32769) /* Desktop */
#define DIALOG_CLASS_ATOM MAKEINTATOM(32770) /* Dialog */
#define WINSWITCH_CLASS_ATOM MAKEINTATOM(32771) /* WinSwitch */
#define ICONTITLE_CLASS_ATOM MAKEINTATOM(32772) /* IconTitle */
typedef struct tagWND
{
HWND hwndNext; /* Next sibling */
......
......@@ -56,8 +56,8 @@ typedef struct {
HICON hIcon;
HCURSOR hCursor;
HBRUSH hbrBackground;
LPSTR lpszMenuName WINE_PACKED;
LPSTR lpszClassName WINE_PACKED;
SEGPTR lpszMenuName WINE_PACKED;
SEGPTR lpszClassName WINE_PACKED;
} WNDCLASS, *LPWNDCLASS;
#define CS_VREDRAW 0x0001
......@@ -429,8 +429,7 @@ typedef struct tagMSG
typedef WORD ATOM;
#define MAKEINTATOM(i) ((LPCSTR)MAKELP(0, (i)))
#define MAKEINTATOM(i) ((SEGPTR)MAKELONG((i),0))
/* Raster operations */
......@@ -2399,12 +2398,12 @@ F(void,SwitchStackBack)
F(void,ValidateCodeSegments)
F(void,WaitMessage)
F(void,Yield)
Fa(ATOM,AddAtom,LPCSTR,a)
Fa(ATOM,AddAtom,SEGPTR,a)
Fa(ATOM,DeleteAtom,ATOM,a)
Fa(ATOM,FindAtom,LPCSTR,a)
Fa(ATOM,GlobalAddAtom,LPCSTR,a)
Fa(ATOM,FindAtom,SEGPTR,a)
Fa(ATOM,GlobalAddAtom,SEGPTR,a)
Fa(ATOM,GlobalDeleteAtom,ATOM,a)
Fa(ATOM,GlobalFindAtom,LPCSTR,a)
Fa(ATOM,GlobalFindAtom,SEGPTR,a)
Fa(ATOM,RegisterClass,LPWNDCLASS,a)
Fa(BOOL,BringWindowToTop,HWND,a)
Fa(BOOL,DeleteDC,HDC,a)
......@@ -2559,7 +2558,7 @@ Fa(WORD,LocalLock,HLOCAL,a)
Fa(WORD,LocalSize,HLOCAL,a)
Fa(WORD,RealizeDefaultPalette,HDC,a)
Fa(WORD,RegisterClipboardFormat,LPCSTR,a)
Fa(WORD,RegisterWindowMessage,LPCSTR,a)
Fa(WORD,RegisterWindowMessage,SEGPTR,a)
Fa(WORD,SetHandleCount,WORD,a)
Fa(WORD,VkKeyScan,WORD,a)
Fa(int,AddFontResource,LPSTR,a)
......@@ -2651,7 +2650,7 @@ Fb(BOOL,SetWindowPlacement,HWND,a,LPWINDOWPLACEMENT,b)
Fb(BOOL,ShowWindow,HWND,a,int,b)
Fb(BOOL,TranslateMDISysAccel,HWND,a,LPMSG,b)
Fb(BOOL,UnhookWindowsHook,short,a,FARPROC,b)
Fb(BOOL,UnregisterClass,LPSTR,a,HANDLE,b)
Fb(BOOL,UnregisterClass,SEGPTR,a,HANDLE,b)
Fb(DWORD,GetNearestColor,HDC,a,DWORD,b)
Fb(DWORD,SetBkColor,HDC,a,COLORREF,b)
Fb(DWORD,SetMapperFlags,HDC,a,DWORD,b)
......@@ -2683,7 +2682,7 @@ Fb(HMENU,LoadMenu,HANDLE,a,SEGPTR,b)
Fb(HMENU,LookupMenuHandle,HMENU,a,INT,b)
Fb(HPALETTE,GDISelectPalette,HDC,a,HPALETTE,b)
Fb(HWND,ChildWindowFromPoint,HWND,a,POINT,b)
Fb(HWND,FindWindow,LPSTR,a,LPSTR,b)
Fb(HWND,FindWindow,SEGPTR,a,LPSTR,b)
Fb(HWND,GetDlgItem,HWND,a,WORD,b)
Fb(HWND,GetNextWindow,HWND,a,WORD,b)
Fb(HWND,GetWindow,HWND,a,WORD,b)
......
......@@ -32,26 +32,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -29,8 +29,9 @@
#include <assert.h>
#include "bit_array.h"
#if defined(HAS_BITOPS)
# include <asm/bitops.h>
#ifdef HAS_BITOPS
#define inline __inline__ /* So we can compile with -ansi */
#include <asm/bitops.h>
#else
static __inline__ int clear_bit(int bit, int *mem);
static __inline__ int set_bit(int bit, int *mem);
......
......@@ -14,6 +14,7 @@
#include "dde_atom.h"
#include "shm_main_blk.h"
#include "shm_fragment.h"
#include "ldt.h"
#include "stddebug.h"
#include "debug.h"
......@@ -109,20 +110,25 @@ void ATOM_GlobalInit(void)
*/
/* important! don't forget to unlock semaphores before return */
ATOM GlobalAddAtom( LPCSTR str )
ATOM GlobalAddAtom( SEGPTR name )
{
int atom_idx;
int atom_ofs;
AtomData_ptr ptr;
ATOM atom;
char *str;
dprintf_atom(stddeb,"GlobalAddAtom(%p)\n", str);
if ((unsigned) str < MIN_STR_ATOM) /* MS-windows convention */
return (ATOM) (unsigned) str;
if (str[0] == '#') { /* wine convention */
atom= (ATOM) atoi(&str[1]);
/* First check for integer atom */
if (!HIWORD(name)) return (ATOM)LOWORD(name);
str = (char *)PTR_SEG_TO_LIN( name );
if (str[0] == '#')
{
ATOM atom= (ATOM) atoi(&str[1]);
return (atom<MIN_STR_ATOM) ? atom : 0;
}
dprintf_atom(stddeb,"GlobalAddAtom(\"%s\")\n",str);
DDE_IPC_init(); /* will initialize only if needed */
......@@ -199,15 +205,21 @@ ATOM GlobalDeleteAtom( ATOM atom )
/***********************************************************************
* GlobalFindAtom (USER.270)
*/
ATOM GlobalFindAtom( LPCSTR str )
ATOM GlobalFindAtom( SEGPTR name )
{
int atom_idx;
int atom_ofs;
char *str;
dprintf_atom(stddeb,"GlobalFindAtom(%08lx)\n", name );
/* First check for integer atom */
if (!HIWORD(name)) return (ATOM)LOWORD(name);
dprintf_atom(stddeb,"GlobalFindAtom(%p)\n", str );
if ((unsigned) str < MIN_STR_ATOM) /* MS-windows convention */
return (ATOM) (unsigned) str;
if (str[0] == '#') { /* wine convention */
str = (char *)PTR_SEG_TO_LIN( name );
if (str[0] == '#')
{
ATOM atom= (ATOM) atoi(&str[1]);
return (atom<MIN_STR_ATOM) ? atom : 0;
}
......
......@@ -5,6 +5,7 @@
* Purpose : dynamically growing hash, may use shared or local memory.
***************************************************************************
*/
#include <sys/types.h>
#include <stdlib.h>
#include <assert.h>
#include "generic_hash.h"
......
......@@ -9,6 +9,7 @@
*/
#define inline __inline__
#include <sys/types.h>
#include <sys/sem.h>
#include <stdio.h>
#include <assert.h>
......
......@@ -8,6 +8,7 @@
***************************************************************************
*/
#define inline __inline__
#include <sys/types.h>
#include <sys/sem.h>
#include <stdio.h>
#include <time.h>
......@@ -62,7 +63,7 @@ static void print_shm_info(int shm_id)
}
int proc_exist(__pid_t pid)
int proc_exist(pid_t pid)
{
if ( kill(pid,0) == 0) /* dummy signal to test existence */
return 1;
......@@ -189,7 +190,9 @@ static int shm_locate_MainBlock(key_t shm_key)
}
} else {
switch(errno) {
#ifdef EIDRM
case EIDRM: /* segment destroyed */
#endif
case EACCES: /* no user permision */
break;
......
......@@ -9,7 +9,6 @@ SRCS = \
ne_resource.c \
pe_image.c \
pe_resource.c \
selector.c \
signal.c \
resource.c \
task.c
......
......@@ -10,7 +10,7 @@ LDCOMBINEFLAGS = @LDCOMBINEFLAGS@
MODULE = loader
SRCS = main.c module.c ne_image.c ne_resource.c pe_image.c \
pe_resource.c selector.c signal.c resource.c task.c
pe_resource.c signal.c resource.c task.c
OBJS = $(SRCS:.c=.o)
......@@ -25,26 +25,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -57,18 +57,15 @@ int MAIN_Init(void)
/* Create built-in modules */
if (!MODULE_Init()) return 0;
/* Initialize the DOS file system */
DOS_InitFS();
/* Initialize tasks */
if (!TASK_Init()) return 0;
/* Initialize interrupt vectors */
if (!INT_Init()) return 0;
/* Initialize the DOS file system */
DOS_InitFS();
/* Create DOS environment */
CreateSelectors();
/* Initialize signal handling */
init_wine_signals();
......
......@@ -35,8 +35,6 @@ static HMODULE hCachedModule = 0; /* Module cached by MODULE_OpenFile */
*/
BOOL MODULE_Init(void)
{
extern void load_entrypoints( HMODULE );
HMODULE hModule;
NE_MODULE *pModule;
SEGTABLEENTRY *pSegTable;
......@@ -82,7 +80,6 @@ BOOL MODULE_Init(void)
pModule->next = hFirstModule;
hFirstModule = hModule;
load_entrypoints( hModule );
}
/* Initialize some KERNEL exported values */
......@@ -1169,6 +1166,22 @@ FARPROC GetProcAddress( HANDLE hModule, SEGPTR name )
}
/***********************************************************************
* GetWndProcEntry16 (not a Windows API function)
*
* Return an entry point from the WINPROCS dll.
*/
WNDPROC GetWndProcEntry16( char *name )
{
WORD ordinal;
static HMODULE hModule = 0;
if (!hModule) hModule = GetModuleHandle( "WINPROCS" );
ordinal = MODULE_GetOrdinal( hModule, name );
return MODULE_GetEntryPoint( hModule, ordinal );
}
/**********************************************************************
* ModuleFirst (TOOLHELP.59)
*/
......
......@@ -549,36 +549,33 @@ int TranslateAccelerator(HWND hWnd, HANDLE hAccel, LPMSG msg)
if (hAccel == 0 || msg == NULL) return 0;
if (msg->message != WM_KEYDOWN &&
msg->message != WM_KEYUP &&
msg->message != WM_SYSKEYDOWN &&
msg->message != WM_SYSKEYUP &&
msg->message != WM_CHAR) return 0;
dprintf_accel(stddeb, "TranslateAccelerators hAccel=%04X !\n", hAccel);
lpAccelTbl = (LPACCELHEADER)GlobalLock(hAccel);
for (i = 0; i < lpAccelTbl->wCount; i++) {
if (lpAccelTbl->tbl[i].type & VIRTKEY_ACCEL) {
if (msg->wParam == lpAccelTbl->tbl[i].wEvent &&
msg->message == WM_KEYDOWN) {
if ((lpAccelTbl->tbl[i].type & SHIFT_ACCEL) &&
!(GetKeyState(VK_SHIFT) & 0xf)) {
GlobalUnlock(hAccel);
return 0;
}
if ((lpAccelTbl->tbl[i].type & CONTROL_ACCEL) &&
!(GetKeyState(VK_CONTROL) & 0xf)) {
if(lpAccelTbl->tbl[i].type & VIRTKEY_ACCEL) {
if(msg->wParam == lpAccelTbl->tbl[i].wEvent &&
(msg->message == WM_KEYDOWN || msg->message == WM_SYSKEYDOWN)) {
INT mask = 0;
if(GetKeyState(VK_SHIFT) & 0xf) mask |= SHIFT_ACCEL;
if(GetKeyState(VK_CONTROL) & 0xf) mask |= CONTROL_ACCEL;
if(GetKeyState(VK_MENU) & 0xf) mask |= ALT_ACCEL;
if(mask == (lpAccelTbl->tbl[i].type &
(SHIFT_ACCEL | CONTROL_ACCEL | ALT_ACCEL))) {
SendMessage(hWnd, WM_COMMAND, lpAccelTbl->tbl[i].wIDval,
0x00010000L);
GlobalUnlock(hAccel);
return 0;
}
if ((lpAccelTbl->tbl[i].type & ALT_ACCEL) &&
!(GetKeyState(VK_MENU) & 0xf)) {
GlobalUnlock(hAccel);
return 0;
}
SendMessage(hWnd, WM_COMMAND, lpAccelTbl->tbl[i].wIDval, 0x00010000L);
GlobalUnlock(hAccel);
return 1;
}
if (msg->message == WM_KEYUP) return 1;
return 1;
}
if (msg->message == WM_KEYUP || msg->message == WM_SYSKEYUP)
return 1;
}
}
else {
if (msg->wParam == lpAccelTbl->tbl[i].wEvent &&
msg->message == WM_CHAR) {
......@@ -619,6 +616,8 @@ LoadString(HANDLE instance, WORD resource_id, LPSTR buffer, int buflen)
dprintf_resource( stddeb, "strlen = %d\n", (int)*p );
i = min(buflen - 1, *p);
if (buffer == NULL)
return i;
if (i > 0) {
memcpy(buffer, p + 1, i);
buffer[i] = '\0';
......
/*
* Selector manipulation functions
*
* Copyright 1993 Robert J. Amstadt
* Copyright 1995 Alexandre Julliard
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#ifndef WINELIB
#include "windows.h"
#include "global.h"
#include "module.h"
#include "stddebug.h"
/* #define DEBUG_SELECTORS */
#include "debug.h"
#define MAX_ENV_SIZE 16384 /* Max. environment size (ought to be dynamic) */
static HANDLE EnvironmentHandle = 0;
extern char WindowsPath[256];
extern char **environ;
WNDPROC GetWndProcEntry16( char *name )
{
WORD ordinal;
static HMODULE hModule = 0;
if (!hModule) hModule = GetModuleHandle( "WINPROCS" );
ordinal = MODULE_GetOrdinal( hModule, name );
return MODULE_GetEntryPoint( hModule, ordinal );
}
/***********************************************************************
* GetDOSEnvironment (KERNEL.131)
*/
SEGPTR GetDOSEnvironment(void)
{
return WIN16_GlobalLock( EnvironmentHandle );
}
/**********************************************************************
* CreateEnvironment
*/
static HANDLE CreateEnvironment(void)
{
HANDLE handle;
char **e;
char *p;
handle = GlobalAlloc( GMEM_MOVEABLE, MAX_ENV_SIZE );
if (!handle) return 0;
p = (char *) GlobalLock( handle );
/*
* Fill environment with Windows path, the Unix environment,
* and program name.
*/
strcpy(p, "PATH=");
strcat(p, WindowsPath);
p += strlen(p) + 1;
for (e = environ; *e; e++)
{
if (strncasecmp(*e, "path", 4))
{
strcpy(p, *e);
p += strlen(p) + 1;
}
}
*p++ = '\0';
/*
* Display environment
*/
p = (char *) GlobalLock( handle );
dprintf_selectors(stddeb, "Environment at %p\n", p);
for (; *p; p += strlen(p) + 1) dprintf_selectors(stddeb, " %s\n", p);
return handle;
}
/**********************************************************************
* CreateSelectors
*/
void CreateSelectors(void)
{
if(!EnvironmentHandle) EnvironmentHandle = CreateEnvironment();
}
#endif /* ifndef WINELIB */
......@@ -55,13 +55,15 @@ static void win_fault(int signal, int code, struct sigcontext *context)
#endif
if (signal != SIGTRAP)
{
if (CS == WINE_CODE_SELECTOR)
if (CS_reg(context) == WINE_CODE_SELECTOR)
{
fprintf(stderr, "Segmentation fault in Wine program (%x:%lx)."
" Please debug\n", CS, EIP );
" Please debug\n",
CS_reg(context), EIP_reg(context) );
}
else if (INSTR_EmulateInstruction( context )) return;
fprintf(stderr,"In win_fault %x:%lx\n", CS, EIP );
fprintf( stderr,"In win_fault %x:%lx\n",
CS_reg(context), EIP_reg(context) );
}
XUngrabPointer(display, CurrentTime);
XUngrabServer(display);
......
......@@ -10,6 +10,7 @@
#include "windows.h"
#include "task.h"
#include "callback.h"
#include "dos_fs.h"
#include "debugger.h"
#include "global.h"
#include "instance.h"
......@@ -36,6 +37,7 @@ static HTASK hCurrentTask = 0;
static HTASK hTaskToKill = 0;
static HTASK hLockedTask = 0;
static WORD nTaskCount = 0;
static HANDLE hDOSEnvironment = 0;
/* TASK_Reschedule() 16-bit entry point */
static FARPROC TASK_RescheduleProc;
......@@ -43,13 +45,122 @@ static FARPROC TASK_RescheduleProc;
#define TASK_SCHEDULE() CallTo16_word_(TASK_RescheduleProc,0)
static HANDLE TASK_CreateDOSEnvironment(void);
/***********************************************************************
* TASK_Init
*/
BOOL TASK_Init(void)
{
TASK_RescheduleProc = (FARPROC)GetWndProcEntry16( "TASK_Reschedule" );
return TRUE;
if (!(hDOSEnvironment = TASK_CreateDOSEnvironment()))
fprintf( stderr, "Not enough memory for DOS Environment\n" );
return (hDOSEnvironment != 0);
}
/***********************************************************************
* TASK_CreateDOSEnvironment
*
* Create the original DOS environment.
*/
static HANDLE TASK_CreateDOSEnvironment(void)
{
static const char program_name[] = "KRNL386.EXE";
char **e, *p;
int initial_size, size;
HANDLE handle;
extern char **environ;
extern char WindowsDirectory[], SystemDirectory[];
/* DOS environment format:
* ASCIIZ string 1
* ASCIIZ string 2
* ...
* ASCIIZ string n
* ASCIIZ PATH=xxx
* ASCIIZ windir=xxx
* BYTE 0
* WORD 1
* ASCIIZ program name (e.g. C:\WINDOWS\SYSTEM\KRNL386.EXE)
*/
/* First compute the size of the fixed part of the environment */
initial_size = 5 + /* PATH= */
strlen(WindowsPath) + 1 + /* path value */
7 + /* windir= */
strlen(WindowsDirectory) + 1 + /* windir value */
1 + /* BYTE 0 at end */
sizeof(WORD) + /* WORD 1 */
strlen(SystemDirectory) + 1 + /* program directory */
strlen(program_name) + 1; /* program name */
/* Compute the total size of the Unix environment (except path) */
for (e = environ, size = initial_size; *e; e++)
{
if (strncasecmp(*e, "path=", 5))
{
int len = strlen(*e) + 1;
if (size + len >= 32767)
{
fprintf( stderr, "Warning: environment larger than 32k.\n" );
break;
}
size += len;
}
}
/* Now allocate the environment */
if (!(handle = GlobalAlloc( GMEM_FIXED, size ))) return 0;
p = (char *)GlobalLock( handle );
/* And fill it with the Unix environment */
for (e = environ, size = initial_size; *e; e++)
{
if (strncasecmp(*e, "path=", 5))
{
int len = strlen(*e) + 1;
if (size + len >= 32767) break;
strcpy( p, *e );
size += len;
p += len;
}
}
/* Now add the path and Windows directory */
strcpy( p, "PATH=" );
strcat( p, WindowsPath );
p += strlen(p) + 1;
strcpy( p, "windir=" );
strcat( p, WindowsDirectory );
p += strlen(p) + 1;
/* Now add the program name */
*p++ = '\0';
*(WORD *)p = 1;
p += sizeof(WORD);
strcpy( p, SystemDirectory );
strcat( p, "\\" );
strcat( p, program_name );
/* Display it */
p = (char *) GlobalLock( handle );
dprintf_task(stddeb, "Master DOS environment at %p\n", p);
for (; *p; p += strlen(p) + 1) dprintf_task(stddeb, " %s\n", p);
dprintf_task( stddeb, "Progname: %s\n", p+3 );
return handle;
}
......@@ -229,7 +340,7 @@ static void TASK_CallToStart(void)
0 /*dx*/, 0 /*si*/, ds_reg /*di*/ );
/* This should never return */
fprintf( stderr, "TASK_CallToStart: Main program returned!\n" );
exit(1);
TASK_KillCurrentTask( 1 );
}
......@@ -241,6 +352,7 @@ HTASK TASK_CreateTask( HMODULE hModule, HANDLE hInstance, HANDLE hPrevInstance,
{
HTASK hTask;
TDB *pTask;
HANDLE hParentEnv;
NE_MODULE *pModule;
SEGTABLEENTRY *pSegTable;
LPSTR name;
......@@ -260,7 +372,24 @@ HTASK TASK_CreateTask( HMODULE hModule, HANDLE hInstance, HANDLE hPrevInstance,
if (!hTask) return 0;
pTask = (TDB *)GlobalLock( hTask );
/* get current directory */
/* Allocate the new environment block */
if (!(hParentEnv = hEnvironment))
{
TDB *pParent = (TDB *)GlobalLock( hCurrentTask );
hParentEnv = pParent ? pParent->pdb.environment : hDOSEnvironment;
}
/* FIXME: do we really need to make a copy also when */
/* we don't use the parent environment? */
if (!(hEnvironment = GlobalAlloc( GMEM_FIXED, GlobalSize( hParentEnv ) )))
{
GlobalFree( hTask );
return 0;
}
memcpy( GlobalLock( hEnvironment ), GlobalLock( hParentEnv ),
GlobalSize( hParentEnv ) );
/* Get current directory */
GetModuleFileName( hModule, filename, sizeof(filename) );
name = strrchr(filename, '\\');
......@@ -355,8 +484,8 @@ HTASK TASK_CreateTask( HMODULE hModule, HANDLE hInstance, HANDLE hPrevInstance,
pSegTable[pModule->ss-1].minsize + pModule->stack_size) & ~1;
stack16Top = (char *)PTR_SEG_OFF_TO_LIN( pTask->ss, pTask->sp );
frame16 = (STACK16FRAME *)stack16Top - 1;
frame16->saved_ss = pTask->ss;
frame16->saved_sp = pTask->sp;
frame16->saved_ss = 0; /*pTask->ss;*/
frame16->saved_sp = 0; /*pTask->sp;*/
frame16->ds = frame16->es = pTask->hInstance;
frame16->entry_point = 0;
frame16->ordinal_number = 24; /* WINPROCS.24 is TASK_Reschedule */
......@@ -380,8 +509,9 @@ HTASK TASK_CreateTask( HMODULE hModule, HANDLE hInstance, HANDLE hPrevInstance,
if (Options.debug)
{
DBG_ADDR addr = { pSegTable[pModule->cs-1].selector, pModule->ip };
fprintf( stderr, "Task '%s': ", name );
DEBUG_AddBreakpoint( pSegTable[pModule->cs-1].selector, pModule->ip );
DEBUG_AddBreakpoint( &addr );
}
/* Add the task to the linked list */
......@@ -844,6 +974,18 @@ int GetInstanceData( HANDLE instance, WORD buffer, int len )
/***********************************************************************
* GetDOSEnvironment (KERNEL.131)
*/
SEGPTR GetDOSEnvironment(void)
{
TDB *pTask;
if (!(pTask = (TDB *)GlobalLock( hCurrentTask ))) return 0;
return WIN16_GlobalLock( pTask->pdb.environment );
}
/***********************************************************************
* GetNumTasks (KERNEL.152)
*/
WORD GetNumTasks(void)
......
......@@ -3,10 +3,11 @@
MODULE = memory
SRCS = \
selector.c \
atom.c \
global.c \
ldt.c \
local.c
local.c \
selector.c
OBJS = $(SRCS:.c=.o)
......
......@@ -9,7 +9,12 @@ LDCOMBINEFLAGS = @LDCOMBINEFLAGS@
MODULE = memory
SRCS = selector.c global.c ldt.c local.c
SRCS = \
atom.c \
global.c \
ldt.c \
local.c \
selector.c
OBJS = $(SRCS:.c=.o)
......@@ -24,26 +29,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -5,22 +5,10 @@
*/
/*
* Current limitations:
*
* - The code assumes that LocalAlloc() returns a block aligned on a
* 4-bytes boundary (because of the shifting done in HANDLETOATOM).
* If this is not the case, the allocation code will have to be changed.
*
* - Integer atoms created with MAKEINTATOM are not supported. This is
* because they can't generally be differentiated from string constants
* located below 0x10000 in the emulation library. If you need
* integer atoms, use the "#1234" form.
*
* 13/Feb, miguel
* Changed the calls to LocalAlloc to LocalAlign. When compiling WINELIB
* you call a special version of LocalAlloc that would do the alignement.
* When compiling the emulator we depend on LocalAlloc returning the
* aligned block. Needed to test the Library.
* Warning: The code assumes that LocalAlloc() returns a block aligned
* on a 4-bytes boundary (because of the shifting done in
* HANDLETOATOM). If this is not the case, the allocation code will
* have to be changed.
*/
#include <stdlib.h>
......@@ -130,20 +118,22 @@ static WORD ATOM_Hash( WORD entries, LPCSTR str, WORD len )
/***********************************************************************
* ATOM_AddAtom
*/
static ATOM ATOM_AddAtom( WORD selector, LPCSTR str )
static ATOM ATOM_AddAtom( WORD selector, SEGPTR name )
{
WORD hash;
HANDLE entry;
ATOMENTRY * entryPtr;
ATOMTABLE * table;
int len;
if ((len = strlen( str )) > 255) len = 255;
char *str;
/* Check for integer atom */
/* Check for integer atom */
/* if (!((int)str & 0xffff0000)) return (ATOM)((int)str & 0xffff); */
if (!HIWORD(name)) return (ATOM)LOWORD(name);
str = PTR_SEG_TO_LIN( name );
if (str[0] == '#') return atoi( &str[1] );
if ((len = strlen( str )) > 255) len = 255;
if (!(table = ATOM_GetTable( selector, TRUE ))) return 0;
hash = ATOM_Hash( table->size, str, len );
entry = table->entries[hash];
......@@ -210,19 +200,21 @@ static ATOM ATOM_DeleteAtom( WORD selector, ATOM atom )
/***********************************************************************
* ATOM_FindAtom
*/
static ATOM ATOM_FindAtom( WORD selector, LPCSTR str )
static ATOM ATOM_FindAtom( WORD selector, SEGPTR name )
{
ATOMTABLE * table;
WORD hash;
HANDLE entry;
int len;
if ((len = strlen( str )) > 255) len = 255;
/* Check for integer atom */
/* if (!((int)str & 0xffff0000)) return (ATOM)((int)str & 0xffff); */
char *str;
/* Check for integer atom */
if (!HIWORD(name)) return (ATOM)LOWORD(name);
str = PTR_SEG_TO_LIN( name );
if (str[0] == '#') return atoi( &str[1] );
if ((len = strlen( str )) > 255) len = 255;
if (!(table = ATOM_GetTable( selector, FALSE ))) return 0;
hash = ATOM_Hash( table->size, str, len );
entry = table->entries[hash];
......@@ -295,7 +287,7 @@ HANDLE GetAtomHandle( ATOM atom )
/***********************************************************************
* AddAtom (KERNEL.70)
*/
ATOM AddAtom( LPCSTR str )
ATOM AddAtom( SEGPTR str )
{
return ATOM_AddAtom( CURRENT_DS, str );
}
......@@ -313,7 +305,7 @@ ATOM DeleteAtom( ATOM atom )
/***********************************************************************
* FindAtom (KERNEL.69)
*/
ATOM FindAtom( LPCSTR str )
ATOM FindAtom( SEGPTR str )
{
return ATOM_FindAtom( CURRENT_DS, str );
}
......@@ -331,7 +323,7 @@ WORD GetAtomName( ATOM atom, LPSTR buffer, short count )
/***********************************************************************
* LocalAddAtom (USER.268)
*/
ATOM LocalAddAtom( LPCSTR str )
ATOM LocalAddAtom( SEGPTR str )
{
return ATOM_AddAtom( USER_HeapSel, str );
}
......@@ -349,7 +341,7 @@ ATOM LocalDeleteAtom( ATOM atom )
/***********************************************************************
* LocalFindAtom (USER.270)
*/
ATOM LocalFindAtom( LPCSTR str )
ATOM LocalFindAtom( SEGPTR str )
{
return ATOM_FindAtom( USER_HeapSel, str );
}
......
......@@ -4,6 +4,7 @@
* Copyright 1995 Alexandre Julliard
*/
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
......@@ -13,6 +14,7 @@
#include "selectors.h"
#include "dde_mem.h"
#include "stackframe.h"
#include "options.h"
#include "stddebug.h"
#include "debug.h"
......@@ -128,7 +130,7 @@ HGLOBAL GLOBAL_CreateBlock( WORD flags, void *ptr, DWORD size,
pArena->base = (DWORD)ptr;
pArena->size = GET_SEL_LIMIT(sel) + 1;
if (flags & GMEM_DDESHARE)
if ((flags & GMEM_DDESHARE) && Options.ipc)
{
pArena->handle = shmdata->handle;
pArena->shmid = shmdata->shmid;
......@@ -194,7 +196,7 @@ HGLOBAL GLOBAL_Alloc( WORD flags, DWORD size, HGLOBAL hOwner,
/* Allocate the linear memory */
if (flags & GMEM_DDESHARE)
if ((flags & GMEM_DDESHARE) && Options.ipc)
ptr= DDE_malloc(flags, size, &shmdata);
else
ptr = malloc( size );
......@@ -266,7 +268,7 @@ HGLOBAL GlobalReAlloc( HGLOBAL handle, DWORD size, WORD flags )
handle, size, flags );
if (!handle) return 0;
if (flags & GMEM_DDESHARE || is_dde_handle(handle)) {
if (Options.ipc && (flags & GMEM_DDESHARE || is_dde_handle(handle))) {
fprintf(stdnimp,
"GlobalReAlloc: shared memory reallocating unimplemented\n");
return 0;
......
......@@ -66,6 +66,7 @@ WORD FreeSelector( WORD sel )
{
WORD i, count;
ldt_entry entry;
STACK16FRAME *frame;
dprintf_selector( stddeb, "FreeSelector(%04x)\n", sel );
if (IS_SELECTOR_FREE(sel)) return sel; /* error */
......@@ -80,11 +81,12 @@ WORD FreeSelector( WORD sel )
/* Clear the saved 16-bit selector */
#ifndef WINELIB
if (CURRENT_STACK16)
frame = CURRENT_STACK16;
while (frame)
{
/* FIXME: maybe we ought to walk up the stack and fix all frames */
if (CURRENT_STACK16->ds == sel) CURRENT_STACK16->ds = 0;
if (CURRENT_STACK16->es == sel) CURRENT_STACK16->es = 0;
if (frame->ds == sel) frame->ds = 0;
if (frame->es == sel) frame->es = 0;
frame = PTR_SEG_OFF_TO_LIN(frame->saved_ss, frame->saved_sp);
}
#endif
return 0;
......
......@@ -3,7 +3,6 @@
MODULE = misc
SRCS = \
atom.c \
clipboard.c \
comm.c \
commdlg.c \
......
......@@ -11,7 +11,7 @@ LDCOMBINEFLAGS = @LDCOMBINEFLAGS@
MODULE = misc
SRCS = atom.c clipboard.c comm.c commdlg.c compobj.c dos_fs.c \
SRCS = clipboard.c comm.c commdlg.c compobj.c dos_fs.c \
driver.c exec.c escape.c file.c keyboard.c kernel32.c lstr.c \
main.c ole2.c ole2disp.c ole2nls.c olecli.c olesvr.c network.c \
profile.c rect.c shell.c sound.c spy.c stress.c user.c \
......@@ -24,8 +24,8 @@ OBJS = $(SRCS:.c=.o)
all: checkrc $(MODULE).o
checkrc:
(cd $(TOPSRC)/rc; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)')
checkrc: dummy
cd $(TOPSRC)/rc; $(MAKE) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'LD=$(LD)' 'LDCOMBINEFLAGS=$(LDCOMBINEFLAGS)'
$(MODULE).o: $(OBJS)
$(LD) $(LDCOMBINEFLAGS) $(OBJS) -o $(MODULE).o
......@@ -33,27 +33,17 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
rm -f ole2nls.o shell.o commdlg.o
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -368,7 +368,7 @@ static LONG FILEDLG_WMInitDialog(HWND hWnd, WORD wParam, LONG lParam)
else
*tmpstr = 0;
if (!FILEDLG_ScanDir(hWnd, tmpstr))
fprintf(stderr, "FileDlg: couldn't read initial directory!\n");
fprintf(stderr, "FileDlg: couldn't read initial directory %s!\n", tmpstr);
/* select current drive in combo 2 */
n = DOS_GetDefaultDrive();
SendDlgItemMessage(hWnd, cmb2, CB_SETCURSEL, n - 1, 0);
......
......@@ -124,6 +124,7 @@ void ToUnix(char *s)
{
while(*s){
if (*s == '\\') *s = '/';
*s=tolower(*s); /* umsdos fs can't read files without :( */
s++;
}
}
......@@ -188,7 +189,6 @@ void DOS_InitFS(void)
DosDrives[x].disabled = 0;
}
DosDrives[25].rootdir = "/";
strcpy(DosDrives[25].cwd, "/");
strcpy(DosDrives[25].label, "UNIX-FS");
DosDrives[25].serialnumber = 0x12345678;
DosDrives[25].disabled = 0;
......@@ -206,6 +206,7 @@ void DOS_InitFS(void)
getcwd(temp, 254);
strcat(temp, "/"); /* For DOS_GetDosFileName */
strcpy(DosDrives[25].cwd, temp );
strcpy(temp, DOS_GetDosFileName(temp));
if(temp[0] != 'Z')
{
......
......@@ -72,8 +72,8 @@ INT _lread (INT hFile, LPSTR lpBuffer, WORD wBytes)
{
int result;
dprintf_file(stddeb, "_lread: handle %d, buffer = %ld, length = %d\n",
hFile, (long) lpBuffer, wBytes);
dprintf_file(stddeb, "_lread: handle %d, buffer = %p, length = %d\n",
hFile, lpBuffer, wBytes);
result = wBytes == 0 ? 0 : read (hFile, lpBuffer, wBytes);
......@@ -90,10 +90,28 @@ INT _lwrite (INT hFile, LPCSTR lpBuffer, WORD wBytes)
{
int result;
dprintf_file(stddeb, "_lwrite: handle %d, buffer = %ld, length = %d\n",
hFile, (long) lpBuffer, wBytes);
dprintf_file(stddeb, "_lwrite: handle %d, buffer = %p, length = %d\n",
hFile, lpBuffer, wBytes);
result = wBytes == 0 ? 0 : write (hFile, lpBuffer, wBytes);
if(wBytes == 0) { /* Expand the file size if necessary */
char toWrite = 0;
off_t prev, end;
prev = lseek(hFile, 0, SEEK_CUR);
if(prev == -1) return HFILE_ERROR;
end = lseek(hFile, 0, SEEK_END);
if(end == -1) return HFILE_ERROR;
if(prev > end) {
lseek(hFile, prev-1, SEEK_SET);
result = write(hFile, &toWrite, 1) - 1;
if(result == -2) ++result;
}
else {
lseek(hFile, prev, SEEK_SET);
result = 0;
}
}
else result = write (hFile, lpBuffer, wBytes);
if (result == -1)
return HFILE_ERROR;
......@@ -325,7 +343,7 @@ INT _lcreat (LPSTR lpszFilename, INT fnAttribute)
lpszFilename, fnAttribute);
if ((UnixFileName = DOS_GetUnixFileName(lpszFilename)) == NULL)
return HFILE_ERROR;
handle = open (UnixFileName, O_CREAT | O_TRUNC | O_WRONLY, 0666);
handle = open (UnixFileName, O_CREAT | O_TRUNC | O_RDWR, 0666);
if (handle == -1)
return HFILE_ERROR;
......
......@@ -109,7 +109,7 @@ BOOL IsCharAlpha(char ch)
/* IsCharAlphanumeric USER 434 */
BOOL IsCharAlphanumeric(char ch)
{
return (ch<'0')?0:(ch<'9');
return (ch < '0') ? 0 : (ch <= '9');
}
/* IsCharUpper USER 435 */
......
......@@ -69,7 +69,8 @@ struct options Options =
SW_SHOWNORMAL, /* cmdShow */
FALSE,
FALSE, /* AllowReadOnly */
FALSE /* Enhanced mode */
FALSE, /* Enhanced mode */
FALSE /* IPC enabled */
};
......@@ -80,6 +81,7 @@ static XrmOptionDescRec optionsTable[] =
{ "-depth", ".depth", XrmoptionSepArg, (caddr_t)NULL },
{ "-display", ".display", XrmoptionSepArg, (caddr_t)NULL },
{ "-iconic", ".iconic", XrmoptionNoArg, (caddr_t)"on" },
{ "-ipc", ".ipc", XrmoptionNoArg, (caddr_t)"off"},
{ "-name", ".name", XrmoptionSepArg, (caddr_t)NULL },
{ "-privatemap", ".privatemap", XrmoptionNoArg, (caddr_t)"on" },
{ "-synchronous", ".synchronous", XrmoptionNoArg, (caddr_t)"on" },
......@@ -100,6 +102,7 @@ static XrmOptionDescRec optionsTable[] =
" -desktop geom Use a desktop window of the given geometry\n" \
" -display name Use the specified display\n" \
" -iconic Start as an icon\n" \
" -ipc Enable IPC facilities\n" \
" -debug Enter debugger before starting application\n" \
" -name name Set the application name\n" \
" -privatemap Use a private color map\n" \
......@@ -309,6 +312,8 @@ static void MAIN_ParseOptions( int *argc, char *argv[] )
Options.allowReadOnly = TRUE;
if (MAIN_GetResource( db, ".enhanced", &value ))
Options.enhanced = TRUE;
if (MAIN_GetResource( db, ".ipc", &value ))
Options.ipc = TRUE;
if (MAIN_GetResource( db, ".depth", &value))
screenDepth = atoi( value.addr );
if (MAIN_GetResource( db, ".desktop", &value))
......@@ -558,7 +563,7 @@ void MessageBeep(WORD i)
*/
LONG GetVersion(void)
{
return MAKELONG( WINVERSION, DOSVERSION );
return MAKELONG( WINVERSION, WINDOSVER );
}
/***********************************************************************
......
......@@ -134,6 +134,7 @@ static TSecHeader *load (char *filename, char **pfullname)
state = FirstBrace;
next = CharBuffer;
while ((c = fgetc (f)) != EOF){
if (c == '\r') /* Ignore Carriage Return */
continue;
......
......@@ -5,6 +5,7 @@
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <ctype.h>
#include "windows.h"
#include "shell.h"
#include "neexe.h"
......@@ -17,7 +18,7 @@
LPKEYSTRUCT lphRootKey = NULL,lphTopKey = NULL;
static char RootKeyName[]=".classes", TopKeyName[] = "(null)";
static char RootKeyName[]=".classes", TopKeyName[] = "[top-null]";
/*************************************************************************
* SHELL_RegCheckForRoot() internal use only
......@@ -62,7 +63,7 @@ static LONG SHELL_RegCheckForRoot()
*/
LONG RegOpenKey(HKEY hKey, LPCSTR lpSubKey, HKEY FAR *lphKey)
{
LPKEYSTRUCT lpKey;
LPKEYSTRUCT lpKey,lpNextKey;
LPCSTR ptr;
char str[128];
LONG dwRet;
......@@ -71,18 +72,21 @@ LONG RegOpenKey(HKEY hKey, LPCSTR lpSubKey, HKEY FAR *lphKey)
if (dwRet != ERROR_SUCCESS) return dwRet;
dprintf_reg(stddeb, "RegOpenKey(%08lX, %p='%s', %p)\n",
hKey, lpSubKey, lpSubKey, lphKey);
if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;
if (lphKey == NULL) return ERROR_INVALID_PARAMETER;
switch(hKey) {
case 0:
lpKey = lphTopKey; break;
case HKEY_CLASSES_ROOT: /* == 1 */
case 0x80000000:
lpKey = lphRootKey; break;
default:
dprintf_reg(stddeb,"RegOpenKey // specific key = %08lX !\n", hKey);
lpKey = (LPKEYSTRUCT)GlobalLock(hKey);
}
if (!*lpSubKey) { *lphKey = hKey; return ERROR_SUCCESS; }
if (lpSubKey == NULL || !*lpSubKey) {
*lphKey = hKey;
return ERROR_SUCCESS;
}
while(*lpSubKey) {
ptr = strchr(lpSubKey,'\\');
if (!ptr) ptr = lpSubKey + strlen(lpSubKey);
......@@ -91,8 +95,11 @@ LONG RegOpenKey(HKEY hKey, LPCSTR lpSubKey, HKEY FAR *lphKey)
lpSubKey = ptr;
if (*lpSubKey) lpSubKey++;
lpKey = lpKey->lpSubLvl;
while(lpKey != NULL && strcmp(lpKey->lpSubKey, str) != 0) { lpKey = lpKey->lpNextKey; }
lpNextKey = lpKey->lpSubLvl;
while(lpKey != NULL && strcmp(lpKey->lpSubKey, str) != 0) {
lpKey = lpNextKey;
if (lpKey) lpNextKey = lpKey->lpNextKey;
}
if (lpKey == NULL) {
dprintf_reg(stddeb,"RegOpenKey: key %s not found!\n",str);
return ERROR_BADKEY;
......@@ -119,18 +126,21 @@ LONG RegCreateKey(HKEY hKey, LPCSTR lpSubKey, HKEY FAR *lphKey)
dwRet = SHELL_RegCheckForRoot();
if (dwRet != ERROR_SUCCESS) return dwRet;
dprintf_reg(stddeb, "RegCreateKey(%08lX, '%s', %p)\n", hKey, lpSubKey, lphKey);
if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;
if (lphKey == NULL) return ERROR_INVALID_PARAMETER;
switch(hKey) {
case 0:
lpKey = lphTopKey; break;
case HKEY_CLASSES_ROOT: /* == 1 */
case 0x80000000:
lpKey = lphRootKey; break;
default:
dprintf_reg(stddeb,"RegCreateKey // specific key = %08lX !\n", hKey);
lpKey = (LPKEYSTRUCT)GlobalLock(hKey);
}
if (!*lpSubKey) { *lphKey = hKey; return ERROR_SUCCESS; }
if (lpSubKey == NULL || !*lpSubKey) {
*lphKey = hKey;
return ERROR_SUCCESS;
}
while (*lpSubKey) {
dprintf_reg(stddeb, "RegCreateKey: Looking for subkey %s\n", lpSubKey);
ptr = strchr(lpSubKey,'\\');
......@@ -210,7 +220,7 @@ LONG RegSetValue(HKEY hKey, LPCSTR lpSubKey, DWORD dwType,
LONG dwRet;
dprintf_reg(stddeb, "RegSetValue(%08lX, '%s', %08lX, '%s', %08lX);\n",
hKey, lpSubKey, dwType, lpVal, dwIgnored);
if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;
/*if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;*/
if (lpVal == NULL) return ERROR_INVALID_PARAMETER;
if ((dwRet = RegOpenKey(hKey, lpSubKey, &hRetKey)) != ERROR_SUCCESS) {
dprintf_reg(stddeb, "RegSetValue // key not found ... so create it !\n");
......@@ -240,7 +250,7 @@ LONG RegQueryValue(HKEY hKey, LPCSTR lpSubKey, LPSTR lpVal, LONG FAR *lpcb)
int size;
dprintf_reg(stddeb, "RegQueryValue(%08lX, '%s', %p, %p);\n",
hKey, lpSubKey, lpVal, lpcb);
if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;
/*if (lpSubKey == NULL) return ERROR_INVALID_PARAMETER;*/
if (lpVal == NULL) return ERROR_INVALID_PARAMETER;
if (lpcb == NULL) return ERROR_INVALID_PARAMETER;
if (!*lpcb) return ERROR_INVALID_PARAMETER;
......@@ -285,12 +295,12 @@ LONG RegEnumKey(HKEY hKey, DWORD dwSubKey, LPSTR lpBuf, DWORD dwSize)
case 0:
lpKey = lphTopKey; break;
case HKEY_CLASSES_ROOT: /* == 1 */
case 0x80000000:
lpKey = lphRootKey; break;
default:
dprintf_reg(stddeb,"RegEnumKey // specific key = %08lX !\n", hKey);
lpKey = (LPKEYSTRUCT)GlobalLock(hKey);
}
lpKey = lpKey->lpSubLvl;
while(lpKey != NULL){
if (!dwSubKey){
......@@ -301,7 +311,7 @@ LONG RegEnumKey(HKEY hKey, DWORD dwSubKey, LPSTR lpBuf, DWORD dwSize)
return ERROR_SUCCESS;
}
dwSubKey--;
lpKey = lpKey->lpNextKey;
lpKey = lpKey->lpNextKey;
}
dprintf_reg(stddeb, "RegEnumKey: key not found!\n");
return ERROR_INVALID_PARAMETER;
......@@ -351,30 +361,75 @@ BOOL DragQueryPoint(HDROP h, POINT FAR *p)
HINSTANCE ShellExecute(HWND hWnd, LPCSTR lpOperation, LPCSTR lpFile, LPCSTR lpParameters, LPCSTR lpDirectory, int iShowCmd)
{
char cmd[400];
char *p,*x;
long len;
char subclass[200];
/* OK. We are supposed to lookup the program associated with lpFile,
* then to execute it using that program. If lpFile is a program,
* we have to pass the parameters. If an instance is already running,
* we might have to send DDE commands.
*/
dprintf_exec(stddeb, "ShellExecute(%4X,'%s','%s','%s','%s',%x)\n",
hWnd, lpOperation ? lpOperation:"<null>", lpFile ? lpFile:"<null>",
lpParameters ? lpParameters : "<null>",
lpDirectory ? lpDirectory : "<null>", iShowCmd);
if(lpOperation && !strcasecmp(lpOperation,"print"))
{
fprintf(stderr, "Shell print %s: not supported\n", lpFile);
return 2; /* file not found */
}
if(lpOperation && !strcasecmp(lpOperation,"open"))
{
fprintf(stderr, "ShellExecute: Unknown operation %s\n",lpOperation);
return 2;
if (lpFile==NULL) return 0; /* should not happen */
if (lpOperation==NULL) /* default is open */
lpOperation="open";
p=strrchr(lpFile,'.');
if (p!=NULL) {
x=p; /* the suffixes in the register database are lowercased */
while (*x) {*x=tolower(*x);x++;}
}
/* OK. We are supposed to lookup the program associated with lpFile,
then to execute it using that program. If lpFile is a program,
we have to pass the parameters. If an instance is already running,
we might have to send DDE commands.
This implementation does none of that. It assumes lpFile is a program.
Plain WinExec will do what we need */
if(lpParameters)
if (p==NULL || !strcmp(p,".exe")) {
p=".exe";
if (lpParameters) {
sprintf(cmd,"%s %s",lpFile,lpParameters);
else
} else {
strcpy(cmd,lpFile);
}
} else {
len=200;
if (RegQueryValue(HKEY_CLASSES_ROOT,p,subclass,&len)==ERROR_SUCCESS) {
if (len>20)
fprintf(stddeb,"ShellExecute:subclass with len %ld? (%s), please report.\n",len,subclass);
subclass[len]='\0';
strcat(subclass,"\\shell\\");
strcat(subclass,lpOperation);
strcat(subclass,"\\command");
dprintf_exec(stddeb,"ShellExecute:looking for %s.\n",subclass);
len=400;
if (RegQueryValue(HKEY_CLASSES_ROOT,subclass,cmd,&len)==ERROR_SUCCESS) {
char *t;
dprintf_exec(stddeb,"ShellExecute:...got %s\n",cmd);
cmd[len]='\0';
t=strstr(cmd,"%1");
if (t==NULL) {
strcat(cmd," ");
strcat(cmd,lpFile);
} else {
char *s;
s=malloc(len+strlen(lpFile)+10);
strncpy(s,cmd,t-cmd);
strcat(s,lpFile);
strcat(s,t+2);
strcpy(cmd,s);
free(s);
}
/* does this use %x magic too? */
if (lpParameters) {
strcat(cmd," ");
strcat(cmd,lpParameters);
}
} else {
fprintf(stddeb,"ShellExecute: No %s\\shell\\%s\\command found for \"%s\" suffix.\n",subclass,lpOperation,p);
return 14; /* unknown type */
}
} else {
fprintf(stddeb,"ShellExecute: No operation found for \"%s\" suffix.\n",p);
return 14; /* file not found */
}
}
return WinExec(cmd,iShowCmd);
}
......
......@@ -26,26 +26,16 @@ $(MODULE).o: $(OBJS)
depend:
sed '/\#\#\# Dependencies/q' < Makefile > tmp_make
$(CC) $(DIVINCL) $(XINCL) -MM *.c >> tmp_make
cp tmp_make Makefile
rm tmp_make
mv tmp_make Makefile
clean:
rm -f *.o \#*\# *~ tmp_make
distclean: clean
rm Makefile
rm -f Makefile
countryclean:
NAMES = $(SRCS:.c=)
winelibclean:
for i in $(NAMES); do \
if test `grep -c WINELIB $$i.c` -ne 0; then \
rm $$i.o; \
fi; \
done
dummy:
### Dependencies:
......@@ -22,147 +22,153 @@
*
* Handler for int 31h (DPMI).
*/
void INT_Int31Handler( struct sigcontext_struct sigcontext )
void INT_Int31Handler( struct sigcontext_struct context )
{
#define context (&sigcontext)
DWORD dw;
BYTE *ptr;
ResetCflag;
switch(AX)
RESET_CFLAG(&context);
switch(AX_reg(&context))
{
case 0x0000: /* Allocate LDT descriptors */
if (!(AX = AllocSelectorArray( CX )))
if (!(AX_reg(&context) = AllocSelectorArray( CX_reg(&context) )))
{
AX = 0x8011; /* descriptor unavailable */
SetCflag;
AX_reg(&context) = 0x8011; /* descriptor unavailable */
SET_CFLAG(&context);
}
break;
case 0x0001: /* Free LDT descriptor */
if (FreeSelector( BX ))
if (FreeSelector( BX_reg(&context) ))
{
AX = 0x8022; /* invalid selector */
SetCflag;
AX_reg(&context) = 0x8022; /* invalid selector */
SET_CFLAG(&context);
}
break;
case 0x0003: /* Get next selector increment */
AX = __AHINCR;
AX_reg(&context) = __AHINCR;
break;
case 0x0004: /* Lock selector (not supported) */
AX = 0; /* FIXME: is this a correct return value? */
AX_reg(&context) = 0; /* FIXME: is this a correct return value? */
break;
case 0x0005: /* Unlock selector (not supported) */
AX = 0; /* FIXME: is this a correct return value? */
AX_reg(&context) = 0; /* FIXME: is this a correct return value? */
break;
case 0x0006: /* Get selector base address */
if (!(dw = GetSelectorBase( BX )))
if (!(dw = GetSelectorBase( BX_reg(&context) )))
{
AX = 0x8022; /* invalid selector */
SetCflag;
AX_reg(&context) = 0x8022; /* invalid selector */
SET_CFLAG(&context);
}
else
{
CX = HIWORD(dw);
DX = LOWORD(dw);
CX_reg(&context) = HIWORD(dw);
DX_reg(&context) = LOWORD(dw);
}
break;
case 0x0007: /* Set selector base address */
SetSelectorBase( BX, MAKELONG( DX, CX ) );
SetSelectorBase( BX_reg(&context),
MAKELONG( DX_reg(&context), CX_reg(&context) ) );
break;
case 0x0008: /* Set selector limit */
SetSelectorLimit( BX, MAKELONG( DX, CX ) );
SetSelectorLimit( BX_reg(&context),
MAKELONG( DX_reg(&context), CX_reg(&context) ) );
break;
case 0x0009: /* Set selector access rights */
SelectorAccessRights( BX, 1, CX );
SelectorAccessRights( BX_reg(&context), 1, CX_reg(&context) );
case 0x000a: /* Allocate selector alias */
if (!(AX = AllocCStoDSAlias( BX )))
if (!(AX_reg(&context) = AllocCStoDSAlias( BX_reg(&context) )))
{
AX = 0x8011; /* descriptor unavailable */
SetCflag;
AX_reg(&context) = 0x8011; /* descriptor unavailable */
SET_CFLAG(&context);
}
break;
case 0x000b: /* Get descriptor */
{
ldt_entry entry;
LDT_GetEntry( SELECTOR_TO_ENTRY(BX), &entry );
LDT_GetEntry( SELECTOR_TO_ENTRY( BX_reg(&context) ), &entry );
/* FIXME: should use ES:EDI for 32-bit clients */
LDT_EntryToBytes( PTR_SEG_OFF_TO_LIN( ES, DI ), &entry );
LDT_EntryToBytes( PTR_SEG_OFF_TO_LIN( ES_reg(&context),
DI_reg(&context) ), &entry );
}
break;
case 0x000c: /* Set descriptor */
{
ldt_entry entry;
LDT_BytesToEntry( PTR_SEG_OFF_TO_LIN( ES, DI ), &entry );
LDT_GetEntry( SELECTOR_TO_ENTRY(BX), &entry );
LDT_BytesToEntry( PTR_SEG_OFF_TO_LIN( ES_reg(&context),
DI_reg(&context) ), &entry );
LDT_GetEntry( SELECTOR_TO_ENTRY( BX_reg(&context) ), &entry );
}
break;
case 0x000d: /* Allocate specific LDT descriptor */
AX = 0x8011; /* descriptor unavailable */
SetCflag;
AX_reg(&context) = 0x8011; /* descriptor unavailable */
SET_CFLAG(&context);
break;
case 0x0204: /* Get protected mode interrupt vector */
dw = (DWORD)INT_GetHandler( BL );
CX = HIWORD(dw);
DX = LOWORD(dw);
dw = (DWORD)INT_GetHandler( BL_reg(&context) );
CX_reg(&context) = HIWORD(dw);
DX_reg(&context) = LOWORD(dw);
break;
case 0x0205: /* Set protected mode interrupt vector */
INT_SetHandler( BL, (SEGPTR)MAKELONG( DX, CX ) );
INT_SetHandler( BL_reg(&context),
(SEGPTR)MAKELONG( DX_reg(&context), CX_reg(&context) ));
break;
case 0x0400: /* Get DPMI version */
AX = 0x005a; /* DPMI version 0.90 */
BX = 0x0005; /* Flags: 32-bit, virtual memory */
CL = 3; /* CPU type: 386 */
DX = 0x0102; /* Master and slave interrupt controller base */
AX_reg(&context) = 0x005a; /* DPMI version 0.90 */
BX_reg(&context) = 0x0005; /* Flags: 32-bit, virtual memory */
CL_reg(&context) = 3; /* CPU type: 386 */
DX_reg(&context) = 0x0102; /* Master/slave interrupt controller base*/
break;
case 0x0500: /* Get free memory information */
ptr = (BYTE *)PTR_SEG_OFF_TO_LIN( ES, DI );
ptr = (BYTE *)PTR_SEG_OFF_TO_LIN( ES_reg(&context), DI_reg(&context) );
*(DWORD *)ptr = 0x00ff0000; /* Largest block available */
memset( ptr + 4, 0xff, 0x2c ); /* No other information supported */
break;
case 0x0501: /* Allocate memory block */
if (!(ptr = (BYTE *)malloc( MAKELONG( CX, BX ) )))
if (!(ptr = (BYTE *)malloc( MAKELONG( CX_reg(&context),
BX_reg(&context) ) )))
{
AX = 0x8012; /* linear memory not available */
SetCflag;
AX_reg(&context) = 0x8012; /* linear memory not available */
SET_CFLAG(&context);
}
else
{
BX = SI = HIWORD(ptr);
CX = DI = LOWORD(ptr);
BX_reg(&context) = SI_reg(&context) = HIWORD(ptr);
CX_reg(&context) = DI_reg(&context) = LOWORD(ptr);
}
break;
case 0x0502: /* Free memory block */
free( (void *)MAKELONG( DI, SI ) );
free( (void *)MAKELONG( DI_reg(&context), SI_reg(&context) ) );
break;
case 0x0503: /* Resize memory block */
if (!(ptr = (BYTE *)realloc( (void *)MAKELONG(DI,SI),MAKELONG(CX,BX))))
if (!(ptr = (BYTE *)realloc( (void *)MAKELONG(DI_reg(&context),SI_reg(&context)),
MAKELONG(CX_reg(&context),BX_reg(&context)))))
{
AX = 0x8012; /* linear memory not available */
SetCflag;
AX_reg(&context) = 0x8012; /* linear memory not available */
SET_CFLAG(&context);
}
else
{
BX = SI = HIWORD(ptr);
CX = DI = LOWORD(ptr);
BX_reg(&context) = SI_reg(&context) = HIWORD(ptr);
CX_reg(&context) = DI_reg(&context) = LOWORD(ptr);
}
break;
......@@ -173,10 +179,9 @@ void INT_Int31Handler( struct sigcontext_struct sigcontext )
break; /* Just ignore it */
default:
INT_BARF( 0x31 );
AX = 0x8001; /* unsupported function */
SetCflag;
INT_BARF( &context, 0x31 );
AX_reg(&context) = 0x8001; /* unsupported function */
SET_CFLAG(&context);
break;
}
#undef context
}
#include <stdlib.h>
#include <stdio.h>
#include "wine.h"
#include "miscemu.h"
#include "registers.h"
#include "stddebug.h"
/* #define DEBUG_INT */
#include "debug.h"
struct Win87EmInfoStruct {
unsigned short Version;
unsigned short SizeSaveArea;
unsigned short WinDataSeg;
unsigned short WinCodeSeg;
unsigned short Have80x87;
unsigned short Unused;
struct Win87EmInfoStruct
{
unsigned short Version;
unsigned short SizeSaveArea;
unsigned short WinDataSeg;
unsigned short WinCodeSeg;
unsigned short Have80x87;
unsigned short Unused;
};
void
WIN87_fpmath( struct sigcontext_struct sigcontext )
{
/* Declare a context pointer so that registers macros work */
struct sigcontext_struct *context = &sigcontext;
/* Implementing this is easy cause Linux and *BSD* ALWAYS have a numerical
* coprocessor. (either real or emulated on kernellevel)
*/
/* win87em.dll also sets interrupt vectors: 2 (NMI), 0x34 - 0x3f (emulator
* calls of standard libraries, see Ralph Browns interrupt list), 0x75
* (int13 error reporting of coprocessor)
*/
/* have a look at /usr/src/linux/arch/i386/math-emu/ *.[ch] for more info
* especially control_w.h and status_w.h
*/
/* FIXME: Only skeletal implementation for now */
dprintf_int(stddeb, "_fpmath: (%x:%lx %x %x)\n", CS, EIP, ES, BX );
void WIN87_fpmath( struct sigcontext_struct context )
{
dprintf_int(stddeb, "_fpmath: (cs:eip=%x:%lx es=%x bx=%04x ax=%04x dx==%04x)\n",
CS_reg(&context), EIP_reg(&context),
ES_reg(&context), BX_reg(&context),
AX_reg(&context), DX_reg(&context) );
switch(BX)
switch(BX_reg(&context))
{
case 11:
AX = 1;
case 0: /* install (increase instanceref) emulator, install NMI vector */
AX_reg(&context) = 0;
break;
case 1: /* Init Emulator */
AX_reg(&context) = 0;
break;
case 2: /* deinstall emulator (decrease instanceref), deinstall NMI vector
* if zero. Every '0' call should have a matching '2' call.
*/
AX_reg(&context) = 0;
break;
case 3:
/*INT_SetHandler(0x3E,MAKELONG(AX,DX));*/
break;
case 4: /* set control word (& ~(CW_Denormal|CW_Invalid)) */
/* OUT: newset control word in AX */
break;
case 5: /* return internal control word in AX */
break;
default:
AX = 0;
case 6: /* round top of stack to integer using method AX & 0x0C00 */
/* returns current controlword */
break;
case 7: /* POP top of stack as integer into DX:AX */
/* IN: AX&0x0C00 rounding protocol */
/* OUT: DX:AX variable popped */
{
DWORD dw,junk;
/* I don't know much about asm() programming. This could be
* wrong.
*/
__asm__("fistp %1\nwait":"=m" (junk):"m" (dw):"memory");
dprintf_int(stddeb,"emulate.c:On top of stack was %ld\n",dw);
AX_reg(&context) = LOWORD(dw);
DX_reg(&context) = HIWORD(dw);
}
break;
case 8: /* restore internal control words from emulator control word */
break;
case 9: /* clear emu control word and some other things */
break;
case 10: /* dunno. but looks like returning nr. of things on stack in AX */
break;
case 11: /* just returns the installed flag in DX:AX */
DX_reg(&context) = 0;
AX_reg(&context) = 1;
break;
case 12: /* save AX in some internal state var */
break;
default: /* error. Say that loud and clear */
AX_reg(&context) = DX_reg(&context) = 0xFFFF;
break;
}
}
void
WIN87_WinEm87Info(struct Win87EmInfoStruct *pWIS, int cbWin87EmInfoStruct)
{
......
......@@ -21,8 +21,8 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
int prefix, segprefix, repX, long_op, long_addr;
BYTE *instr;
long_op = long_addr = (GET_SEL_FLAGS(CS) & LDT_FLAGS_32BIT) != 0;
instr = (BYTE *) PTR_SEG_OFF_TO_LIN( CS, long_op ? EIP : IP );
long_op = long_addr = (GET_SEL_FLAGS(CS_reg(context)) & LDT_FLAGS_32BIT) != 0;
instr = (BYTE *) PTR_SEG_OFF_TO_LIN( CS_reg(context), EIP_reg(context) );
/* First handle any possible prefix */
......@@ -34,22 +34,22 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
switch(*instr)
{
case 0x2e:
segprefix = CS;
segprefix = CS_reg(context);
break;
case 0x36:
segprefix = SS;
segprefix = SS_reg(context);
break;
case 0x3e:
segprefix = DS;
segprefix = DS_reg(context);
break;
case 0x26:
segprefix = ES;
segprefix = ES_reg(context);
break;
case 0x64:
segprefix = FS;
segprefix = FS_reg(context);
break;
case 0x65:
segprefix = GS;
segprefix = GS_reg(context);
break;
case 0x66:
long_op = !long_op; /* opcode size prefix */
......@@ -72,7 +72,7 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
if (prefix)
{
instr++;
EIP++;
EIP_reg(context)++;
}
}
......@@ -90,15 +90,16 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
{
SEGPTR addr = INT_GetHandler( instr[1] );
/* FIXME: should check the stack 'big' bit */
WORD *stack = (WORD *)PTR_SEG_OFF_TO_LIN( SS, SP );
WORD *stack = (WORD *)PTR_SEG_OFF_TO_LIN( SS_reg(context),
SP_reg(context) );
/* Push the flags and return address on the stack */
*(--stack) = FL;
*(--stack) = CS;
*(--stack) = IP + 2;
SP -= 3 * sizeof(WORD);
*(--stack) = FL_reg(context);
*(--stack) = CS_reg(context);
*(--stack) = IP_reg(context) + 2;
SP_reg(context) -= 3 * sizeof(WORD);
/* Jump to the interrupt handler */
CS = HIWORD(addr);
EIP = LOWORD(addr);
CS_reg(context) = HIWORD(addr);
EIP_reg(context) = LOWORD(addr);
}
break;
......@@ -106,73 +107,75 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
if (long_op)
{
/* FIXME: should check the stack 'big' bit */
DWORD *stack = (DWORD *)PTR_SEG_OFF_TO_LIN( SS, SP );
EIP = *stack++;
CS = *stack++;
EFL = *stack;
SP += 3*sizeof(DWORD); /* Pop the return address and flags */
DWORD *stack = (DWORD *)PTR_SEG_OFF_TO_LIN( SS_reg(context),
SP_reg(context) );
EIP_reg(context) = *stack++;
CS_reg(context) = *stack++;
EFL_reg(context) = *stack;
SP_reg(context) += 3*sizeof(DWORD); /* Pop the return address and flags */
}
else
{
/* FIXME: should check the stack 'big' bit */
WORD *stack = (WORD *)PTR_SEG_OFF_TO_LIN( SS, SP );
EIP = *stack++;
CS = *stack++;
FL = *stack;
SP += 3*sizeof(WORD); /* Pop the return address and flags */
WORD *stack = (WORD *)PTR_SEG_OFF_TO_LIN( SS_reg(context),
SP_reg(context) );
EIP_reg(context) = *stack++;
CS_reg(context) = *stack++;
FL_reg(context) = *stack;
SP_reg(context) += 3*sizeof(WORD); /* Pop the return address and flags */
}
break;
case 0xe4: /* inb al,XX */
AL = inport( instr[1], 1 );
EIP += 2;
AL_reg(context) = inport( instr[1], 1 );
EIP_reg(context) += 2;
break;
case 0xe5: /* in (e)ax,XX */
if (long_op) EAX = inport( instr[1], 4 );
else AX = inport( instr[1], 2 );
EIP += 2;
if (long_op) EAX_reg(context) = inport( instr[1], 4 );
else AX_reg(context) = inport( instr[1], 2 );
EIP_reg(context) += 2;
break;
case 0xe6: /* outb XX,al */
outport( instr[1], 1, AL );
EIP += 2;
outport( instr[1], 1, AL_reg(context) );
EIP_reg(context) += 2;
break;
case 0xe7: /* out XX,(e)ax */
if (long_op) outport( instr[1], 4, EAX );
else outport( instr[1], 2, AX );
EIP += 2;
if (long_op) outport( instr[1], 4, EAX_reg(context) );
else outport( instr[1], 2, AX_reg(context) );
EIP_reg(context) += 2;
break;
case 0xec: /* inb al,dx */
AL = inport( DX, 1 );
EIP++;
AL_reg(context) = inport( DX_reg(context), 1 );
EIP_reg(context)++;
break;
case 0xed: /* in (e)ax,dx */
if (long_op) EAX = inport( DX, 4 );
else AX = inport( DX, 2 );
EIP++;
if (long_op) EAX_reg(context) = inport( DX_reg(context), 4 );
else AX_reg(context) = inport( DX_reg(context), 2 );
EIP_reg(context)++;
break;
case 0xee: /* outb dx,al */
outport( DX, 1, AL );
EIP++;
outport( DX_reg(context), 1, AL_reg(context) );
EIP_reg(context)++;
break;
case 0xef: /* out dx,(e)ax */
if (long_op) outport( DX, 4, EAX );
else outport( DX, 2, AX );
EIP++;
if (long_op) outport( DX_reg(context), 4, EAX_reg(context) );
else outport( DX_reg(context), 2, AX_reg(context) );
EIP_reg(context)++;
break;
case 0xfa: /* cli, ignored */
EIP++;
EIP_reg(context)++;
break;
case 0xfb: /* sti, ignored */
EIP++;
EIP_reg(context)++;
break;
case 0x6c: /* insb */
......@@ -182,11 +185,12 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
{
int typ = *instr; /* Just in case it's overwritten. */
int outp = (typ >= 0x6e);
unsigned long count = repX ? (long_addr ? ECX : CX) : 1;
unsigned long count = repX ?
(long_addr ? ECX_reg(context) : CX_reg(context)) : 1;
int opsize = (typ & 1) ? (long_op ? 4 : 2) : 1;
int step = (EFL & 0x400) ? -opsize : +opsize;
/* FIXME: Check this, please. */
int seg = outp ? (segprefix >= 0 ? segprefix : DS) : ES;
int step = (EFL_reg(context) & 0x400) ? -opsize : +opsize;
int seg = outp ? (segprefix >= 0 ? segprefix : DS_reg(context))
: ES_reg(context);
if (outp)
/* FIXME: Check segment readable. */
......@@ -197,53 +201,51 @@ BOOL INSTR_EmulateInstruction( struct sigcontext_struct *context )
if (repX)
if (long_addr)
ECX = 0;
ECX_reg(context) = 0;
else
CX = 0;
CX_reg(context) = 0;
while (count-- > 0)
{
void *data;
if (outp)
{
data = PTR_SEG_OFF_TO_LIN (seg, long_addr ? ESI : SI);
if (long_addr)
ESI += step;
else
SI += step;
}
{
data = PTR_SEG_OFF_TO_LIN (seg,
long_addr ? ESI_reg(context) : SI_reg(context));
if (long_addr) ESI_reg(context) += step;
else SI_reg(context) += step;
}
else
{
data = PTR_SEG_OFF_TO_LIN (seg, long_addr ? EDI : DI);
if (long_addr)
EDI += step;
else
DI += step;
}
{
data = PTR_SEG_OFF_TO_LIN (seg,
long_addr ? EDI_reg(context) : DI_reg(context));
if (long_addr) EDI_reg(context) += step;
else DI_reg(context) += step;
}
switch (typ)
{
{
case 0x6c:
*((BYTE *)data) = inport (DX, 1);
*((BYTE *)data) = inport( DX_reg(context), 1);
break;
case 0x6d:
if (long_op)
*((DWORD *)data) = inport (DX, 4);
*((DWORD *)data) = inport( DX_reg(context), 4);
else
*((WORD *)data) = inport (DX, 2);
*((WORD *)data) = inport( DX_reg(context), 2);
break;
case 0x6e:
outport (DX, 1, *((BYTE *)data));
outport( DX_reg(context), 1, *((BYTE *)data));
break;
case 0x6f:
if (long_op)
outport (DX, 4, *((DWORD *)data));
outport( DX_reg(context), 4, *((DWORD *)data));
else
outport (DX, 2, *((WORD *)data));
outport( DX_reg(context), 2, *((WORD *)data));
break;
}
}
EIP++;
EIP_reg(context)++;
break;
}
......
......@@ -13,29 +13,27 @@
*
* Handler for int 10h (video).
*/
void INT_Int10Handler( struct sigcontext_struct sigcontext )
void INT_Int10Handler( struct sigcontext_struct context )
{
#define context (&sigcontext)
switch(AH)
switch(AH_reg(&context))
{
case 0x0f:
AL = 0x5b;
AL_reg(&context) = 0x5b;
break;
case 0x12:
if (BL == 0x10)
if (BL_reg(&context) == 0x10)
{
BX = 0x0003;
CX = 0x0009;
BX_reg(&context) = 0x0003;
CX_reg(&context) = 0x0009;
}
break;
case 0x1a:
BX = 0x0008;
BX_reg(&context) = 0x0008;
break;
default:
INT_BARF( 0x10 );
INT_BARF( &context, 0x10 );
}
#undef context
}
......@@ -13,29 +13,28 @@
*
* Handler for int 13h (disk I/O).
*/
void INT_Int13Handler( struct sigcontext_struct sigcontext )
void INT_Int13Handler( struct sigcontext_struct context )
{
#define context (&sigcontext)
switch(AH)
switch(AH_reg(&context))
{
case 0x00: /* RESET DISK SYSTEM */
case 0x04: /* VERIFY DISK SECTOR(S) */
AH = 0;
AH_reg(&context) = 0;
break;
case 0x05: /* FORMAT TRACK */
AH = 0x0c;
SetCflag;
AH_reg(&context) = 0x0c;
SET_CFLAG(&context);
break;
case 0x06: /* FORMAT TRACK AND SET BAD SECTOR FLAGS */
case 0x07: /* FORMAT DRIVE STARTING AT GIVEN TRACK */
AH = 0x0c;
AH_reg(&context) = 0x0c;
break;
case 0x08: /* GET DRIVE PARAMETERS */
AH = (DL & 0x80) ? 0x07 : 0x01;
SetCflag;
AH_reg(&context) = (DL_reg(&context) & 0x80) ? 0x07 : 0x01;
SET_CFLAG(&context);
break;
case 0x09: /* INITIALIZE CONTROLLER WITH DRIVE PARAMETERS */
......@@ -44,19 +43,18 @@ void INT_Int13Handler( struct sigcontext_struct sigcontext )
case 0x10: /* CHECK IF DRIVE READY */
case 0x11: /* RECALIBRATE DRIVE */
case 0x14: /* CONTROLLER INTERNAL DIAGNOSTIC */
AH = 0;
AH_reg(&context) = 0;
break;
case 0x0e: /* READ SECTOR BUFFER (XT only) */
case 0x0f: /* WRITE SECTOR BUFFER (XT only) */
case 0x12: /* CONTROLLER RAM DIAGNOSTIC (XT,PS) */
case 0x13: /* DRIVE DIAGNOSTIC (XT,PS) */
AH = 0x01;
SetCflag;
AH_reg(&context) = 0x01;
SET_CFLAG(&context);
break;
default:
INT_BARF( 0x13 );
INT_BARF( &context, 0x13 );
}
#undef context
}
......@@ -19,15 +19,15 @@
*
* Handler for int 1ah (date and time).
*/
void INT_Int1aHandler( struct sigcontext_struct sigcontext )
void INT_Int1aHandler( struct sigcontext_struct context )
{
#define context (&sigcontext)
time_t ltime;
DWORD ticks;
struct tm *bdtime;
struct timeval tvs;
time_t ltime;
DWORD ticks;
struct tm *bdtime;
struct timeval tvs;
switch(AH) {
switch(AH_reg(&context))
{
case 0:
/* This should give us the (approximately) correct
* 18.206 clock ticks per second since midnight
......@@ -38,9 +38,9 @@ void INT_Int1aHandler( struct sigcontext_struct sigcontext )
ticks = (((bdtime->tm_hour * 3600 + bdtime->tm_min * 60 +
bdtime->tm_sec) * 18206) / 1000) +
(tvs.tv_usec / 54927);
CX = ticks >> 16;
DX = ticks & 0x0000FFFF;
AX = 0; /* No midnight rollover */
CX_reg(&context) = HIWORD(ticks);
DX_reg(&context) = LOWORD(ticks);
AX_reg(&context) = 0; /* No midnight rollover */
dprintf_int(stddeb,"int1a_00 // ticks=%ld\n", ticks);
break;
......@@ -48,14 +48,17 @@ void INT_Int1aHandler( struct sigcontext_struct sigcontext )
ltime = time(NULL);
bdtime = localtime(&ltime);
CX = (BIN_TO_BCD(bdtime->tm_hour)<<8) | BIN_TO_BCD(bdtime->tm_min);
DX = (BIN_TO_BCD(bdtime->tm_sec)<<8);
CX_reg(&context) = (BIN_TO_BCD(bdtime->tm_hour)<<8) |
BIN_TO_BCD(bdtime->tm_min);
DX_reg(&context) = (BIN_TO_BCD(bdtime->tm_sec)<<8);
case 4:
ltime = time(NULL);
bdtime = localtime(&ltime);
CX = (BIN_TO_BCD(bdtime->tm_year/100)<<8) | BIN_TO_BCD((bdtime->tm_year-1900)%100);
DX = (BIN_TO_BCD(bdtime->tm_mon)<<8) | BIN_TO_BCD(bdtime->tm_mday);
CX_reg(&context) = (BIN_TO_BCD(bdtime->tm_year/100)<<8) |
BIN_TO_BCD((bdtime->tm_year-1900)%100);
DX_reg(&context) = (BIN_TO_BCD(bdtime->tm_mon)<<8) |
BIN_TO_BCD(bdtime->tm_mday);
break;
/* setting the time,date or RTC is not allow -EB */
......@@ -72,7 +75,6 @@ void INT_Int1aHandler( struct sigcontext_struct sigcontext )
break;
default:
INT_BARF( 0x1a );
}
#undef context
INT_BARF( &context, 0x1a );
}
}
......@@ -16,39 +16,38 @@
*
* Handler for int 25h (absolute disk read).
*/
void INT_Int25Handler( struct sigcontext_struct sigcontext )
void INT_Int25Handler( struct sigcontext_struct context )
{
#define context (&sigcontext)
BYTE *dataptr = PTR_SEG_OFF_TO_LIN(DS, BX);
DWORD begin, length;
BYTE *dataptr = PTR_SEG_OFF_TO_LIN( DS_reg(&context), BX_reg(&context) );
DWORD begin, length;
if(!DOS_ValidDrive(AL))
{
SetCflag;
AX = 0x0101; /* unknown unit */
return;
}
if (!DOS_ValidDrive(AL_reg(&context)))
{
SET_CFLAG(&context);
AX_reg(&context) = 0x0101; /* unknown unit */
return;
}
if (CX == 0xffff) {
begin = getdword(dataptr);
length = getword(&dataptr[4]);
dataptr = (BYTE *) PTR_SEG_TO_LIN(getdword(&dataptr[6]));
} else {
begin = DX;
length = CX;
}
dprintf_int(stdnimp, "int25: abs diskread, drive %d, sector %ld, "
"count %ld, buffer %d\n", AL, begin, length, (int) dataptr);
if (CX_reg(&context) == 0xffff)
{
begin = getdword(dataptr);
length = getword(&dataptr[4]);
dataptr = (BYTE *) PTR_SEG_TO_LIN(getdword(&dataptr[6]));
}
else
{
begin = DX_reg(&context);
length = CX_reg(&context);
}
dprintf_int( stdnimp, "int25: abs diskread, drive %d, sector %ld, "
"count %ld, buffer %d\n",
AL_reg(&context), begin, length, (int) dataptr);
memset(dataptr, 0, length * 512);
memset(dataptr, 0, length * 512);
if (begin == 0 && length > 1)
*(dataptr + 512) = 0xf8;
if (begin == 0 && length > 1) *(dataptr + 512) = 0xf8;
if (begin == 1)
*dataptr = 0xf8;
if (begin == 1) *dataptr = 0xf8;
ResetCflag;
#undef context
RESET_CFLAG(&context);
}
......@@ -15,32 +15,33 @@
*
* Handler for int 26h (absolute disk read).
*/
void INT_Int26Handler( struct sigcontext_struct sigcontext )
void INT_Int26Handler( struct sigcontext_struct context )
{
#define context (&sigcontext)
BYTE *dataptr = PTR_SEG_OFF_TO_LIN(DS, BX);
DWORD begin, length;
BYTE *dataptr = PTR_SEG_OFF_TO_LIN( DS_reg(&context), BX_reg(&context) );
DWORD begin, length;
if(!DOS_ValidDrive(AL))
{
SetCflag;
AX = 0x0101; /* unknown unit */
return;
}
if (!DOS_ValidDrive(AL_reg(&context)))
{
SET_CFLAG(&context);
AX_reg(&context) = 0x0101; /* unknown unit */
return;
}
if (CX == 0xffff) {
begin = getdword(dataptr);
length = getword(&dataptr[4]);
dataptr = (BYTE *) PTR_SEG_TO_LIN(getdword(&dataptr[6]));
} else {
begin = DX;
length = CX;
}
if (CX_reg(&context) == 0xffff)
{
begin = getdword(dataptr);
length = getword(&dataptr[4]);
dataptr = (BYTE *) PTR_SEG_TO_LIN(getdword(&dataptr[6]));
}
else
{
begin = DX_reg(&context);
length = CX_reg(&context);
}
dprintf_int(stdnimp,"int26: abs diskwrite, drive %d, sector %ld, "
"count %ld, buffer %d\n", AL, begin, length, (int) dataptr);
dprintf_int( stdnimp,"int26: abs diskwrite, drive %d, sector %ld, "
"count %ld, buffer %d\n",
AL_reg(&context), begin, length, (int) dataptr );
ResetCflag;
#undef context
RESET_CFLAG(&context);
}
......@@ -13,16 +13,14 @@
*
* Handler for int 2ah (network).
*/
void INT_Int2aHandler( struct sigcontext_struct sigcontext )
void INT_Int2aHandler( struct sigcontext_struct context )
{
#define context (&sigcontext)
switch(AH)
switch(AH_reg(&context))
{
case 0x00: /* NETWORK INSTALLATION CHECK */
break;
default:
INT_BARF( 0x2a );
INT_BARF( &context, 0x2a );
}
#undef context
}
......@@ -16,13 +16,12 @@ static void do_int2f_16(struct sigcontext_struct *context);
*
* Handler for int 2fh (multiplex).
*/
void INT_Int2fHandler( struct sigcontext_struct sigcontext )
void INT_Int2fHandler( struct sigcontext_struct context )
{
#define context (&sigcontext)
switch(AH)
switch(AH_reg(&context))
{
case 0x10:
AL = 0xff; /* share is installed */
AL_reg(&context) = 0xff; /* share is installed */
break;
case 0x15: /* mscdex */
......@@ -30,48 +29,47 @@ void INT_Int2fHandler( struct sigcontext_struct sigcontext )
break;
case 0x16:
do_int2f_16( context );
do_int2f_16( &context );
break;
default:
INT_BARF( 0x2f );
INT_BARF( &context, 0x2f );
}
#undef context
}
static void do_int2f_16(struct sigcontext_struct *context)
{
switch(AL)
switch(AL_reg(context))
{
case 0x00: /* Windows enhanced mode installation check */
AX = Options.enhanced ? WINVERSION : 0;
AX_reg(context) = Options.enhanced ? WINVERSION : 0;
break;
case 0x0a: /* Get Windows version and type */
AX = 0;
BX = (WINVERSION >> 8) | ((WINVERSION << 8) & 0xff00);
CX = Options.enhanced ? 3 : 2;
AX_reg(context) = 0;
BX_reg(context) = (WINVERSION >> 8) | ((WINVERSION << 8) & 0xff00);
CX_reg(context) = Options.enhanced ? 3 : 2;
break;
case 0x80: /* Release time-slice */
break; /* nothing to do */
case 0x86: /* DPMI detect mode */
AX = 0; /* Running under DPMI */
AX_reg(context) = 0; /* Running under DPMI */
break;
case 0x87: /* DPMI installation check */
AX = 0x0000; /* DPMI Installed */
BX = 0x0001; /* 32bits available */
CL = 0x03; /* processor 386 */
DX = 0x005a; /* DPMI major/minor 0.90 */
SI = 0; /* # of para. of DOS extended private data */
ES = 0; /* ES:DI is DPMI switch entry point */
DI = 0;
AX_reg(context) = 0x0000; /* DPMI Installed */
BX_reg(context) = 0x0001; /* 32bits available */
CL_reg(context) = 0x03; /* processor 386 */
DX_reg(context) = 0x005a; /* DPMI major/minor 0.90 */
SI_reg(context) = 0; /* # of para. of DOS extended private data */
ES_reg(context) = 0; /* ES:DI is DPMI switch entry point */
DI_reg(context) = 0;
break;
default:
INT_BARF( 0x2f );
INT_BARF( context, 0x2f );
}
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment