ReactOS  0.4.13-dev-1174-gdff75d7
emulator.c File Reference
#include "ntvdm.h"
#include <debug.h>
#include "emulator.h"
#include "memory.h"
#include "cpu/callback.h"
#include "cpu/cpu.h"
#include "cpu/bop.h"
#include <isvbop.h>
#include "int32.h"
#include "clock.h"
#include "bios/rom.h"
#include "hardware/cmos.h"
#include "hardware/disk.h"
#include "hardware/dma.h"
#include "hardware/keyboard.h"
#include "hardware/mouse.h"
#include "hardware/pic.h"
#include "hardware/pit.h"
#include "hardware/ppi.h"
#include "hardware/ps2.h"
#include "hardware/sound/speaker.h"
#include "hardware/video/svga.h"
#include "./console/video.h"
#include "vddsup.h"
#include "io.h"
Include dependency graph for emulator.c:

Go to the source code of this file.

Macros

#define NDEBUG
 
#define BOP_DEBUGGER   0x56
 
#define LINE_SIZE   75 + 2
 

Functions

UCHAR FASTCALL EmulatorIntAcknowledge (PFAST486_STATE State)
 
VOID FASTCALL EmulatorFpu (PFAST486_STATE State)
 
VOID EmulatorException (BYTE ExceptionNumber, LPWORD Stack)
 
VOID EmulatorInterruptSignal (VOID)
 
static VOID WINAPI EmulatorDebugBreakBop (LPWORD Stack)
 
static VOID WINAPI PitChan0Out (LPVOID Param, BOOLEAN State)
 
static VOID WINAPI PitChan1Out (LPVOID Param, BOOLEAN State)
 
static VOID WINAPI PitChan2Out (LPVOID Param, BOOLEAN State)
 
static DWORD WINAPI ConsoleEventThread (LPVOID Parameter)
 
static VOID PauseEventThread (VOID)
 
static VOID ResumeEventThread (VOID)
 
static VOID DumpMemoryRaw (HANDLE hFile)
 
static VOID DumpMemoryTxt (HANDLE hFile)
 
VOID DumpMemory (BOOLEAN TextFormat)
 
VOID MountFloppy (IN ULONG DiskNumber)
 
VOID EjectFloppy (IN ULONG DiskNumber)
 
VOID EmulatorPause (VOID)
 
VOID EmulatorResume (VOID)
 
VOID EmulatorTerminate (VOID)
 
BOOLEAN EmulatorInitialize (HANDLE ConsoleInput, HANDLE ConsoleOutput)
 
VOID EmulatorCleanup (VOID)
 
VOID WINAPI VDDSimulate16 (VOID)
 
VOID WINAPI VDDTerminateVDM (VOID)
 

Variables

LPVOID BaseAddress = NULL
 
BOOLEAN VdmRunning = TRUE
 
HANDLE VdmTaskEvent = NULL
 
static HANDLE InputThread = NULL
 
LPCWSTR ExceptionName []
 

Macro Definition Documentation

◆ BOP_DEBUGGER

#define BOP_DEBUGGER   0x56

Definition at line 67 of file emulator.c.

◆ LINE_SIZE

#define LINE_SIZE   75 + 2

◆ NDEBUG

#define NDEBUG

Definition at line 13 of file emulator.c.

Function Documentation

◆ ConsoleEventThread()

static DWORD WINAPI ConsoleEventThread ( LPVOID  Parameter)
static

Definition at line 189 of file emulator.c.

