|
|
1.1 root 1: /*
2: MS-DOS Player for Win32 console
3:
4: Author : Takeda.Toshiya
5: Date : 2009.11.09-
6: */
7:
8: #ifndef _MSDOS_H_
9: #define _MSDOS_H_
10:
1.1.1.12 root 11: #ifndef _WIN32_WINNT
12: #define _WIN32_WINNT 0x501
13: #endif
1.1 root 14: #include <windows.h>
15: #include <winioctl.h>
16: #include <tchar.h>
1.1.1.13 root 17: #include <stddef.h>
1.1 root 18: #include <stdlib.h>
19: #include <stdio.h>
1.1.1.2 root 20: #include <assert.h>
1.1 root 21: #include <conio.h>
1.1.1.27 root 22: #include <locale.h>
1.1.1.2 root 23: #include <math.h>
1.1 root 24: #include <dos.h>
25: #include <fcntl.h>
26: #include <sys/types.h>
27: #include <sys/stat.h>
28: #include <io.h>
29: #include <sys/locking.h>
30: #include <mbctype.h>
31: #include <direct.h>
32: #include <errno.h>
1.1.1.9 root 33: #include <tlhelp32.h>
34: #include <psapi.h>
1.1.1.20 root 35: #include <setupapi.h>
1.1.1.27 root 36: #include <winsock.h>
1.1 root 37:
1.1.1.15 root 38: #ifdef _DEBUG
39: #define _CRTDBG_MAP_ALLOC
40: #include <crtdbg.h>
41: #define calloc(c, s) _calloc_dbg(c, s, _NORMAL_BLOCK, __FILE__, __LINE__)
42: #define malloc(s) _malloc_dbg(s, _NORMAL_BLOCK, __FILE__, __LINE__)
43: #define new new(_NORMAL_BLOCK, __FILE__, __LINE__)
44: #endif
45:
1.1.1.9 root 46: // variable scope of 'for' loop for Microsoft Visual C++ 6.0
47: #if defined(_MSC_VER) && (_MSC_VER == 1200)
1.1 root 48: #define for if(0);else for
49: #endif
1.1.1.9 root 50:
51: // disable warnings for Microsoft Visual C++ 2005 or later
1.1 root 52: #if defined(_MSC_VER) && (_MSC_VER >= 1400)
53: #pragma warning( disable : 4819 )
54: #pragma warning( disable : 4995 )
55: #pragma warning( disable : 4996 )
1.1.1.9 root 56: // for MAME i86/i386
57: #pragma warning( disable : 4018 )
58: #pragma warning( disable : 4065 )
59: #pragma warning( disable : 4146 )
60: #pragma warning( disable : 4244 )
61: #pragma warning( disable : 4267 )
62: #endif
63:
64: // endian
65: #if !defined(__LITTLE_ENDIAN__) && !defined(__BIG_ENDIAN__)
66: #if defined(__BYTE_ORDER) && (defined(__LITTLE_ENDIAN) || defined(__BIG_ENDIAN))
67: #if __BYTE_ORDER == __LITTLE_ENDIAN
68: #define __LITTLE_ENDIAN__
69: #elif __BYTE_ORDER == __BIG_ENDIAN
70: #define __BIG_ENDIAN__
71: #endif
72: #elif defined(WORDS_LITTLEENDIAN)
73: #define __LITTLE_ENDIAN__
74: #elif defined(WORDS_BIGENDIAN)
75: #define __BIG_ENDIAN__
76: #endif
77: #endif
78: #if !defined(__LITTLE_ENDIAN__) && !defined(__BIG_ENDIAN__)
79: // Microsoft Visual C++
80: #define __LITTLE_ENDIAN__
1.1 root 81: #endif
1.1.1.9 root 82:
1.1 root 83: // compat for mingw32 headers
84: #ifndef COMMON_LVB_UNDERSCORE
85: #define COMMON_LVB_UNDERSCORE 0x8000
86: #endif
87:
88: // type definition
89: #ifndef UINT8
90: typedef unsigned char UINT8;
91: #endif
92: #ifndef UINT16
93: typedef unsigned short UINT16;
94: #endif
95: #ifndef UINT32
96: typedef unsigned int UINT32;
97: #endif
1.1.1.27 root 98: #ifndef UINT64
99: typedef unsigned long long UINT64;
100: #endif
1.1 root 101: #ifndef INT8
102: typedef signed char INT8;
103: #endif
104: #ifndef INT16
105: typedef signed short INT16;
106: #endif
107: #ifndef INT32
108: typedef signed int INT32;
109: #endif
1.1.1.27 root 110: #ifndef INT64
111: typedef signed long long INT64;
112: #endif
1.1 root 113:
114: #pragma pack(1)
115: typedef union {
116: UINT32 dw;
117: struct {
1.1.1.9 root 118: #ifdef __BIG_ENDIAN__
119: UINT16 h, l;
120: #else
1.1 root 121: UINT16 l, h;
1.1.1.9 root 122: #endif
1.1 root 123: } w;
124: } PAIR32;
125: #pragma pack()
126:
1.1.1.24 root 127: // MAME i86/i386
128:
129: // src/emu/devcpu.h
130: // offsets and addresses are 32-bit (for now...)
131: typedef UINT32 offs_t;
132:
1.1 root 133: /* ----------------------------------------------------------------------------
134: FIFO buffer
135: ---------------------------------------------------------------------------- */
136:
137: class FIFO
138: {
139: private:
1.1.1.20 root 140: int size;
141: int *buf;
1.1.1.29! root 142: int cnt, rpt, wpt;
1.1 root 143: public:
1.1.1.20 root 144: FIFO(int s) {
145: size = s;
146: buf = (int *)malloc(size * sizeof(int));
1.1 root 147: cnt = rpt = wpt = 0;
148: }
1.1.1.20 root 149: void release()
150: {
1.1.1.29! root 151: if(buf != NULL) {
! 152: free(buf);
! 153: buf = NULL;
! 154: }
1.1.1.20 root 155: }
1.1.1.27 root 156: void clear()
157: {
158: cnt = rpt = wpt = 0;
159: }
1.1 root 160: void write(int val) {
1.1.1.20 root 161: if(cnt < size) {
1.1 root 162: buf[wpt++] = val;
1.1.1.20 root 163: if(wpt >= size) {
1.1 root 164: wpt = 0;
165: }
166: cnt++;
167: }
168: }
169: int read() {
170: int val = 0;
171: if(cnt) {
172: val = buf[rpt++];
1.1.1.20 root 173: if(rpt >= size) {
1.1 root 174: rpt = 0;
175: }
176: cnt--;
177: }
1.1.1.20 root 178: return(val);
1.1 root 179: }
180: int count() {
1.1.1.20 root 181: return(cnt);
182: }
183: int remain() {
184: return(size - cnt);
185: }
186: bool full()
187: {
188: return(cnt == size);
189: }
190: bool empty()
191: {
192: return(cnt == 0);
1.1 root 193: }
194: };
195:
196: /* ----------------------------------------------------------------------------
1.1.1.14 root 197: MAME i86/i386
198: ---------------------------------------------------------------------------- */
199:
200: #if defined(HAS_I86)
201: #define CPU_MODEL i8086
202: #elif defined(HAS_I186)
203: #define CPU_MODEL i80186
204: #elif defined(HAS_V30)
205: #define CPU_MODEL v30
206: #elif defined(HAS_I286)
207: #define CPU_MODEL i80286
208: #elif defined(HAS_I386)
209: #define CPU_MODEL i386
210: #else
211: // #if defined(HAS_I386SX)
212: // #define CPU_MODEL i386SX
213: // #else
214: #if defined(HAS_I486)
215: #define CPU_MODEL i486
216: #else
217: #if defined(HAS_PENTIUM)
218: #define CPU_MODEL pentium
219: #elif defined(HAS_MEDIAGX)
220: #define CPU_MODEL mediagx
221: #elif defined(HAS_PENTIUM_PRO)
222: #define CPU_MODEL pentium_pro
223: #elif defined(HAS_PENTIUM_MMX)
224: #define CPU_MODEL pentium_mmx
225: #elif defined(HAS_PENTIUM2)
226: #define CPU_MODEL pentium2
227: #elif defined(HAS_PENTIUM3)
228: #define CPU_MODEL pentium3
229: #elif defined(HAS_PENTIUM4)
230: #define CPU_MODEL pentium4
231: #endif
232: #define SUPPORT_RDTSC
233: #endif
234: #define SUPPORT_FPU
235: // #endif
236: #define HAS_I386
237: #endif
238:
239: /* ----------------------------------------------------------------------------
1.1.1.27 root 240: debugger
241: ---------------------------------------------------------------------------- */
242:
243: //#define USE_DEBUGGER
244:
245: #ifdef USE_DEBUGGER
246: #define MAX_BREAK_POINTS 8
247:
248: bool now_debugging = false;
249: bool now_going = false;
250: bool now_suspended = false;
251: bool force_suspend = false;
252:
253: typedef struct {
254: struct {
255: UINT32 addr;
256: UINT32 seg;
257: UINT32 ofs;
258: int status; // 0 = none, 1 = enabled, other = disabled
259: } table[MAX_BREAK_POINTS];
260: int hit;
261: } break_point_t;
262:
263: break_point_t break_point = {0};
264: break_point_t rd_break_point = {0};
265: break_point_t wr_break_point = {0};
266: break_point_t in_break_point = {0};
267: break_point_t out_break_point = {0};
268:
269: typedef struct {
270: struct {
271: int int_num;
272: UINT8 ah, ah_registered;
273: UINT8 al, al_registered;
274: int status; // 0 = none, 1 = enabled, other = disabled
275: } table[MAX_BREAK_POINTS];
276: int hit;
277: } int_break_point_t;
278:
279: int_break_point_t int_break_point = {0};
280:
281: FILE *fp_debugger = NULL;
282: FILE *fi_debugger = NULL;
283:
284: // these read/write interfaces do not check break points,
285: // debugger should use them not to hit any break point mistakely
286: UINT8 debugger_read_byte(offs_t byteaddress);
287: UINT16 debugger_read_word(offs_t byteaddress);
288: UINT32 debugger_read_dword(offs_t byteaddress);
289: void debugger_write_byte(offs_t byteaddress, UINT8 data);
290: void debugger_write_word(offs_t byteaddress, UINT16 data);
291: void debugger_write_dword(offs_t byteaddress, UINT32 data);
292: UINT8 debugger_read_io_byte(offs_t addr);
293: UINT16 debugger_read_io_word(offs_t addr);
294: UINT32 debugger_read_io_dword(offs_t addr);
295: void debugger_write_io_byte(offs_t addr, UINT8 val);
296: void debugger_write_io_word(offs_t addr, UINT16 val);
297: void debugger_write_io_dword(offs_t addr, UINT32 val);
298: #endif
299:
300: /* ----------------------------------------------------------------------------
1.1.1.29! root 301: service thread
! 302: ---------------------------------------------------------------------------- */
! 303:
! 304: #define USE_SERVICE_THREAD
! 305:
! 306: #ifdef USE_SERVICE_THREAD
! 307: CRITICAL_SECTION input_crit_sect;
! 308: CRITICAL_SECTION key_buf_crit_sect;
! 309: CRITICAL_SECTION putch_crit_sect;
! 310: bool in_service = false;
! 311: bool service_exit = false;
! 312:
! 313: void start_service_loop(LPTHREAD_START_ROUTINE lpStartAddress);
! 314: void finish_service_loop();
! 315: #endif
! 316:
! 317: /* ----------------------------------------------------------------------------
1.1.1.14 root 318: PC/AT hardware emulation
319: ---------------------------------------------------------------------------- */
320:
1.1.1.22 root 321: //#define SUPPORT_GRAPHIC_SCREEN
322:
1.1.1.14 root 323: void hardware_init();
324: void hardware_finish();
1.1.1.22 root 325: void hardware_release();
1.1.1.14 root 326: void hardware_run();
327: void hardware_update();
328:
329: // memory
330:
331: #if defined(HAS_I386)
1.1.1.27 root 332: #define ADDR_MASK 0xffffffff
333: #define MAX_MEM 0x2000000 /* 32MB */
1.1.1.14 root 334: #elif defined(HAS_I286)
1.1.1.27 root 335: #define ADDR_MASK 0xffffff
336: #define MAX_MEM 0x1000000 /* 16MB */
1.1.1.14 root 337: #else
1.1.1.27 root 338: #define ADDR_MASK 0xfffff
339: #define MAX_MEM 0x100000 /* 1MB */
1.1.1.14 root 340: #endif
1.1.1.27 root 341: UINT8 mem[MAX_MEM + 15];
1.1.1.14 root 342:
343: // ems
344:
345: #define MAX_EMS_HANDLES 16
346: #define MAX_EMS_PAGES 2048 /* 32MB */
347:
1.1.1.21 root 348: typedef struct {
1.1.1.14 root 349: char name[8];
350: UINT8* buffer;
351: int pages;
352: bool allocated;
1.1.1.21 root 353: } ems_handle_t;
1.1.1.14 root 354:
1.1.1.21 root 355: typedef struct {
1.1.1.14 root 356: UINT16 handle;
357: UINT16 page;
358: bool mapped;
1.1.1.21 root 359: } ems_page_t;
1.1.1.14 root 360:
1.1.1.25 root 361: ems_handle_t ems_handles[MAX_EMS_HANDLES + 1] = {0};
1.1.1.21 root 362: ems_page_t ems_pages[4];
1.1.1.14 root 363: int free_ems_pages;
364:
365: void ems_init();
366: void ems_finish();
1.1.1.22 root 367: void ems_release();
1.1.1.14 root 368: void ems_allocate_pages(int handle, int pages);
369: void ems_reallocate_pages(int handle, int pages);
370: void ems_release_pages(int handle);
371: void ems_map_page(int physical, int handle, int logical);
372: void ems_unmap_page(int physical);
373:
1.1.1.20 root 374: // dma
375:
376: typedef struct {
377: struct {
378: union {
379: UINT16 w;
380: struct {
381: #ifdef __BIG_ENDIAN__
382: UINT8 h, l;
383: #else
384: UINT8 l, h;
385: #endif
386: } b;
387: } areg, creg, bareg, bcreg;
388: UINT8 mode;
389: UINT8 pagereg;
390: UINT32 port;
391: } ch[4];
392:
393: bool low_high;
394: UINT8 cmd;
395: UINT8 req;
396: UINT8 mask;
397: UINT8 tc;
398: UINT16 tmp;
399: } dma_t;
400:
1.1.1.21 root 401: dma_t dma[2];
1.1.1.20 root 402:
403: void dma_init();
404: void dma_reset(int c);
405: void dma_write(int c, UINT32 addr, UINT8 data);
406: UINT8 dma_read(int c, UINT32 addr);
407: void dma_page_write(int c, int ch, UINT8 data);
408: UINT8 dma_page_read(int c, int ch);
409: void dma_run(int c, int ch);
410:
1.1.1.14 root 411: // pic
412:
413: typedef struct {
414: UINT8 imr, isr, irr, prio;
415: UINT8 icw1, icw2, icw3, icw4;
416: UINT8 ocw3;
417: UINT8 icw2_r, icw3_r, icw4_r;
418: } pic_t;
419:
420: pic_t pic[2];
421: int pic_req_chip, pic_req_level;
422: UINT8 pic_req_bit;
423:
424: void pic_init();
425: void pic_write(int c, UINT32 addr, UINT8 data);
426: UINT8 pic_read(int c, UINT32 addr);
427: void pic_req(int c, int level, int signal);
428: int pic_ack();
429: void pic_update();
430:
1.1.1.20 root 431: // pio
432:
433: typedef struct {
434: UINT8 data, stat, ctrl;
435: } pio_t;
436:
1.1.1.21 root 437: pio_t pio[2];
1.1.1.20 root 438:
439: void pio_init();
440: void pio_write(int c, UINT32 addr, UINT8 data);
441: UINT8 pio_read(int c, UINT32 addr);
442:
1.1.1.14 root 443: // pit
444:
445: #define PIT_ALWAYS_RUNNING
446:
447: typedef struct {
448: INT32 count;
449: UINT16 latch;
1.1.1.21 root 450: UINT16 prev_latch, next_latch;
1.1.1.14 root 451: UINT16 count_reg;
452: UINT8 ctrl_reg;
453: int count_latched;
454: int low_read, high_read;
455: int low_write, high_write;
456: int mode;
457: int status_latched;
458: UINT8 status;
459: // constant clock
460: UINT32 expired_time;
461: UINT32 prev_time;
1.1.1.17 root 462: UINT64 accum;
1.1.1.14 root 463: } pit_t;
464:
465: pit_t pit[3];
466: #ifndef PIT_ALWAYS_RUNNING
467: int pit_active;
468: #endif
469:
470: void pit_init();
471: void pit_write(int ch, UINT8 val);
472: UINT8 pit_read(int ch);
473: int pit_run(int ch, UINT32 cur_time);
474: void pit_latch_count(int ch);
475: int pit_get_expired_time(int ch);
476:
477: UINT8 system_port = 0;
478:
1.1.1.20 root 479: // sio
480:
481: #define SIO_BUFFER_SIZE 1024
482:
483: typedef struct {
484: int channel;
485:
486: FIFO *send_buffer;
487: FIFO *recv_buffer;
488:
489: union {
490: UINT16 w;
491: struct {
492: #ifdef __BIG_ENDIAN__
493: UINT8 h, l;
494: #else
495: UINT8 l, h;
496: #endif
497: } b;
498: } divisor;
499: UINT16 prev_divisor;
500: UINT8 line_ctrl, prev_line_ctrl;
501: UINT8 selector;
502:
503: UINT8 modem_ctrl;
1.1.1.21 root 504: bool set_brk, set_rts, set_dtr;
505: bool prev_set_brk;
506: // bool prev_set_rts, prev_set_dtr;
1.1.1.20 root 507:
508: UINT8 line_stat_buf, line_stat_err;
509: UINT8 modem_stat, prev_modem_stat;
510:
511: UINT8 irq_enable;
512: UINT8 irq_identify;
513:
514: UINT8 scratch;
515: } sio_t;
516:
517: typedef struct {
518: HANDLE hThread;
519: CRITICAL_SECTION csSendData;
520: CRITICAL_SECTION csRecvData;
521: CRITICAL_SECTION csLineCtrl;
522: CRITICAL_SECTION csLineStat;
523: CRITICAL_SECTION csModemCtrl;
524: CRITICAL_SECTION csModemStat;
525: } sio_mt_t;
526:
1.1.1.23 root 527: sio_t sio[4] = {0};
528: sio_mt_t sio_mt[4];
1.1.1.20 root 529:
530: void sio_init();
531: void sio_finish();
1.1.1.22 root 532: void sio_release();
1.1.1.20 root 533: void sio_write(int c, UINT32 addr, UINT8 data);
534: UINT8 sio_read(int c, UINT32 addr);
535: void sio_update(int c);
536: void sio_update_irq(int c);
537: DWORD WINAPI sio_thread(void *lpx);
538:
1.1.1.14 root 539: // cmos
540:
541: UINT8 cmos[128];
542: UINT8 cmos_addr;
543:
544: void cmos_init();
545: void cmos_write(int addr, UINT8 val);
546: UINT8 cmos_read(int addr);
547:
548: // kbd (a20)
549:
550: UINT8 kbd_data;
551: UINT8 kbd_status;
552: UINT8 kbd_command;
553:
554: void kbd_init();
555: UINT8 kbd_read_data();
556: void kbd_write_data(UINT8 val);
557: UINT8 kbd_read_status();
558: void kbd_write_command(UINT8 val);
559:
560: /* ----------------------------------------------------------------------------
1.1 root 561: MS-DOS virtual machine
562: ---------------------------------------------------------------------------- */
563:
1.1.1.24 root 564: #if defined(HAS_I386)
565: //#define SUPPORT_VCPI
566: #endif
1.1.1.23 root 567: #if defined(HAS_I286) || defined(HAS_I386)
568: #define SUPPORT_XMS
569: //#define SUPPORT_HMA
570: #endif
571:
1.1 root 572: #define VECTOR_TOP 0
573: #define VECTOR_SIZE 0x400
574: #define BIOS_TOP (VECTOR_TOP + VECTOR_SIZE)
575: #define BIOS_SIZE 0x100
576: #define WORK_TOP (BIOS_TOP + BIOS_SIZE)
1.1.1.14 root 577: #define WORK_SIZE 0x200
1.1.1.20 root 578: // IO.SYS 0070:0000
579: #define DEVICE_TOP (WORK_TOP + WORK_SIZE)
1.1.1.21 root 580: #define DEVICE_SIZE 0x100 /* 22 + 18 * 12 + 7 */
1.1.1.20 root 581: #define DOS_INFO_TOP (DEVICE_TOP + DEVICE_SIZE)
1.1 root 582: #define DOS_INFO_SIZE 0x100
1.1.1.26 root 583: //#define EXT_BIOS_TOP (DOS_INFO_TOP + DOS_INFO_SIZE)
584: //#define EXT_BIOS_SIZE 0x400
585: #ifdef EXT_BIOS_TOP
1.1.1.20 root 586: #define DPB_TOP (EXT_BIOS_TOP + EXT_BIOS_SIZE)
1.1.1.26 root 587: #else
588: #define DPB_TOP (DOS_INFO_TOP + DOS_INFO_SIZE)
589: #endif
1.1 root 590: #define DPB_SIZE 0x400
1.1.1.16 root 591: #define SFT_TOP (DPB_TOP + DPB_SIZE)
592: #define SFT_SIZE 0x4b0 /* 6 + 0x3b * 20 */
593: #define DISK_BUF_TOP (SFT_TOP + SFT_SIZE)
1.1.1.14 root 594: #define DISK_BUF_SIZE 0x20
595: #define CDS_TOP (DISK_BUF_TOP + DISK_BUF_SIZE)
1.1 root 596: #define CDS_SIZE 0x80
597: #define FCB_TABLE_TOP (CDS_TOP + CDS_SIZE)
598: #define FCB_TABLE_SIZE 0x10
1.1.1.26 root 599: #define SDA_TOP (FCB_TABLE_TOP + FCB_TABLE_SIZE)
1.1.1.18 root 600: #define SDA_SIZE 0xb0
1.1.1.13 root 601: // nls tables
1.1.1.18 root 602: #define UPPERTABLE_TOP (SDA_TOP + SDA_SIZE)
1.1.1.13 root 603: #define UPPERTABLE_SIZE 0x82
1.1.1.18 root 604: #define LOWERTABLE_TOP (UPPERTABLE_TOP + UPPERTABLE_SIZE)
605: #define LOWERTABLE_SIZE 0x82
606: #define FILENAME_UPPERTABLE_TOP (LOWERTABLE_TOP + LOWERTABLE_SIZE)
1.1.1.13 root 607: #define FILENAME_UPPERTABLE_SIZE 0x82
608: #define FILENAME_TERMINATOR_TOP (FILENAME_UPPERTABLE_TOP + FILENAME_UPPERTABLE_SIZE)
609: #define FILENAME_TERMINATOR_SIZE 0x20 /* requirement: 10 + 14(terminate chars) */
610: #define COLLATING_TABLE_TOP (FILENAME_TERMINATOR_TOP + FILENAME_TERMINATOR_SIZE)
611: #define COLLATING_TABLE_SIZE 0x102
612: #define DBCS_TOP (COLLATING_TABLE_TOP + COLLATING_TABLE_SIZE)
1.1 root 613: #define DBCS_TABLE (DBCS_TOP + 2)
614: #define DBCS_SIZE 0x10
1.1.1.13 root 615: #define MSDOS_SYSTEM_DATA_END (DBCS_TOP + DBCS_SIZE)
616: #define MEMORY_TOP ((MSDOS_SYSTEM_DATA_END + 15) & ~15U)
1.1.1.22 root 617: #ifdef SUPPORT_GRAPHIC_SCREEN
618: #define MEMORY_END 0xa0000
619: #define VGA_VRAM_TOP 0xa0000
620: #else
1.1.1.7 root 621: #define MEMORY_END 0xb8000
1.1.1.22 root 622: #endif
1.1.1.7 root 623: #define TEXT_VRAM_TOP 0xb8000
1.1.1.14 root 624: #define EMS_TOP 0xc0000
625: #define EMS_SIZE 0x10000
626: UINT32 UMB_TOP = EMS_TOP; // EMS is disabled
1.1.1.7 root 627: #define UMB_END 0xf8000
628: #define SHADOW_BUF_TOP 0xf8000
1.1.1.14 root 629: #define EMB_TOP 0x10fff0
630: #define EMB_END MAX_MEM
631:
632: UINT32 IRET_TOP = 0;
633: #define IRET_SIZE 0x100
634: UINT32 XMS_TOP = 0;
1.1.1.23 root 635: #define XMS_SIZE 0x20 /* 18 + 6 + 7 */
1.1 root 636:
637: //#define ENV_SIZE 0x800
638: #define ENV_SIZE 0x2000
639: #define PSP_SIZE 0x100
1.1.1.27 root 640: #define PSP_SYSTEM 0x0008
1.1 root 641:
642: #define MAX_FILES 128
643: #define MAX_PROCESS 16
1.1.1.12 root 644: #define MAX_DTAINFO 128
1.1.1.11 root 645: #define LFN_DTA_LADDR 0x10FFF0
1.1.1.12 root 646: #define FIND_MAGIC 0x46696e64
1.1 root 647:
1.1.1.16 root 648: #define DUP_STDIN 27
649: #define DUP_STDOUT 28
650: #define DUP_STDERR 29
651: #define DUP_STDAUX 30
652: #define DUP_STDPRN 31
1.1 root 653:
1.1.1.16 root 654: //#define MAP_AUX_DEVICE_TO_FILE
655: //#define MAP_PRN_DEVICE_TO_FILE
1.1 root 656:
657: #pragma pack(1)
658: typedef struct {
659: UINT8 mz;
660: UINT16 psp;
1.1.1.24 root 661: UINT16 paragraphs;
662: UINT8 reserved[3];
1.1.1.3 root 663: char prog_name[8];
1.1 root 664: } mcb_t;
665: #pragma pack()
666:
1.1.1.23 root 667: #ifdef SUPPORT_HMA
668: #pragma pack(1)
669: typedef struct {
670: UINT8 ms[2];
671: UINT16 owner;
672: UINT16 size;
673: UINT16 next;
674: } hma_mcb_t;
675: #pragma pack()
676: #endif
677:
1.1 root 678: #pragma pack(1)
679: typedef struct {
680: UINT16 env_seg;
681: PAIR32 cmd_line;
682: PAIR32 fcb1;
683: PAIR32 fcb2;
684: UINT16 sp;
685: UINT16 ss;
686: UINT16 ip;
687: UINT16 cs;
688: } param_block_t;
689: #pragma pack()
690:
691: #pragma pack(1)
692: typedef struct {
693: UINT8 len;
694: char cmd[127];
695: } cmd_line_t;
696: #pragma pack()
697:
698: #pragma pack(1)
699: typedef struct {
700: UINT8 exit[2];
701: UINT16 first_mcb;
702: UINT8 reserved_1;
703: UINT8 far_call;
704: PAIR32 cpm_entry;
705: PAIR32 int_22h;
706: PAIR32 int_23h;
707: PAIR32 int_24h;
708: UINT16 parent_psp;
709: UINT8 file_table[20];
710: UINT16 env_seg;
711: PAIR32 stack;
1.1.1.12 root 712: UINT16 file_table_size;
713: PAIR32 file_table_ptr;
714: UINT8 reserved_2[24];
1.1 root 715: UINT8 service[3];
716: UINT8 reserved_3[2];
717: UINT8 ex_fcb[7];
718: UINT8 fcb1[16];
719: UINT8 fcb2[20];
720: UINT8 buffer[128];
721: } psp_t;
722: #pragma pack()
723:
724: #pragma pack(1)
725: typedef struct {
726: UINT16 mz;
727: UINT16 extra_bytes;
728: UINT16 pages;
729: UINT16 relocations;
730: UINT16 header_size;
731: UINT16 min_alloc;
732: UINT16 max_alloc;
733: UINT16 init_ss;
734: UINT16 init_sp;
735: UINT16 check_sum;
736: UINT16 init_ip;
737: UINT16 init_cs;
738: UINT16 relocation_table;
739: UINT16 overlay;
740: } exe_header_t;
741: #pragma pack()
742:
743: #pragma pack(1)
744: typedef struct {
745: UINT8 flag;
746: UINT8 reserved[5];
747: UINT8 attribute;
748: } ext_fcb_t;
749: #pragma pack()
750:
751: #pragma pack(1)
752: typedef struct {
753: UINT8 drive;
754: UINT8 file_name[8 + 3];
755: UINT16 current_block;
756: UINT16 record_size;
757: UINT32 file_size;
758: UINT16 date;
759: UINT16 time;
1.1.1.12 root 760: union {
761: UINT8 reserved[8];
762: HANDLE handle;
763: };
1.1 root 764: UINT8 cur_record;
765: UINT32 rand_record;
766: } fcb_t;
767: #pragma pack()
768:
769: #pragma pack(1)
770: typedef struct {
771: UINT8 drive;
772: UINT8 file_name[8 + 3];
773: UINT8 attribute;
774: UINT8 nt_res;
775: UINT8 create_time_ms;
776: UINT16 creation_time;
777: UINT16 creation_date;
778: UINT16 last_access_date;
779: UINT16 cluster_hi;
780: UINT16 last_write_time;
781: UINT16 last_write_date;
782: UINT16 cluster_lo;
783: UINT32 file_size;
784: } find_fcb_t;
785: #pragma pack()
786:
787: #pragma pack(1)
788: typedef struct {
1.1.1.12 root 789: union {
790: UINT8 reserved[21];
791: struct {
792: UINT32 find_magic;
793: UINT32 dta_index;
794: };
795: };
1.1 root 796: UINT8 attrib;
797: UINT16 time;
798: UINT16 date;
799: UINT32 size;
800: char name[13];
801: } find_t;
802: #pragma pack()
803:
804: #pragma pack(1)
805: typedef struct {
806: UINT32 attrib;
807: PAIR32 ctime_lo;
808: PAIR32 ctime_hi;
809: PAIR32 atime_lo;
810: PAIR32 atime_hi;
811: PAIR32 mtime_lo;
812: PAIR32 mtime_hi;
813: UINT32 size_hi;
814: UINT32 size_lo;
815: UINT8 reserved[8];
816: char full_name[260];
817: char short_name[14];
818: } find_lfn_t;
819: #pragma pack()
820:
821: #pragma pack(1)
822: typedef struct {
823: UINT16 info_level;
824: UINT32 serial_number;
825: char volume_label[11];
826: char file_system[8];
827: } drive_info_t;
828: #pragma pack()
829:
830: #pragma pack(1)
831: typedef struct {
832: UINT16 size_of_structure;
833: UINT16 structure_version;
834: UINT32 sectors_per_cluster;
835: UINT32 bytes_per_sector;
836: UINT32 available_clusters_on_drive;
837: UINT32 total_clusters_on_drive;
838: UINT32 available_sectors_on_drive;
839: UINT32 total_sectors_on_drive;
840: UINT32 available_allocation_units;
841: UINT32 total_allocation_units;
842: UINT8 reserved[8];
843: } ext_space_info_t;
844: #pragma pack()
845:
846: #pragma pack(1)
847: typedef struct {
848: UINT8 drive_num;
849: UINT8 unit_num;
850: UINT16 bytes_per_sector;
851: UINT8 highest_sector_num;
852: UINT8 shift_count;
853: UINT16 reserved_sectors;
854: UINT8 fat_num;
855: UINT16 root_entries;
856: UINT16 first_data_sector;
857: UINT16 highest_cluster_num;
858: UINT16 sectors_per_fat;
859: UINT16 first_dir_sector;
860: UINT32 device_driver_header;
861: UINT8 media_type;
862: UINT8 drive_accessed;
863: UINT16 next_dpb_ofs;
864: UINT16 next_dpb_seg;
865: UINT16 first_free_cluster;
866: UINT16 free_clusters;
1.1.1.12 root 867: // extended
868: UINT16 fat_mirroring;
869: UINT16 info_sector;
870: UINT16 backup_boot_sector;
871: UINT32 first_cluster_sector;
872: UINT32 maximum_cluster_num;
873: UINT32 fat_sectors;
874: UINT32 root_cluster;
875: UINT32 free_search_cluster;
1.1 root 876: } dpb_t;
877: #pragma pack()
878:
879: #pragma pack(1)
880: typedef struct {
881: char path_name[67];
882: UINT16 drive_attrib;
883: UINT8 physical_drive_number;
884: } cds_t;
885: #pragma pack()
886:
887: #pragma pack(1)
888: typedef struct {
1.1.1.18 root 889: UINT8 reserved_1[3]; // -34
890: UINT8 switchar; // -31 current switch character
891: UINT8 malloc_strategy; // -30 current memory allocation strategy
892: UINT8 reserved_2[29]; // -29
893: // ----- from DOSBox -----
894: UINT8 crit_error_flag; // 0x00 Critical Error Flag
895: UINT8 indos_flag; // 0x01 InDOS flag (count of active INT 21 calls)
896: UINT8 drive_crit_error; // 0x02 Drive on which current critical error occurred or FFh
897: UINT8 locus_of_last_error; // 0x03 locus of last error
898: UINT16 extended_error_code; // 0x04 extended error code of last error
899: UINT8 suggested_action; // 0x06 suggested action for last error
900: UINT8 error_class; // 0x07 class of last error
901: PAIR32 last_error_pointer; // 0x08 ES:DI pointer for last error
902: PAIR32 current_dta; // 0x0C current DTA (Disk Transfer Address)
903: UINT16 current_psp; // 0x10 current PSP
904: UINT16 sp_int_23; // 0x12 stores SP across an INT 23
905: UINT16 return_code; // 0x14 return code from last process termination (zerod after reading with AH=4Dh)
906: UINT8 current_drive; // 0x16 current drive
907: UINT8 extended_break_flag; // 0x17 extended break flag
908: UINT8 fill[2]; // 0x18 flag: code page switching || flag: copy of previous byte in case of INT 24 Abort
909: } sda_t;
910: #pragma pack()
911:
912: #pragma pack(1)
913: typedef struct {
1.1.1.14 root 914: UINT8 reserved_0[4]; // -38
915: UINT16 magic_word; // -34 from DOSBox
916: UINT8 reserved_1[30]; // -32
1.1 root 917: UINT16 first_mcb; // -2
918: PAIR32 first_dpb; // +0
1.1.1.14 root 919: PAIR32 first_sft; // +4
1.1.1.20 root 920: PAIR32 clock_device; // +8
921: PAIR32 con_device; // +12
1.1.1.14 root 922: UINT16 max_sector_len; // +16
923: PAIR32 disk_buf_info; // +18 from DOSBox
1.1 root 924: PAIR32 cds; // +22
925: PAIR32 fcb_table; // +26
1.1.1.20 root 926: UINT8 reserved_2[3]; // +30
1.1 root 927: UINT8 last_drive; // +33
1.1.1.14 root 928: struct {
1.1.1.20 root 929: PAIR32 next_driver; // +34
1.1.1.14 root 930: UINT16 attributes; // +38
931: UINT16 strategy; // +40
932: UINT16 interrupt; // +42
933: char dev_name[8]; // +44
934: } nul_device;
1.1.1.20 root 935: UINT8 reserved_3[11]; // +52
1.1 root 936: UINT16 buffers_x; // +63
937: UINT16 buffers_y; // +65
938: UINT8 boot_drive; // +67
939: UINT8 i386_or_later; // +68
940: UINT16 ext_mem_size; // +69
1.1.1.14 root 941: PAIR32 disk_buf_heads; // +71 from DOSBox
1.1.1.20 root 942: UINT8 reserved_4[21]; // +75
1.1.1.5 root 943: UINT8 dos_flag; // +96
1.1.1.20 root 944: UINT8 reserved_5[2]; // +97
1.1.1.15 root 945: UINT8 umb_linked; // +99 from DOSBox
1.1.1.20 root 946: UINT8 reserved_6[2]; // +100
1.1.1.15 root 947: UINT16 first_umb_fcb; // +102 from DOSBox
948: UINT16 first_mcb_2; // +104 from DOSBox
1.1.1.21 root 949: UINT8 nul_device_routine[7];
1.1 root 950: } dos_info_t;
951: #pragma pack()
952:
1.1.1.14 root 953: #pragma pack(1)
954: typedef struct {
1.1.1.20 root 955: PAIR32 next_driver;
956: UINT16 attributes;
957: UINT16 strategy;
958: UINT16 interrupt;
959: char dev_name[8];
960: } device_t;
961: #pragma pack()
962:
963: #pragma pack(1)
964: typedef struct {
1.1.1.14 root 965: UINT16 date_format;
966: char currency_symbol[5];
967: char thou_sep[2];
968: char dec_sep[2];
969: char date_sep[2];
970: char time_sep[2];
971: char currency_format;
972: char currency_dec_digits;
973: char time_format;
974: PAIR32 case_map;
975: char list_sep[2];
976: char reserved[10];
977: } country_info_t;
978: #pragma pack()
979:
1.1 root 980: typedef struct {
981: char path[MAX_PATH];
982: int valid;
983: int id;
984: int atty;
985: int mode;
986: UINT16 info;
987: UINT16 psp;
988: } file_handler_t;
989:
990: static const struct {
991: int mode;
992: int in;
993: int out;
994: } file_mode[] = {
1.1.1.11 root 995: { _O_RDONLY | _O_BINARY, 1, 0 },
1.1 root 996: { _O_WRONLY | _O_BINARY, 0, 1 },
997: { _O_RDWR | _O_BINARY, 1, 1 },
998: };
999:
1000: typedef struct {
1001: UINT16 psp;
1002: char module_dir[MAX_PATH];
1.1.1.27 root 1003: #ifdef USE_DEBUGGER
1004: char module_path[MAX_PATH];
1005: #endif
1.1 root 1006: PAIR32 dta;
1007: UINT8 switchar;
1008: UINT8 verify;
1009: int max_files;
1010: char volume_label[MAX_PATH];
1011: bool parent_int_10h_feh_called;
1012: bool parent_int_10h_ffh_called;
1.1.1.12 root 1013: UINT16 parent_ds;
1.1.1.25 root 1014: UINT16 parent_es;
1.1.1.14 root 1015: struct {
1016: UINT16 handle;
1017: UINT16 page;
1018: bool mapped;
1019: } ems_pages[4];
1020: bool ems_pages_stored;
1.1.1.22 root 1021: bool called_by_int2eh;
1.1 root 1022: } process_t;
1023:
1.1.1.11 root 1024: typedef struct {
1025: UINT16 psp;
1026: UINT32 dta;
1.1.1.12 root 1027: UINT8 allowable_mask;
1028: UINT8 required_mask;
1.1.1.11 root 1029: HANDLE find_handle;
1030: } dtainfo_t;
1031:
1.1.1.24 root 1032: UINT8 dos_major_version = 7; // Windows 98 Second Edition
1033: UINT8 dos_minor_version = 10;
1034: UINT8 win_major_version = 4;
1035: UINT8 win_minor_version = 10;
1.1.1.8 root 1036:
1.1.1.7 root 1037: UINT16 first_mcb;
1.1 root 1038: UINT16 current_psp;
1039:
1040: int retval = 0;
1041: UINT16 error_code = 0;
1042:
1043: file_handler_t file_handler[MAX_FILES];
1044: UINT8 file_buffer[0x100000];
1045:
1046: process_t process[MAX_PROCESS];
1.1.1.11 root 1047: dtainfo_t dtalist[MAX_DTAINFO];
1.1 root 1048:
1.1.1.6 root 1049: UINT16 malloc_strategy = 0;
1050:
1.1.1.12 root 1051: char comspec_path[MAX_PATH] = "C:\\COMMAND.COM";
1052:
1.1 root 1053: void msdos_syscall(unsigned num);
1054: int msdos_init(int argc, char *argv[], char *envp[], int standard_env);
1055: void msdos_finish();
1056:
1057: // console
1058:
1.1.1.12 root 1059: #define SCR_BUF_WIDTH 256
1060: #define SCR_BUF_HEIGHT 128
1.1 root 1061:
1062: #define SET_RECT(rect, l, t, r, b) { \
1063: rect.Left = l; \
1064: rect.Top = t; \
1065: rect.Right = r; \
1066: rect.Bottom = b; \
1067: }
1068:
1.1.1.19 root 1069: DWORD dwConsoleMode = 0;
1070:
1.1.1.12 root 1071: CHAR_INFO scr_buf[SCR_BUF_WIDTH * SCR_BUF_HEIGHT];
1072: char scr_char[SCR_BUF_WIDTH * SCR_BUF_HEIGHT];
1073: WORD scr_attr[SCR_BUF_WIDTH * SCR_BUF_HEIGHT];
1.1 root 1074: COORD scr_buf_size;
1075: COORD scr_buf_pos;
1076: int scr_width, scr_height;
1.1.1.12 root 1077: int scr_top;
1.1.1.10 root 1078: bool restore_console_on_exit = false;
1.1 root 1079: bool cursor_moved;
1080:
1.1.1.22 root 1081: FIFO *key_buf_char = NULL;
1082: FIFO *key_buf_scan = NULL;
1.1.1.19 root 1083: bool key_changed = false;
1.1.1.4 root 1084: UINT32 key_code = 0;
1.1.1.27 root 1085: UINT32 key_recv = 0;
1.1 root 1086:
1.1.1.27 root 1087: UINT8 ctrl_break_checking = 0x00; // ???
1088: bool ctrl_break_detected = false;
1089: bool ctrl_break_pressed = false;
1.1.1.21 root 1090: bool ctrl_c_pressed = false;
1.1.1.27 root 1091: bool raise_int_1bh = false;
1.1.1.21 root 1092:
1.1 root 1093: int active_code_page;
1094: int system_code_page;
1.1.1.26 root 1095: int console_code_page;
1.1 root 1096:
1.1.1.12 root 1097: UINT32 text_vram_top_address;
1098: UINT32 text_vram_end_address;
1099: UINT32 shadow_buffer_top_address;
1100: UINT32 shadow_buffer_end_address;
1101: int vram_pages;
1.1 root 1102: bool int_10h_feh_called = false;
1103: bool int_10h_ffh_called = false;
1104:
1.1.1.28 root 1105: #define MAX_MOUSE_BUTTONS 2
1.1.1.19 root 1106:
1.1.1.21 root 1107: typedef struct {
1.1.1.28 root 1108: bool enabled; // from DOSBox
1109: int hidden;
1110: int old_hidden; // from DOSBox
1.1.1.19 root 1111: struct {
1112: int x, y;
1113: } position, prev_position, max_position, min_position, mickey;
1114: struct {
1115: bool status;
1116: int pressed_times;
1117: int released_times;
1118: struct {
1119: int x, y;
1120: } pressed_position;
1121: struct {
1122: int x, y;
1123: } released_position;
1124: } buttons[MAX_MOUSE_BUTTONS];
1125: int get_buttons()
1126: {
1127: int val = 0;
1128: for(int i = 0; i < MAX_MOUSE_BUTTONS; i++) {
1129: if(buttons[i].status) {
1130: val |= 1 << i;
1131: }
1132: }
1133: return(val);
1134: }
1135: UINT16 status;
1136: UINT16 status_irq;
1137: UINT16 call_mask;
1138: PAIR32 call_addr;
1139: // dummy
1140: UINT16 sensitivity[3];
1141: UINT16 display_page;
1142: UINT16 language;
1143: UINT16 hot_spot[2];
1.1.1.21 root 1144: } mouse_t;
1145:
1146: mouse_t mouse;
1.1.1.19 root 1147:
1148: UINT16 mouse_push_ax;
1149: UINT16 mouse_push_bx;
1150: UINT16 mouse_push_cx;
1151: UINT16 mouse_push_dx;
1152: UINT16 mouse_push_si;
1153: UINT16 mouse_push_di;
1154:
1.1.1.23 root 1155: // hma
1156:
1157: #ifdef SUPPORT_HMA
1158: bool is_hma_used_by_xms = false;
1159: bool is_hma_used_by_int_2fh = false;
1160: #endif
1161:
1162: // xms
1163:
1164: #ifdef SUPPORT_XMS
1.1.1.24 root 1165: typedef struct emb_handle_s {
1166: UINT32 handle; // 0=allocated
1167: offs_t address;
1.1.1.23 root 1168: int size_kb;
1169: int lock;
1.1.1.24 root 1170: struct emb_handle_s *prev;
1171: struct emb_handle_s *next;
1172: } emb_handle_t;
1.1.1.23 root 1173:
1.1.1.24 root 1174: emb_handle_t *emb_handle_top = NULL;
1.1.1.23 root 1175: int xms_a20_local_enb_count;
1176: UINT16 xms_dx_after_call_08h = 0;
1.1.1.26 root 1177:
1178: void msdos_xms_init();
1179: void msdos_xms_finish();
1180: void msdos_xms_release();
1181: emb_handle_t *msdos_xms_get_emb_handle(int handle);
1182: int msdos_xms_get_unused_emb_handle_id();
1183: int msdos_xms_get_unused_emb_handle_count();
1184: void msdos_xms_split_emb_handle(emb_handle_t *emb_handle, int size_kb);
1185: void msdos_xms_combine_emb_handles(emb_handle_t *emb_handle);
1186: emb_handle_t *msdos_xms_alloc_emb_handle(int size_kb);
1187: void msdos_xms_free_emb_handle(emb_handle_t *emb_handle);
1.1.1.23 root 1188: #endif
1189:
1.1 root 1190: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.