190 {
192  HANDLE WaitHandles[2];
193  DWORD WaitResult;
194 
195  /*
196  * For optimization purposes, Windows (and hence ReactOS, too, for
197  * compatibility reasons) uses a static buffer if no more than five
198  * input records are read. Otherwise a new buffer is used.
199  * The client-side expects that we know this behaviour.
200  * See consrv/coninput.c
201  *
202  * We exploit here this optimization by also using a buffer of 5 records.
203  */
204  INPUT_RECORD InputRecords[5];
205  ULONG NumRecords, i;
206 
207  WaitHandles[0] = VdmTaskEvent;
208  WaitHandles[1] = GetConsoleInputWaitHandle();
209 
210  while (VdmRunning)
211  {
212  /* Make sure the task event is signaled */
213  WaitResult = WaitForMultipleObjects(ARRAYSIZE(WaitHandles),
214  WaitHandles,
215  TRUE,
216  INFINITE);
217  switch (WaitResult)
218  {
219  case WAIT_OBJECT_0 + 0:
220  case WAIT_OBJECT_0 + 1:
221  break;
222  default:
223  return GetLastError();
224  }
225 
226  /* Wait for an input record */
228  InputRecords,
229  ARRAYSIZE(InputRecords),
230  &NumRecords,
232  {
233  DWORD LastError = GetLastError();
234  DPRINT1("Error reading console input (0x%p, %lu) - Error %lu\n", ConsoleInput, NumRecords, LastError);
235  return LastError;
236  }
237 
238  // ASSERT(NumRecords != 0);
239  if (NumRecords == 0)
240  {
241  DPRINT1("Got NumRecords == 0!\n");
242  continue;
243  }
244 
245  /* Dispatch the events */
246  for (i = 0; i < NumRecords; i++)
247  {
248  /* Check the event type */
249  switch (InputRecords[i].EventType)
250  {
251  /*
252  * Hardware events
253  */
254  case KEY_EVENT:
255  KeyboardEventHandler(&InputRecords[i].Event.KeyEvent);
256  break;
257 
258  case MOUSE_EVENT:
259  MouseEventHandler(&InputRecords[i].Event.MouseEvent);
260  break;
261 
263  ScreenEventHandler(&InputRecords[i].Event.WindowBufferSizeEvent);
264  break;
265 
266  /*
267  * Interface events
268  */
269  case MENU_EVENT:
270  MenuEventHandler(&InputRecords[i].Event.MenuEvent);
271  break;
272 
273  case FOCUS_EVENT:
274  FocusEventHandler(&InputRecords[i].Event.FocusEvent);
275  break;
276 
277  default:
278  DPRINT1("Unknown input event type 0x%04x\n", InputRecords[i].EventType);
279  break;
280  }
281  }
282 
283  /* Let the console subsystem queue some new events */
284  Sleep(10);
285  }
286 
287  return 0;
288 }
#define TRUE
Definition: types.h:120
BOOL WINAPI DECLSPEC_HOTPATCH ReadConsoleInputExW(IN HANDLE hConsoleInput, OUT PINPUT_RECORD lpBuffer, IN DWORD nLength, OUT LPDWORD lpNumberOfEventsRead, IN WORD wFlags)
Definition: readwrite.c:1298
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
#define WINDOW_BUFFER_SIZE_EVENT
Definition: wincon.h:124
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1059
HANDLE VdmTaskEvent
Definition: emulator.c:51
_In_ PVOID Parameter
Definition: ldrtypes.h:240
DWORD WINAPI WaitForMultipleObjects(IN DWORD nCount, IN CONST HANDLE *lpHandles, IN BOOL bWaitAll, IN DWORD dwMilliseconds)
Definition: synch.c:151
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
VOID MenuEventHandler(PMENU_EVENT_RECORD MenuEvent)
Definition: console.c:527
#define KEY_EVENT
Definition: wincon.h:122
HANDLE WINAPI GetConsoleInputWaitHandle(VOID)
Definition: console.c:683
#define FOCUS_EVENT
Definition: wincon.h:126
VOID KeyboardEventHandler(PKEY_EVENT_RECORD KeyEvent)
Definition: keyboard.c:167
VOID MouseEventHandler(PMOUSE_EVENT_RECORD MouseEvent)
Definition: mouse.c:427
#define WAIT_OBJECT_0
Definition: winbase.h:387
VOID FocusEventHandler(PFOCUS_EVENT_RECORD FocusEvent)
Definition: console.c:600
#define MOUSE_EVENT
Definition: wincon.h:123
unsigned long DWORD
Definition: ntddk_ex.h:95
PVOID HANDLE
Definition: typedefs.h:71
#define MENU_EVENT
Definition: wincon.h:125
#define CONSOLE_READ_CONTINUE
Definition: wincon.h:117
#define DPRINT1
Definition: precomp.h:8
unsigned int ULONG
Definition: retypes.h:1
_In_ ACCESS_MASK _In_opt_ POBJECT_ATTRIBUTES _In_ EVENT_TYPE EventType
Definition: exfuncs.h:165
BOOLEAN VdmRunning
Definition: emulator.c:49
#define INFINITE
Definition: serial.h:102
VOID ScreenEventHandler(PWINDOW_BUFFER_SIZE_RECORD ScreenEvent)
Definition: video.c:448

Referenced by EmulatorInitialize().

◆ DumpMemory()

VOID DumpMemory ( BOOLEAN  TextFormat)

Definition at line 369 of file emulator.c.

370 {
371  static ULONG DumpNumber = 0;
372 
373  HANDLE hFile;
375 
376  /* Build a suitable file name */
378  L"memdump%lu.%s",
379  DumpNumber,
380  TextFormat ? L"txt" : L"dat");
381  ++DumpNumber;
382 
383  DPRINT1("Creating memory dump file '%S'...\n", FileName);
384 
385  /* Always create the dump file */
388  0,
389  NULL,
392  NULL);
393 
395  {
396  DPRINT1("Error when creating '%S' for memory dumping, GetLastError() = %u\n",
398  return;
399  }
400 
401  /* Dump the VM memory in the chosen format */
402  if (TextFormat)
404  else
406 
407  /* Close the file */
409 
410  DPRINT1("Memory dump done\n");
411 }
static VOID DumpMemoryRaw(HANDLE hFile)
Definition: emulator.c:304
#define CloseHandle
Definition: compat.h:398
#define INVALID_HANDLE_VALUE
Definition: compat.h:391
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1059
static VOID DumpMemoryTxt(HANDLE hFile)
Definition: emulator.c:317
#define GENERIC_WRITE
Definition: nt_native.h:90
int _snwprintf(wchar_t *buffer, size_t count, const wchar_t *format,...)
smooth NULL
Definition: ftsmooth.c:416
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define MAX_PATH
Definition: compat.h:26
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:126
static const WCHAR L[]
Definition: oid.c:1250
_In_ HANDLE hFile
Definition: mswsock.h:90
#define CREATE_ALWAYS
Definition: disk.h:72
#define DPRINT1
Definition: precomp.h:8
#define CreateFileW
Definition: compat.h:400
unsigned int ULONG
Definition: retypes.h:1

Referenced by MenuEventHandler().

◆ DumpMemoryRaw()

static VOID DumpMemoryRaw ( HANDLE  hFile)
static

Definition at line 304 of file emulator.c.

305 {
306  PVOID Buffer;
307  DWORD Size;
308 
309  /* Dump the VM memory */
314 }
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
DWORD WINAPI DECLSPEC_HOTPATCH SetFilePointer(HANDLE hFile, LONG lDistanceToMove, PLONG lpDistanceToMoveHigh, DWORD dwMoveMethod)
Definition: fileinfo.c:204
#define MAX_ADDRESS
#define REAL_TO_PHYS(ptr)
Definition: emulator.h:33
smooth NULL
Definition: ftsmooth.c:416
Definition: bufpool.h:45
unsigned long DWORD
Definition: ntddk_ex.h:95
IN PVOID IN PVOID IN USHORT IN USHORT Size
Definition: pci.h:359
_In_ HANDLE hFile
Definition: mswsock.h:90
#define FILE_BEGIN
Definition: winbase.h:112
#define ULONG_PTR
Definition: config.h:101
IN BOOLEAN OUT PSTR Buffer
Definition: progress.h:34

Referenced by DumpMemory().

◆ DumpMemoryTxt()

static VOID DumpMemoryTxt ( HANDLE  hFile)
static

Definition at line 317 of file emulator.c.

318 {
319 #define LINE_SIZE 75 + 2
320  ULONG i;
321  PBYTE Ptr1, Ptr2;
322  CHAR LineBuffer[LINE_SIZE];
323  PCHAR Line;
324  DWORD LineSize;
325 
326  /* Dump the VM memory */
328  Ptr1 = Ptr2 = REAL_TO_PHYS(NULL);
329  while (MAX_ADDRESS - (ULONG_PTR)PHYS_TO_REAL(Ptr1) > 0)
330  {
331  Ptr1 = Ptr2;
332  Line = LineBuffer;
333 
334  /* Print the address */
335  Line += snprintf(Line, LINE_SIZE + LineBuffer - Line, "%08Ix ", (ULONG_PTR)PHYS_TO_REAL(Ptr1));
336 
337  /* Print up to 16 bytes... */
338 
339  /* ... in hexadecimal form first... */
340  i = 0;
341  while (i++ <= 0x0F && (MAX_ADDRESS - (ULONG_PTR)PHYS_TO_REAL(Ptr1) > 0))
342  {
343  Line += snprintf(Line, LINE_SIZE + LineBuffer - Line, " %02x", *Ptr1);
344  ++Ptr1;
345  }
346 
347  /* ... align with spaces if needed... */
348  RtlFillMemory(Line, (0x0F + 2 - i) * 3 + 2, ' ');
349  Line += (0x0F + 2 - i) * 3 + 2;
350 
351  /* ... then in character form. */
352  i = 0;
353  while (i++ <= 0x0F && (MAX_ADDRESS - (ULONG_PTR)PHYS_TO_REAL(Ptr2) > 0))
354  {
355  *Line++ = ((*Ptr2 >= 0x20 && *Ptr2 <= 0x7E) || (*Ptr2 >= 0x80 && *Ptr2 < 0xFF) ? *Ptr2 : '.');
356  ++Ptr2;
357  }
358 
359  /* Newline */
360  *Line++ = '\r';
361  *Line++ = '\n';
362 
363  /* Finally write the line to the file */
364  LineSize = Line - LineBuffer;
365  WriteFile(hFile, LineBuffer, LineSize, &LineSize, NULL);
366  }
367 }
signed char * PCHAR
Definition: retypes.h:7
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
char CHAR
Definition: xmlstorage.h:175
#define snprintf
Definition: wintirpc.h:48
#define PHYS_TO_REAL(ptr)
Definition: emulator.h:34
#define LINE_SIZE
DWORD WINAPI DECLSPEC_HOTPATCH SetFilePointer(HANDLE hFile, LONG lDistanceToMove, PLONG lpDistanceToMoveHigh, DWORD dwMoveMethod)
Definition: fileinfo.c:204
uint32_t ULONG_PTR
Definition: typedefs.h:63
#define MAX_ADDRESS
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define REAL_TO_PHYS(ptr)
Definition: emulator.h:33
smooth NULL
Definition: ftsmooth.c:416
unsigned long DWORD
Definition: ntddk_ex.h:95
Definition: ncftp.h:79
_In_ HANDLE hFile
Definition: mswsock.h:90
#define FILE_BEGIN
Definition: winbase.h:112
unsigned int ULONG
Definition: retypes.h:1
#define RtlFillMemory(Dest, Length, Fill)
Definition: winternl.h:593
BYTE * PBYTE
Definition: pedump.c:66
struct Line Line

Referenced by DumpMemory().

◆ EjectFloppy()

VOID EjectFloppy ( IN ULONG  DiskNumber)

Definition at line 467 of file emulator.c.

468 {
470 
471  /* Unmount the disk */
472  if (!UnmountDisk(FLOPPY_DISK, DiskNumber))
473  DisplayMessage(L"An error happened when ejecting disk %d", DiskNumber);
474 
475  /* Free the old string */
476  if (GlobalSettings.FloppyDisks[DiskNumber].Buffer)
477  {
479  RtlInitEmptyUnicodeString(&GlobalSettings.FloppyDisks[DiskNumber], NULL, 0);
480  }
481 
482  /* Refresh the menu state */
484 }
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
smooth NULL
Definition: ftsmooth.c:416
UNICODE_STRING FloppyDisks[2]
Definition: ntvdm.h:78
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static const WCHAR L[]
Definition: oid.c:1250
BOOLEAN UnmountDisk(IN DISK_TYPE DiskType, IN ULONG DiskNumber)
Definition: disk.c:602
void DisplayMessage(BOOL bConsole, BOOL bSilent, LPCTSTR lpMessage, LPCTSTR lpTitle, UINT uType)
Definition: regsvr32.c:239
NTVDM_SETTINGS GlobalSettings
Definition: ntvdm.c:25
VOID UpdateVdmMenuDisks(VOID)
Definition: console.c:146

Referenced by MenuEventHandler().

◆ EmulatorCleanup()

VOID EmulatorCleanup ( VOID  )

Definition at line 639 of file emulator.c.

640 {
641  DiskCtrlCleanup();
642 
643  VgaCleanup();
644 
645  /* Close the input thread handle */
647  InputThread = NULL;
648 
649  /* Close the task event */
651  VdmTaskEvent = NULL;
652 
653  PS2Cleanup();
654 
655  SpeakerCleanup();
656  CmosCleanup();
657  // PitCleanup();
658  // PicCleanup();
659 
660  // DmaCleanup();
661 
662  CpuCleanup();
663  MemCleanup();
664 }
#define CloseHandle
Definition: compat.h:398
HANDLE VdmTaskEvent
Definition: emulator.c:51
VOID CmosCleanup(VOID)
Definition: cmos.c:519
smooth NULL
Definition: ftsmooth.c:416
VOID PS2Cleanup(VOID)
Definition: ps2.c:546
VOID VgaCleanup(VOID)
Definition: svga.c:2145
static HANDLE InputThread
Definition: emulator.c:52
VOID MemCleanup(VOID)
Definition: memory.c:780
VOID SpeakerCleanup(VOID)
Definition: speaker.c:294
VOID DiskCtrlCleanup(VOID)
Definition: disk.c:637
VOID CpuCleanup(VOID)
Definition: cpu.c:243

Referenced by EmulatorInitialize(), and VdmShutdown().

◆ EmulatorDebugBreakBop()

static VOID WINAPI EmulatorDebugBreakBop ( LPWORD  Stack)
static

Definition at line 126 of file emulator.c.

127 {
128  DPRINT1("NTVDM: BOP_DEBUGGER\n");
129  DebugBreak();
130 }
void WINAPI DebugBreak(void)
#define DPRINT1
Definition: precomp.h:8

Referenced by EmulatorInitialize().

◆ EmulatorException()

VOID EmulatorException ( BYTE  ExceptionNumber,
LPWORD  Stack 
)

Definition at line 85 of file emulator.c.

86 {
87  WORD CodeSegment, InstructionPointer;
88  PBYTE Opcode;
89 
90  ASSERT(ExceptionNumber < 8);
91 
92  /* Get the CS:IP */
93  InstructionPointer = Stack[STACK_IP];
94  CodeSegment = Stack[STACK_CS];
95  Opcode = (PBYTE)SEG_OFF_TO_PTR(CodeSegment, InstructionPointer);
96 
97  /* Display a message to the user */
98  DisplayMessage(L"Exception: %s occurred at %04X:%04X\n"
99  L"Opcode: %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X",
100  ExceptionName[ExceptionNumber],
101  CodeSegment,
102  InstructionPointer,
103  Opcode[0],
104  Opcode[1],
105  Opcode[2],
106  Opcode[3],
107  Opcode[4],
108  Opcode[5],
109  Opcode[6],
110  Opcode[7],
111  Opcode[8],
112  Opcode[9]);
113 
115 
116  /* Stop the VDM */
118 }
_In_ PVOID _In_ ULONG Opcode
Definition: hubbusif.h:330
VOID NTAPI Fast486DumpState(PFAST486_STATE State)
Definition: debug.c:127
#define SEG_OFF_TO_PTR(seg, off)
Definition: emulator.h:28
unsigned short WORD
Definition: ntddk_ex.h:93
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
LPCWSTR ExceptionName[]
Definition: emulator.c:54
static const WCHAR L[]
Definition: oid.c:1250
#define STACK_CS
Definition: int32.h:34
VOID EmulatorTerminate(VOID)
Definition: emulator.c:503
FAST486_STATE EmulatorContext
Definition: cpu.c:39
void DisplayMessage(BOOL bConsole, BOOL bSilent, LPCTSTR lpMessage, LPCTSTR lpTitle, UINT uType)
Definition: regsvr32.c:239
#define STACK_IP
Definition: int32.h:33
BYTE * PBYTE
Definition: pedump.c:66

Referenced by BiosException().

◆ EmulatorFpu()

VOID FASTCALL EmulatorFpu ( PFAST486_STATE  State)

Definition at line 79 of file emulator.c.

80 {
81  /* The FPU is wired to IRQ 13 */
83 }
VOID PicInterruptRequest(BYTE Number)
Definition: pic.c:192

Referenced by CpuInitialize().

◆ EmulatorInitialize()

BOOLEAN EmulatorInitialize ( HANDLE  ConsoleInput,
HANDLE  ConsoleOutput 
)

Definition at line 510 of file emulator.c.

511 {
512  USHORT i;
513 
514  /* Initialize memory */
515  if (!MemInitialize())
516  {
517  wprintf(L"Memory initialization failed.\n");
518  return FALSE;
519  }
520 
521  /* Initialize I/O ports */
522  /* Initialize RAM */
523 
524  /* Initialize the CPU */
525 
526  /* Initialize the internal clock */
527  if (!ClockInitialize())
528  {
529  wprintf(L"FATAL: Failed to initialize the clock\n");
530  EmulatorCleanup();
531  return FALSE;
532  }
533 
534  /* Initialize the CPU */
535  CpuInitialize();
536 
537  /* Initialize DMA */
538  DmaInitialize();
539 
540  /* Initialize PIC, PIT, CMOS, PC Speaker and PS/2 */
541  PicInitialize();
542 
543  PitInitialize();
547 
548  CmosInitialize();
550  PpiInitialize();
551 
552  PS2Initialize();
553 
554  /* Initialize the keyboard and mouse and connect them to their PS/2 ports */
555  KeyboardInit(0);
556  MouseInit(1);
557 
558  /**************** ATTACH INPUT WITH CONSOLE *****************/
559  /* Create the task event */
562 
563  /* Start the input thread */
565  if (InputThread == NULL)
566  {
567  wprintf(L"FATAL: Failed to create the console input thread.\n");
568  EmulatorCleanup();
569  return FALSE;
570  }
572  /************************************************************/
573 
574  /* Initialize the VGA */
576  {
577  wprintf(L"FATAL: Failed to initialize VGA support.\n");
578  EmulatorCleanup();
579  return FALSE;
580  }
581 
582  /* Initialize the disk controller */
583  if (!DiskCtrlInitialize())
584  {
585  wprintf(L"FATAL: Failed to completely initialize the disk controller.\n");
586  EmulatorCleanup();
587  return FALSE;
588  }
589 
590  /* Mount the available floppy disks */
591  for (i = 0; i < ARRAYSIZE(GlobalSettings.FloppyDisks); ++i)
592  {
593  if (GlobalSettings.FloppyDisks[i].Length != 0 &&
596  {
598  {
599  DPRINT1("Failed to mount floppy disk file '%wZ'.\n", &GlobalSettings.FloppyDisks[i]);
601  RtlInitEmptyUnicodeString(&GlobalSettings.FloppyDisks[i], NULL, 0);
602  }
603  }
604  }
605 
606  /*
607  * Mount the available hard disks. Contrary to floppies, failing
608  * mounting a hard disk is considered as an unrecoverable error.
609  */
610  for (i = 0; i < ARRAYSIZE(GlobalSettings.HardDisks); ++i)
611  {
612  if (GlobalSettings.HardDisks[i].Length != 0 &&
614  *GlobalSettings.HardDisks[i].Buffer != L'\0')
615  {
617  {
618  wprintf(L"FATAL: Failed to mount hard disk file '%wZ'.\n", &GlobalSettings.HardDisks[i]);
619  EmulatorCleanup();
620  return FALSE;
621  }
622  }
623  }
624 
625  /* Refresh the menu state */
627 
628  /* Initialize the software callback system and register the emulator BOPs */
629  InitializeInt32();
631  // RegisterBop(BOP_UNSIMULATE, CpuUnsimulateBop);
632 
633  /* Initialize VDD support */
635 
636  return TRUE;
637 }
VOID PpiInitialize(VOID)
Definition: ppi.c:78
static VOID WINAPI PitChan1Out(LPVOID Param, BOOLEAN State)
Definition: emulator.c:142
#define TRUE
Definition: types.h:120
static VOID ResumeEventThread(VOID)
Definition: emulator.c:295
static DWORD WINAPI ConsoleEventThread(LPVOID Parameter)
Definition: emulator.c:189
VOID RegisterBop(BYTE BopCode, EMULATOR_BOP_PROC BopHandler)
Definition: bop.c:29
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define BOP_DEBUGGER
Definition: emulator.c:67
VOID PicInitialize(VOID)
Definition: pic.c:295
BOOLEAN DiskCtrlInitialize(VOID)
Definition: disk.c:632
HANDLE VdmTaskEvent
Definition: emulator.c:51
#define wprintf(...)
Definition: whoami.c:18
HANDLE WINAPI DECLSPEC_HOTPATCH CreateEventW(IN LPSECURITY_ATTRIBUTES lpEventAttributes OPTIONAL, IN BOOL bManualReset, IN BOOL bInitialState, IN LPCWSTR lpName OPTIONAL)
Definition: synch.c:651
VOID PitSetOutFunction(BYTE Channel, LPVOID Param, PIT_OUT_FUNCTION OutFunction)
Definition: pit.c:476
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:136
smooth NULL
Definition: ftsmooth.c:416
VOID VDDSupInitialize(VOID)
Definition: vddsup.c:507
UNICODE_STRING FloppyDisks[2]
Definition: ntvdm.h:78
UNICODE_STRING HardDisks[4]
Definition: ntvdm.h:79
BOOLEAN KeyboardInit(BYTE PS2Connector)
Definition: keyboard.c:188
static VOID WINAPI PitChan2Out(LPVOID Param, BOOLEAN State)
Definition: emulator.c:160
static VOID WINAPI PitChan0Out(LPVOID Param, BOOLEAN State)
Definition: emulator.c:132
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
static HANDLE InputThread
Definition: emulator.c:52
VOID EmulatorCleanup(VOID)
Definition: emulator.c:639
BOOLEAN CpuInitialize(VOID)
Definition: cpu.c:216
static const WCHAR L[]
Definition: oid.c:1250
VOID DmaInitialize(VOID)
Definition: dma.c:549
BOOLEAN ClockInitialize(VOID)
Definition: clock.c:219
BOOLEAN MemInitialize(VOID)
Definition: memory.c:720
BOOLEAN VgaInitialize(HANDLE TextHandle)
Definition: svga.c:2100
BOOLEAN MountDisk(IN DISK_TYPE DiskType, IN ULONG DiskNumber, IN PCWSTR FileName, IN BOOLEAN ReadOnly)
Definition: disk.c:500
unsigned short USHORT
Definition: pedump.c:61
#define DPRINT1
Definition: precomp.h:8
VOID InitializeInt32(VOID)
Definition: int32.c:194
static HANDLE ConsoleOutput
Definition: console.c:17
VOID PitInitialize(VOID)
Definition: pit.c:503
VOID SpeakerInitialize(VOID)
Definition: speaker.c:259
BOOLEAN PS2Initialize(VOID)
Definition: ps2.c:520
BOOLEAN MouseInit(BYTE PS2Connector)
Definition: mouse.c:464
VOID CmosInitialize(VOID)
Definition: cmos.c:441
Definition: disk.h:45
NTVDM_SETTINGS GlobalSettings
Definition: ntvdm.c:25
VOID UpdateVdmMenuDisks(VOID)
Definition: console.c:146
static VOID WINAPI EmulatorDebugBreakBop(LPWORD Stack)
Definition: emulator.c:126

Referenced by wmain().

◆ EmulatorIntAcknowledge()

UCHAR FASTCALL EmulatorIntAcknowledge ( PFAST486_STATE  State)

Definition at line 71 of file emulator.c.

72 {
74 
75  /* Get the interrupt number from the PIC */
76  return PicGetInterrupt();
77 }
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:323
BYTE PicGetInterrupt(VOID)
Definition: pic.c:244

Referenced by CpuInitialize().

◆ EmulatorInterruptSignal()

VOID EmulatorInterruptSignal ( VOID  )

Definition at line 120 of file emulator.c.

121 {
122  /* Call the Fast486 API */
124 }
VOID NTAPI Fast486InterruptSignal(PFAST486_STATE State)
Definition: fast486.c:205
FAST486_STATE EmulatorContext
Definition: cpu.c:39

Referenced by PicInterruptRequest(), and PicWriteCommand().

◆ EmulatorPause()

VOID EmulatorPause ( VOID  )

Definition at line 487 of file emulator.c.

488 {
489  /* Pause the VDM */
493 }
static VOID PauseEventThread(VOID)
Definition: emulator.c:290
VOID VgaRefreshDisplay(VOID)
Definition: svga.c:1783
VOID VDDBlockUserHook(VOID)
Definition: vddsup.c:479

Referenced by CmdSetExitCode(), CmdStartProcess(), and DosStartProcess32().

◆ EmulatorResume()

VOID EmulatorResume ( VOID  )

Definition at line 495 of file emulator.c.

496 {
497  /* Resume the VDM */
501 }
static VOID ResumeEventThread(VOID)
Definition: emulator.c:295
VOID VgaRefreshDisplay(VOID)
Definition: svga.c:1783
VOID VDDResumeUserHook(VOID)
Definition: vddsup.c:492

Referenced by CmdSetExitCode(), CmdStartProcess(), DosStart(), and DosStartProcess32().

◆ EmulatorTerminate()

◆ MountFloppy()

VOID MountFloppy ( IN ULONG  DiskNumber)

Definition at line 413 of file emulator.c.

414 {
415 // FIXME: This should be present in PSDK commdlg.h
416 //
417 // FlagsEx Values
418 #if (_WIN32_WINNT >= 0x0500)
419 #define OFN_EX_NOPLACESBAR 0x00000001
420 #endif // (_WIN32_WINNT >= 0x0500)
421 
424  WCHAR szFile[MAX_PATH] = L"";
425 
427 
428  RtlZeroMemory(&ofn, sizeof(ofn));
429  ofn.lStructSize = sizeof(ofn);
431  ofn.lpstrTitle = L"Select a virtual floppy image";
433 // ofn.FlagsEx = OFN_EX_NOPLACESBAR;
434  ofn.lpstrFilter = L"Virtual floppy images (*.vfd;*.img;*.ima;*.dsk)\0*.vfd;*.img;*.ima;*.dsk\0All files (*.*)\0*.*\0\0";
435  ofn.lpstrDefExt = L"vfd";
436  ofn.nFilterIndex = 0;
437  ofn.lpstrFile = szFile;
438  ofn.nMaxFile = ARRAYSIZE(szFile);
439 
440  if (!GetOpenFileNameW(&ofn))
441  {
442  DPRINT1("CommDlgExtendedError = %d\n", CommDlgExtendedError());
443  return;
444  }
445 
446  /* Free the old string */
447  if (GlobalSettings.FloppyDisks[DiskNumber].Buffer)
449 
450  /* Reinitialize the string */
452  ASSERT(Success);
453 
454  /* Mount the disk */
455  if (!MountDisk(FLOPPY_DISK, DiskNumber, GlobalSettings.FloppyDisks[DiskNumber].Buffer, !!(ofn.Flags & OFN_READONLY)))
456  {
457  DisplayMessage(L"An error happened when mounting disk %d", DiskNumber);
459  RtlInitEmptyUnicodeString(&GlobalSettings.FloppyDisks[DiskNumber], NULL, 0);
460  return;
461  }
462 
463  /* Refresh the menu state */
465 }
#define OFN_FILEMUSTEXIST
Definition: commdlg.h:106
#define OFN_EXPLORER
Definition: commdlg.h:104
#define OFN_LONGNAMES
Definition: commdlg.h:108
HWND hConsoleWnd
Definition: console.c:20
HWND hwndOwner
Definition: commdlg.h:330
OPENFILENAME ofn
Definition: main.cpp:37
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
LPCSTR lpstrDefExt
Definition: commdlg.h:345
DWORD nMaxFile
Definition: commdlg.h:337
BOOL WINAPI GetOpenFileNameW(OPENFILENAMEW *ofn)
Definition: filedlg.c:4564
unsigned char BOOLEAN
smooth NULL
Definition: ftsmooth.c:416
#define OFN_PATHMUSTEXIST
Definition: commdlg.h:117
UNICODE_STRING FloppyDisks[2]
Definition: ntvdm.h:78
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define MAX_PATH
Definition: compat.h:26
DWORD lStructSize
Definition: commdlg.h:329
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
#define OFN_READONLY
Definition: commdlg.h:118
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
NTSYSAPI BOOLEAN NTAPI RtlCreateUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
static const WCHAR L[]
Definition: oid.c:1250
BOOLEAN MountDisk(IN DISK_TYPE DiskType, IN ULONG DiskNumber, IN PCWSTR FileName, IN BOOLEAN ReadOnly)
Definition: disk.c:500
LPSTR lpstrFile
Definition: commdlg.h:336
LPCSTR lpstrFilter
Definition: commdlg.h:332
#define DPRINT1
Definition: precomp.h:8
LPCSTR lpstrTitle
Definition: commdlg.h:341
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:261
DWORD nFilterIndex
Definition: commdlg.h:335
void DisplayMessage(BOOL bConsole, BOOL bSilent, LPCTSTR lpMessage, LPCTSTR lpTitle, UINT uType)
Definition: regsvr32.c:239
#define OFN_ENABLESIZING
Definition: commdlg.h:101
DWORD WINAPI CommDlgExtendedError(void)
Definition: cdlg32.c:139
NTVDM_SETTINGS GlobalSettings
Definition: ntvdm.c:25
VOID UpdateVdmMenuDisks(VOID)
Definition: console.c:146
DWORD Flags
Definition: commdlg.h:342

Referenced by MenuEventHandler().

◆ PauseEventThread()

static VOID PauseEventThread ( VOID  )
static

Definition at line 290 of file emulator.c.

291 {
293 }
HANDLE VdmTaskEvent
Definition: emulator.c:51
BOOL WINAPI DECLSPEC_HOTPATCH ResetEvent(IN HANDLE hEvent)
Definition: synch.c:714

Referenced by EmulatorPause().

◆ PitChan0Out()

static VOID WINAPI PitChan0Out ( LPVOID  Param,
BOOLEAN  State 
)
static

Definition at line 132 of file emulator.c.

133 {
134  if (State)
135  {
136  DPRINT("PicInterruptRequest\n");
137  PicInterruptRequest(0); // Raise IRQ 0
138  }
139  // else < Lower IRQ 0 >
140 }
void DPRINT(...)
Definition: polytest.cpp:61
VOID PicInterruptRequest(BYTE Number)
Definition: pic.c:192

Referenced by EmulatorInitialize().

◆ PitChan1Out()

static VOID WINAPI PitChan1Out ( LPVOID  Param,
BOOLEAN  State 
)
static

Definition at line 142 of file emulator.c.

143 {
144 #if 0
145  if (State)
146  {
147  /* Set bit 4 of Port 61h */
148  Port61hState |= 1 << 4;
149  }
150  else
151  {
152  /* Clear bit 4 of Port 61h */
153  Port61hState &= ~(1 << 4);
154  }
155 #else
156  Port61hState = (Port61hState & 0xEF) | (State << 4);
157 #endif
158 }
BYTE Port61hState
Definition: ppi.c:31

Referenced by EmulatorInitialize().

◆ PitChan2Out()

static VOID WINAPI PitChan2Out ( LPVOID  Param,
BOOLEAN  State 
)
static

Definition at line 160 of file emulator.c.

161 {
162  BYTE OldPort61hState = Port61hState;
163 
164 #if 0
165  if (State)
166  {
167  /* Set bit 5 of Port 61h */
168  Port61hState |= 1 << 5;
169  }
170  else
171  {
172  /* Clear bit 5 of Port 61h */
173  Port61hState &= ~(1 << 5);
174  }
175 #else
176  Port61hState = (Port61hState & 0xDF) | (State << 5);
177 #endif
178 
179  if ((OldPort61hState ^ Port61hState) & 0x20)
180  {
181  DPRINT("PitChan2Out -- Port61hState changed\n");
183  }
184 }
BYTE Port61hState
Definition: ppi.c:31
VOID SpeakerChange(UCHAR Port61hValue)
Definition: speaker.c:195
void DPRINT(...)
Definition: polytest.cpp:61
unsigned char BYTE
Definition: mem.h:68

Referenced by EmulatorInitialize().

◆ ResumeEventThread()

static VOID ResumeEventThread ( VOID  )
static

Definition at line 295 of file emulator.c.

296 {
298 }
BOOL WINAPI DECLSPEC_HOTPATCH SetEvent(IN HANDLE hEvent)
Definition: synch.c:733
HANDLE VdmTaskEvent
Definition: emulator.c:51

Referenced by EmulatorInitialize(), and EmulatorResume().

◆ VDDSimulate16()

VOID WINAPI VDDSimulate16 ( VOID  )

Definition at line 670 of file emulator.c.

671 {
672  CpuSimulate();
673 }
VOID CpuSimulate(VOID)
Definition: cpu.c:167

◆ VDDTerminateVDM()

VOID WINAPI VDDTerminateVDM ( VOID  )

Definition at line 677 of file emulator.c.

678 {
679  /* Stop the VDM */
681 }
VOID EmulatorTerminate(VOID)
Definition: emulator.c:503

Referenced by RegisterVDD().

Variable Documentation

◆ BaseAddress

LPVOID BaseAddress = NULL

Definition at line 48 of file emulator.c.

◆ ExceptionName

LPCWSTR ExceptionName[]
Initial value:
=
{
L"Division By Zero",
L"Debug",
L"Unexpected Error",
L"Breakpoint",
L"Integer Overflow",
L"Bound Range Exceeded",
L"Invalid Opcode",
L"FPU Not Available"
}
static const WCHAR L[]
Definition: oid.c:1250

Definition at line 54 of file emulator.c.

Referenced by EmulatorException().

◆ InputThread

HANDLE InputThread = NULL
static

Definition at line 52 of file emulator.c.

Referenced by EmulatorCleanup(), and EmulatorInitialize().

◆ VdmRunning

BOOLEAN VdmRunning = TRUE

Definition at line 49 of file emulator.c.

Referenced by ClockUpdate(), ConsoleEventThread(), CpuSimulate(), and EmulatorTerminate().

◆ VdmTaskEvent