Add PS/2 Model 50 emulation.
This commit also adds basic MCA emulation. This commit also adds emulation of the PS/2 Type 1 DMA controller.
This commit is contained in:
parent
2ad4ebc253
commit
9c1d8e5022
29 changed files with 911 additions and 95 deletions
|
|
@ -325,6 +325,11 @@ opcodestart:
|
|||
// pclog("NMI\n");
|
||||
x86_int(2);
|
||||
nmi_enable = 0;
|
||||
if (nmi_auto_clear)
|
||||
{
|
||||
nmi_auto_clear = 0;
|
||||
nmi = 0;
|
||||
}
|
||||
}
|
||||
else if ((flags&I_FLAG) && pic_intpending)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@
|
|||
|
||||
int xt_cpu_multi;
|
||||
int nmi = 0;
|
||||
int nmi_auto_clear = 0;
|
||||
|
||||
int nextcyc=0;
|
||||
int cycdiff;
|
||||
|
|
|
|||
|
|
@ -21,8 +21,8 @@ codegen.c codegen_ops.c codegen_timing_486.c codegen_timing_686.c codegen_timing
|
|||
dac.c device.c disc.c disc_fdi.c disc_img.c disc_sector.c dma.c fdc.c fdc37c665.c fdd.c fdi2raw.c gameport.c \
|
||||
hdd.c headland.c i430lx.c i430fx.c i430vx.c ide.c intel.c intel_flash.c io.c jim.c joystick_ch_flightstick_pro.c joystick_standard.c joystick_sw_pad.c \
|
||||
joystick_tm_fcs.c keyboard.c keyboard_amstrad.c keyboard_at.c keyboard_olim24.c keyboard_pcjr.c keyboard_xt.c \
|
||||
lpt.c mcr.c mem.c mfm_at.c mfm_xebec.c model.c mouse.c mouse_ps2.c mouse_serial.c neat.c nmi.c nvr.c olivetti_m24.c \
|
||||
opti495.c pc.c pci.c pic.c piix.c pit.c ppi.c ps1.c ps2.c rom.c rtc.c scat.c serial.c sis496.c sound.c \
|
||||
lpt.c mca.c mcr.c mem.c mfm_at.c mfm_xebec.c model.c mouse.c mouse_ps2.c mouse_serial.c neat.c nmi.c nvr.c olivetti_m24.c \
|
||||
opti495.c pc.c pci.c pic.c piix.c pit.c ppi.c ps1.c ps2.c ps2_mca.c rom.c rtc.c scat.c serial.c sis496.c sound.c \
|
||||
sound_ad1848.c sound_adlib.c sound_adlibgold.c sound_cms.c sound_emu8k.c sound_gus.c \
|
||||
sound_mpu401_uart.c sound_opl.c sound_pas16.c sound_ps1.c sound_pssj.c sound_sb.c sound_sb_dsp.c sound_sn76489.c \
|
||||
sound_speaker.c sound_ssi2001.c sound_wss.c sound_ym7128.c soundopenal.c tandy_eeprom.c tandy_rom.c thread-pthread.c \
|
||||
|
|
|
|||
|
|
@ -10,8 +10,8 @@ codegen.o codegen_ops.o codegen_timing_486.o codegen_timing_686.o codegen_timing
|
|||
dac.o device.o disc.o disc_fdi.o disc_img.o disc_sector.o dma.o fdc.o fdc37c665.o fdd.o fdi2raw.o gameport.o \
|
||||
hdd.o headland.o i430lx.o i430fx.o i430vx.o ide.o intel.o intel_flash.o io.o jim.o joystick_ch_flightstick_pro.o joystick_standard.o joystick_sw_pad.o \
|
||||
joystick_tm_fcs.o keyboard.o keyboard_amstrad.o keyboard_at.o keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o \
|
||||
lpt.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o \
|
||||
opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o rom.o rtc.o scat.o serial.o sis496.o sound.o \
|
||||
lpt.o mca.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o \
|
||||
opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o ps2_mca.o rom.o rtc.o scat.o serial.o sis496.o sound.o \
|
||||
sound_ad1848.o sound_adlib.o sound_adlibgold.o sound_cms.o sound_emu8k.o sound_gus.o \
|
||||
sound_mpu401_uart.o sound_opl.o sound_pas16.o sound_ps1.o sound_pssj.o sound_sb.o sound_sb_dsp.o sound_sn76489.o \
|
||||
sound_speaker.o sound_ssi2001.o sound_wss.o sound_ym7128.o soundopenal.o tandy_eeprom.o tandy_rom.o thread-pthread.o \
|
||||
|
|
|
|||
|
|
@ -9,8 +9,8 @@ codegen.o codegen_ops.o codegen_timing_486.o codegen_timing_686.o codegen_timing
|
|||
dac.o device.o disc.o disc_fdi.o disc_img.o disc_sector.o dma.o fdc.o fdc37c665.o fdd.o fdi2raw.o gameport.o \
|
||||
hdd.o headland.o i430lx.o i430fx.o i430vx.o ide.o intel.o intel_flash.o io.o jim.o joystick_ch_flightstick_pro.o joystick_standard.o joystick_sw_pad.o \
|
||||
joystick_tm_fcs.o keyboard.o keyboard_amstrad.o keyboard_at.o keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o \
|
||||
lpt.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o \
|
||||
opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o rom.o rtc.o scat.o serial.o sis496.o sound.o \
|
||||
lpt.o mca.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o \
|
||||
opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o ps2_mca.o rom.o rtc.o scat.o serial.o sis496.o sound.o \
|
||||
sound_ad1848.o sound_adlib.o sound_adlibgold.o sound_cms.o sound_emu8k.o sound_gus.o \
|
||||
sound_mpu401_uart.o sound_opl.o sound_pas16.o sound_ps1.o sound_pssj.o sound_sb.o sound_sb_dsp.o sound_sn76489.o \
|
||||
sound_speaker.o sound_ssi2001.o sound_wss.o sound_ym7128.o soundopenal.o tandy_eeprom.o tandy_rom.o thread-pthread.o \
|
||||
|
|
|
|||
|
|
@ -7,8 +7,8 @@ OBJ = 386.o 386_dynarec.o 386_dynarec_ops.o 808x.o acer386sx.o ali1429.o amstrad
|
|||
codegen.o codegen_ops.o codegen_timing_486.o codegen_timing_686.o codegen_timing_pentium.o codegen_timing_winchip.o codegen_x86.o compaq.o config.o cpu.o dac.o \
|
||||
device.o disc.o disc_fdi.o disc_img.o disc_sector.o dma.o fdc.o fdc37c665.o fdd.o fdi2raw.o gameport.o hdd.o headland.o i430lx.o i430fx.o \
|
||||
i430vx.o ide.o intel.o intel_flash.o io.o jim.o joystick_ch_flightstick_pro.o joystick_standard.o joystick_sw_pad.o joystick_tm_fcs.o keyboard.o keyboard_amstrad.o keyboard_at.o \
|
||||
keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o lpt.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o \
|
||||
mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o rom.o rtc.o \
|
||||
keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o lpt.o mca.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o \
|
||||
mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o ps2_mca.o rom.o rtc.o \
|
||||
scat.o serial.o sis496.o sound.o sound_ad1848.o sound_adlib.o sound_adlibgold.o sound_cms.o sound_dbopl.o \
|
||||
sound_emu8k.o sound_gus.o sound_mpu401_uart.o sound_opl.o sound_pas16.o sound_ps1.o sound_pssj.o sound_resid.o \
|
||||
sound_sb.o sound_sb_dsp.o sound_sn76489.o sound_speaker.o sound_ssi2001.o sound_wss.o \
|
||||
|
|
|
|||
|
|
@ -7,8 +7,8 @@ OBJ = 386.o 386_dynarec.o 386_dynarec_ops.o 808x.o acer386sx.o ali1429.o amstrad
|
|||
codegen.o codegen_ops.o codegen_timing_486.o codegen_timing_686.o codegen_timing_pentium.o codegen_timing_winchip.o codegen_x86-64.o compaq.o config.o cpu.o dac.o \
|
||||
device.o disc.o disc_fdi.o disc_img.o disc_sector.o dma.o fdc.o fdc37c665.o fdd.o fdi2raw.o gameport.o hdd.o headland.o i430lx.o i430fx.o \
|
||||
i430vx.o ide.o intel.o intel_flash.o io.o jim.o joystick_ch_flightstick_pro.o joystick_standard.o joystick_sw_pad.o joystick_tm_fcs.o keyboard.o keyboard_amstrad.o keyboard_at.o \
|
||||
keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o lpt.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o \
|
||||
mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o rom.o rtc.o \
|
||||
keyboard_olim24.o keyboard_pcjr.o keyboard_xt.o lpt.o mca.o mcr.o mem.o mfm_at.o mfm_xebec.o model.o mouse.o mouse_ps2.o \
|
||||
mouse_serial.o neat.o nmi.o nvr.o olivetti_m24.o opti495.o pc.o pci.o pic.o piix.o pit.o ppi.o ps1.o ps2.o ps2_mca.o rom.o rtc.o \
|
||||
scat.o serial.o sis496.o sound.o sound_ad1848.o sound_adlib.o sound_adlibgold.o sound_cms.o sound_dbopl.o \
|
||||
sound_emu8k.o sound_gus.o sound_mpu401_uart.o sound_opl.o sound_pas16.o sound_ps1.o sound_pssj.o sound_resid.o \
|
||||
sound_sb.o sound_sb_dsp.o sound_sn76489.o sound_speaker.o sound_ssi2001.o sound_wss.o sound_ym7128.o \
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@
|
|||
#include "cpu.h"
|
||||
#include "fdd.h"
|
||||
#include "gameport.h"
|
||||
#include "hdd.h"
|
||||
#include "model.h"
|
||||
#include "mouse.h"
|
||||
#include "sound.h"
|
||||
|
|
@ -21,6 +22,12 @@ typedef struct allegro_list_t
|
|||
int num;
|
||||
} allegro_list_t;
|
||||
|
||||
typedef struct allegro_list_str_t
|
||||
{
|
||||
char name[256];
|
||||
char *internal_name;
|
||||
} allegro_list_str_t;
|
||||
|
||||
static allegro_list_t model_list[ROM_MAX+1];
|
||||
static allegro_list_t video_list[GFX_MAX+1];
|
||||
static allegro_list_t sound_list[GFX_MAX+1];
|
||||
|
|
@ -28,6 +35,7 @@ static allegro_list_t cpumanu_list[4];
|
|||
static allegro_list_t cpu_list[32];
|
||||
static allegro_list_t joystick_list[32];
|
||||
static allegro_list_t mouse_list[32];
|
||||
static allegro_list_str_t hdd_list[32];
|
||||
|
||||
static char mem_size_str[10], mem_size_units[3];
|
||||
|
||||
|
|
@ -168,6 +176,22 @@ static char *list_proc_cpu(int index, int *list_size)
|
|||
return cpu_list[index].name;
|
||||
}
|
||||
|
||||
static char *list_proc_hdd(int index, int *list_size)
|
||||
{
|
||||
if (index < 0)
|
||||
{
|
||||
int c = 0;
|
||||
|
||||
while (hdd_list[c].internal_name)
|
||||
c++;
|
||||
|
||||
*list_size = c;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return hdd_list[index].name;
|
||||
}
|
||||
|
||||
static char *list_proc_fdd(int index, int *list_size)
|
||||
{
|
||||
if (index < 0)
|
||||
|
|
@ -252,10 +276,10 @@ static int list_proc(int msg, DIALOG *d, int c);
|
|||
|
||||
static DIALOG configure_dialog[] =
|
||||
{
|
||||
{d_shadow_box_proc, 0, 0, 568,352,0,0xffffff,0,0, 0,0,0,0,0}, // 0
|
||||
{d_shadow_box_proc, 0, 0, 568,372,0,0xffffff,0,0, 0,0,0,0,0}, // 0
|
||||
|
||||
{d_button_proc, 226, 328, 50, 16, 0, 0xffffff, 0, D_EXIT, 0, 0, "OK", 0, 0}, // 1
|
||||
{d_button_proc, 296, 328, 50, 16, 0, 0xffffff, 0, D_EXIT, 0, 0, "Cancel", 0, 0}, // 2
|
||||
{d_button_proc, 226, 348, 50, 16, 0, 0xffffff, 0, D_EXIT, 0, 0, "OK", 0, 0}, // 1
|
||||
{d_button_proc, 296, 348, 50, 16, 0, 0xffffff, 0, D_EXIT, 0, 0, "Cancel", 0, 0}, // 2
|
||||
|
||||
{list_proc, 70*2, 12, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_model, 0, 0},
|
||||
|
||||
|
|
@ -266,14 +290,14 @@ static DIALOG configure_dialog[] =
|
|||
{d_list_proc, 70*2, 132, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_vidspeed, 0, 0}, //7
|
||||
{list_proc, 70*2, 152, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_sound, 0, 0}, //8
|
||||
|
||||
{d_edit_proc, 70*2, 256, 32, 14, 0, 0xffffff, 0, 0, 3, 0, mem_size_str, 0, 0},
|
||||
{d_edit_proc, 70*2, 276, 32, 14, 0, 0xffffff, 0, 0, 3, 0, mem_size_str, 0, 0},
|
||||
|
||||
{d_text_proc, 98*2, 256, 40, 10, 0, 0xffffff, 0, 0, 0, 0, mem_size_units, 0, 0},
|
||||
{d_text_proc, 98*2, 276, 40, 10, 0, 0xffffff, 0, 0, 0, 0, mem_size_units, 0, 0},
|
||||
|
||||
{d_check_proc, 14*2, 272, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "CMS / Game Blaster", 0, 0},
|
||||
{d_check_proc, 14*2, 288, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Gravis Ultrasound", 0, 0},
|
||||
{d_check_proc, 14*2, 304, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Innovation SSI-2001", 0, 0},
|
||||
{d_check_proc, 14*2, 316, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Voodoo Graphics", 0, 0}, //14
|
||||
{d_check_proc, 14*2, 292, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "CMS / Game Blaster", 0, 0},
|
||||
{d_check_proc, 14*2, 308, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Gravis Ultrasound", 0, 0},
|
||||
{d_check_proc, 14*2, 324, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Innovation SSI-2001", 0, 0},
|
||||
{d_check_proc, 14*2, 336, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Voodoo Graphics", 0, 0}, //14
|
||||
|
||||
{d_text_proc, 16*2, 16, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Machine :", 0, 0},
|
||||
{d_text_proc, 16*2, 36, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Video :", 0, 0},
|
||||
|
|
@ -281,33 +305,98 @@ static DIALOG configure_dialog[] =
|
|||
{d_text_proc, 16*2, 76, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "CPU :", 0, 0},
|
||||
{d_text_proc, 16*2, 136, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Video speed :", 0, 0},
|
||||
{d_text_proc, 16*2, 156, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Soundcard :", 0, 0},
|
||||
{d_text_proc, 16*2, 256, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Memory :", 0, 0},
|
||||
{d_text_proc, 16*2, 276, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Memory :", 0, 0},
|
||||
|
||||
{d_check_proc, 14*2, 92, 118*2, 10, 0, 0xffffff, 0, 0, 0, 0, "Dynamic Recompiler", 0, 0},
|
||||
|
||||
{d_text_proc, 16*2, 176, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Drive A: :", 0, 0},
|
||||
{d_text_proc, 16*2, 196, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Drive B: :", 0, 0},
|
||||
{d_list_proc, 70*2, 172, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_fdd, 0, 0}, //25
|
||||
{d_list_proc, 70*2, 192, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_fdd, 0, 0},
|
||||
{d_text_proc, 16*2, 196, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Drive A: :", 0, 0},
|
||||
{d_text_proc, 16*2, 216, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Drive B: :", 0, 0},
|
||||
{d_list_proc, 70*2, 192, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_fdd, 0, 0}, //25
|
||||
{d_list_proc, 70*2, 212, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_fdd, 0, 0},
|
||||
|
||||
{video_config_proc, 452, 36, 100, 14, 0, 0xffffff, 0, D_EXIT, 0, 0, "Configure...", 0, 0}, //27
|
||||
{sound_config_proc, 452, 156, 100, 14, 0, 0xffffff, 0, D_EXIT, 0, 0, "Configure...", 0, 0},
|
||||
{voodoo_config_proc, 452, 316, 100, 14, 0, 0xffffff, 0, D_EXIT, 0, 0, "Configure...", 0, 0},
|
||||
{voodoo_config_proc, 452, 336, 100, 14, 0, 0xffffff, 0, D_EXIT, 0, 0, "Configure...", 0, 0},
|
||||
|
||||
{d_text_proc, 16*2, 216, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Joystick :", 0, 0},
|
||||
{d_list_proc, 70*2, 212, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_joystick, 0, 0}, //31
|
||||
{d_text_proc, 16*2, 236, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Joystick :", 0, 0},
|
||||
{d_list_proc, 70*2, 232, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_joystick, 0, 0}, //31
|
||||
|
||||
{d_text_proc, 16*2, 236, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Mouse :", 0, 0},
|
||||
{d_list_proc, 70*2, 232, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_mouse, 0, 0}, //33
|
||||
{d_text_proc, 16*2, 256, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Mouse :", 0, 0},
|
||||
{d_list_proc, 70*2, 252, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_mouse, 0, 0}, //33
|
||||
|
||||
{model_config_proc, 452, 12, 100, 14, 0, 0xffffff, 0, D_EXIT, 0, 0, "Configure...", 0, 0},
|
||||
|
||||
{d_text_proc, 16*2, 116, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "Waitstates :", 0, 0},
|
||||
{d_list_proc, 70*2, 112, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_ws, 0, 0}, //36
|
||||
|
||||
{d_text_proc, 16*2, 176, 40, 10, 0, 0xffffff, 0, 0, 0, 0, "HDD :", 0, 0},
|
||||
{d_list_proc, 70*2, 172, 152*2, 20, 0, 0xffffff, 0, 0, 0, 0, list_proc_hdd, 0, 0}, //38
|
||||
|
||||
{0,0,0,0,0,0,0,0,0,0,0,NULL,NULL,NULL}
|
||||
};
|
||||
|
||||
static void update_hdd_list(int model, int use_selected_hdd)
|
||||
{
|
||||
memset(hdd_list, 0, sizeof(hdd_list));
|
||||
|
||||
if (models[model].flags & MODEL_HAS_IDE)
|
||||
{
|
||||
strcpy(hdd_list[0].name, "Internal IDE");
|
||||
strcpy(hdd_list[0].internal_name, "internal_ide");
|
||||
}
|
||||
else
|
||||
{
|
||||
int c = 0, d = 0;
|
||||
char old_name[16];
|
||||
|
||||
if (use_selected_hdd)
|
||||
{
|
||||
c = configure_dialog[38].d1;
|
||||
|
||||
if (c != -1 && hdd_list[c].internal_name)
|
||||
strncpy(old_name, hdd_list[c].internal_name, sizeof(old_name)-1);
|
||||
else
|
||||
strcpy(old_name, "none");
|
||||
}
|
||||
else
|
||||
strncpy(old_name, hdd_controller_name, sizeof(old_name)-1);
|
||||
|
||||
configure_dialog[38].d1 = 0;
|
||||
pclog("HDD list %i\n", model);
|
||||
c = 0;
|
||||
while (1)
|
||||
{
|
||||
char *s = hdd_controller_get_name(c);
|
||||
|
||||
if (s[0] == 0)
|
||||
break;
|
||||
|
||||
if ((((hdd_controller_get_flags(c) & DEVICE_AT) && !(models[model].flags & MODEL_AT)) ||
|
||||
(hdd_controller_get_flags(c) & DEVICE_MCA) != (models[model].flags & MODEL_MCA)) && c)
|
||||
{
|
||||
pclog("Skip %i 1 %s\n", c, s);
|
||||
c++;
|
||||
continue;
|
||||
}
|
||||
if (!hdd_controller_available(c))
|
||||
{
|
||||
pclog("Skip %i 2 %s\n", c, s);
|
||||
c++;
|
||||
continue;
|
||||
}
|
||||
|
||||
strcpy(hdd_list[d].name, s);
|
||||
hdd_list[d].internal_name = hdd_controller_get_internal_name(c);
|
||||
|
||||
if (!strcmp(old_name, hdd_list[d].internal_name))
|
||||
configure_dialog[38].d1 = d;
|
||||
|
||||
c++;
|
||||
d++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int mouse_valid(int type, int model)
|
||||
{
|
||||
if ((type & MOUSE_TYPE_IF_MASK) == MOUSE_TYPE_PS2 && !(models[model].flags & MODEL_PS2))
|
||||
|
|
@ -411,6 +500,8 @@ static int list_proc(int msg, DIALOG *d, int c)
|
|||
else
|
||||
configure_dialog[36].flags &= ~D_DISABLED;
|
||||
|
||||
update_hdd_list(new_model, 1);
|
||||
|
||||
return D_REDRAW;
|
||||
}
|
||||
|
||||
|
|
@ -583,6 +674,8 @@ pclog("video_card_available : %i\n", c);
|
|||
configure_dialog[33].d1 = 0;
|
||||
update_mouse_list();
|
||||
configure_dialog[33].d1 = settings_mouse_to_list[mouse_type];
|
||||
|
||||
update_hdd_list(model, 0);
|
||||
|
||||
if (!sound_card_has_config(configure_dialog[8].d1))
|
||||
configure_dialog[28].flags |= D_DISABLED;
|
||||
|
|
@ -669,6 +762,7 @@ pclog("video_card_available : %i\n", c);
|
|||
int new_fda = configure_dialog[25].d1;
|
||||
int new_fdb = configure_dialog[26].d1;
|
||||
int new_mouse = settings_list_to_mouse[configure_dialog[33].d1];
|
||||
int new_hdd = configure_dialog[38].d1;
|
||||
|
||||
sscanf(mem_size_str, "%i", &new_mem_size);
|
||||
new_mem_size &= ~(models[new_model].ram_granularity - 1);
|
||||
|
|
@ -683,7 +777,7 @@ pclog("video_card_available : %i\n", c);
|
|||
new_has_fpu != hasfpu || new_GAMEBLASTER != GAMEBLASTER || new_GUS != GUS ||
|
||||
new_SSI2001 != SSI2001 || new_sndcard != sound_card_current || new_voodoo != voodoo_enabled ||
|
||||
new_dynarec != cpu_use_dynarec || new_fda != fdd_get_type(0) || new_fdb != fdd_get_type(1) ||
|
||||
new_mouse != mouse_type)
|
||||
new_mouse != mouse_type || strncmp(hdd_list[new_hdd].internal_name, hdd_controller_name, sizeof(hdd_controller_name)-1))
|
||||
{
|
||||
if (alert("This will reset PCem!", "Okay to continue?", NULL, "OK", "Cancel", 0, 0) != 1)
|
||||
continue;
|
||||
|
|
@ -702,6 +796,11 @@ pclog("video_card_available : %i\n", c);
|
|||
cpu_use_dynarec = new_dynarec;
|
||||
mouse_type = new_mouse;
|
||||
|
||||
if (hdd_list[new_hdd].internal_name)
|
||||
strncpy(hdd_controller_name, hdd_list[new_hdd].internal_name, sizeof(hdd_controller_name)-1);
|
||||
else
|
||||
strcpy(hdd_controller_name, "none");
|
||||
|
||||
mem_resize();
|
||||
loadbios();
|
||||
resetpchard();
|
||||
|
|
|
|||
|
|
@ -47,7 +47,8 @@ char *device_get_config_string(char *name);
|
|||
enum
|
||||
{
|
||||
DEVICE_NOT_WORKING = 1, /*Device does not currently work correctly and will be disabled in a release build*/
|
||||
DEVICE_AT = 2 /*Device requires an AT-compatible system*/
|
||||
DEVICE_AT = 2, /*Device requires an AT-compatible system*/
|
||||
DEVICE_MCA = 0x20, /*Device requires an MCA system*/
|
||||
};
|
||||
|
||||
int model_get_config_int(char *s);
|
||||
|
|
|
|||
299
src/dma.c
299
src/dma.c
|
|
@ -7,9 +7,7 @@
|
|||
#include "video.h"
|
||||
|
||||
static uint8_t dmaregs[16];
|
||||
static int dmaon[4];
|
||||
static uint8_t dma16regs[16];
|
||||
static int dma16on[4];
|
||||
static uint8_t dmapages[16];
|
||||
|
||||
void dma_reset()
|
||||
|
|
@ -52,7 +50,7 @@ uint8_t dma_read(uint16_t addr, void *priv)
|
|||
dma.wp ^= 1;
|
||||
if (dma.wp)
|
||||
return dma.ac[(addr >> 1) & 3] & 0xff;
|
||||
return dma.ac[(addr >> 1) & 3] >> 8;
|
||||
return (dma.ac[(addr >> 1) & 3] >> 8) & 0xff;
|
||||
|
||||
case 1: case 3: case 5: case 7: /*Count registers*/
|
||||
dma.wp ^= 1;
|
||||
|
|
@ -80,10 +78,10 @@ void dma_write(uint16_t addr, uint8_t val, void *priv)
|
|||
{
|
||||
case 0: case 2: case 4: case 6: /*Address registers*/
|
||||
dma.wp ^= 1;
|
||||
if (dma.wp) dma.ab[(addr >> 1) & 3] = (dma.ab[(addr >> 1) & 3] & 0xff00) | val;
|
||||
else dma.ab[(addr >> 1) & 3] = (dma.ab[(addr >> 1) & 3] & 0x00ff) | (val << 8);
|
||||
if (dma.wp) dma.ab[(addr >> 1) & 3] = (dma.ab[(addr >> 1) & 3] & 0xffff00) | val;
|
||||
else dma.ab[(addr >> 1) & 3] = (dma.ab[(addr >> 1) & 3] & 0xff00ff) | (val << 8);
|
||||
dma.ac[(addr >> 1) & 3] = dma.ab[(addr >> 1) & 3];
|
||||
dmaon[(addr >> 1) & 3] = 1;
|
||||
// pclog("Addr = %04x\n", dma.ab[(addr >> 1) & 3]);
|
||||
return;
|
||||
|
||||
case 1: case 3: case 5: case 7: /*Count registers*/
|
||||
|
|
@ -91,7 +89,6 @@ void dma_write(uint16_t addr, uint8_t val, void *priv)
|
|||
if (dma.wp) dma.cb[(addr >> 1) & 3] = (dma.cb[(addr >> 1) & 3] & 0xff00) | val;
|
||||
else dma.cb[(addr >> 1) & 3] = (dma.cb[(addr >> 1) & 3] & 0x00ff) | (val << 8);
|
||||
dma.cc[(addr >> 1) & 3] = dma.cb[(addr >> 1) & 3];
|
||||
dmaon[(addr >> 1) & 3] = 1;
|
||||
return;
|
||||
|
||||
case 8: /*Control register*/
|
||||
|
|
@ -122,6 +119,155 @@ void dma_write(uint16_t addr, uint8_t val, void *priv)
|
|||
}
|
||||
}
|
||||
|
||||
static uint8_t dma_ps2_read(uint16_t addr, void *priv)
|
||||
{
|
||||
uint8_t temp;
|
||||
|
||||
switch (addr)
|
||||
{
|
||||
case 0x1a:
|
||||
switch (dma.xfr_command)
|
||||
{
|
||||
case 2: /*Address*/
|
||||
switch (dma.byte_ptr)
|
||||
{
|
||||
case 0:
|
||||
temp = (dma.xfr_channel & 4) ? (dma16.ac[dma.xfr_channel & 3] & 0xff) : (dma.ac[dma.xfr_channel] & 0xff);
|
||||
dma.byte_ptr = 1;
|
||||
break;
|
||||
case 1:
|
||||
temp = (dma.xfr_channel & 4) ? (dma16.ac[dma.xfr_channel & 3] >> 8) : (dma.ac[dma.xfr_channel] >> 8);
|
||||
dma.byte_ptr = 2;
|
||||
break;
|
||||
case 2:
|
||||
temp = (dma.xfr_channel & 4) ? (dma16.ac[dma.xfr_channel & 3] >> 16) : (dma.ac[dma.xfr_channel] >> 16);
|
||||
dma.byte_ptr = 0;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 4: /*Count*/
|
||||
if (dma.byte_ptr)
|
||||
temp = (dma.xfr_channel & 4) ? (dma16.cc[dma.xfr_channel & 3] >> 8) : (dma.cc[dma.xfr_channel] >> 8);
|
||||
else
|
||||
temp = (dma.xfr_channel & 4) ? (dma16.cc[dma.xfr_channel & 3] & 0xff) : (dma.cc[dma.xfr_channel] & 0xff);
|
||||
dma.byte_ptr = (dma.byte_ptr + 1) & 1;
|
||||
break;
|
||||
case 7: /*Mode*/
|
||||
temp = (dma.xfr_channel & 4) ? dma16.mode[dma.xfr_channel & 3] : dma.mode[dma.xfr_channel];
|
||||
break;
|
||||
|
||||
default:
|
||||
fatal("Bad XFR Read command %i channel %i\n", dma.xfr_command, dma.xfr_channel);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
// pclog("Read DMA %04X %04X:%04X %02X\n",addr,CS,pc, temp);
|
||||
|
||||
return temp;
|
||||
}
|
||||
|
||||
static void dma_ps2_write(uint16_t addr, uint8_t val, void *priv)
|
||||
{
|
||||
uint8_t mode;
|
||||
|
||||
// pclog("Write PS2 DMA %04X %02X %04X:%04X\n",addr,val,CS,cpu_state.pc);
|
||||
|
||||
switch (addr)
|
||||
{
|
||||
case 0x18:
|
||||
dma.xfr_channel = val & 0x7;
|
||||
dma.xfr_command = val >> 4;
|
||||
dma.byte_ptr = 0;
|
||||
switch (dma.xfr_command)
|
||||
{
|
||||
case 9: /*Set DMA mask*/
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.m |= (1 << (dma.xfr_channel & 3));
|
||||
else
|
||||
dma.m |= (1 << dma.xfr_channel);
|
||||
break;
|
||||
case 0xa: /*Reset DMA mask*/
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.m &= ~(1 << (dma.xfr_channel & 3));
|
||||
else
|
||||
dma.m &= ~(1 << dma.xfr_channel);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0x1a:
|
||||
switch (dma.xfr_command)
|
||||
{
|
||||
case 2: /*Address*/
|
||||
switch (dma.byte_ptr)
|
||||
{
|
||||
case 0:
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.ac[dma.xfr_channel & 3] = (dma16.ac[dma.xfr_channel & 3] & 0xffff00) | val;
|
||||
else
|
||||
dma.ac[dma.xfr_channel] = (dma.ac[dma.xfr_channel] & 0xffff00) | val;
|
||||
dma.byte_ptr = 1;
|
||||
break;
|
||||
case 1:
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.ac[dma.xfr_channel & 3] = (dma16.ac[dma.xfr_channel & 3] & 0xff00ff) | (val << 8);
|
||||
else
|
||||
dma.ac[dma.xfr_channel] = (dma.ac[dma.xfr_channel] & 0xff00ff) | (val << 8);
|
||||
dma.byte_ptr = 2;
|
||||
break;
|
||||
case 2:
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.ac[dma.xfr_channel & 3] = (dma16.ac[dma.xfr_channel & 3] & 0x00ffff) | (val << 16);
|
||||
else
|
||||
dma.ac[dma.xfr_channel] = (dma.ac[dma.xfr_channel] & 0x00ffff) | (val << 16);
|
||||
dma.byte_ptr = 0;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case 4: /*Count*/
|
||||
if (dma.byte_ptr)
|
||||
{
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.cc[dma.xfr_channel & 3] = (dma16.cc[dma.xfr_channel & 3] & 0xff) | (val << 8);
|
||||
else
|
||||
dma.cc[dma.xfr_channel] = (dma.cc[dma.xfr_channel] & 0xff) | (val << 8);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.cc[dma.xfr_channel & 3] = (dma16.cc[dma.xfr_channel & 3] & 0xff00) | val;
|
||||
else
|
||||
dma.cc[dma.xfr_channel] = (dma.cc[dma.xfr_channel] & 0xff00) | val;
|
||||
}
|
||||
dma.byte_ptr = (dma.byte_ptr + 1) & 1;
|
||||
break;
|
||||
|
||||
case 7: /*Mode register*/
|
||||
mode = 0;
|
||||
if (val & 0x10)
|
||||
mode |= 0x20;
|
||||
if ((val & 0xc) == 4)
|
||||
mode |= 8;
|
||||
else if ((val & 0xc) == 0xc)
|
||||
mode |= 4;
|
||||
if ((val & 0x40) && !(dma.xfr_channel & 4))
|
||||
fatal("16-bit DMA on 8-bit channel\n");
|
||||
if (!(val & 0x40) && (dma.xfr_channel & 4))
|
||||
fatal("8-bit DMA on 16-bit channel\n");
|
||||
if (dma.xfr_channel & 4)
|
||||
dma16.mode[dma.xfr_channel & 3] = mode;
|
||||
else
|
||||
dma.mode[dma.xfr_channel] = mode;
|
||||
break;
|
||||
|
||||
default:
|
||||
fatal("Bad XFR command %i channel %i val %02x\n", dma.xfr_command, dma.xfr_channel, val);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t dma16_read(uint16_t addr, void *priv)
|
||||
{
|
||||
uint8_t temp;
|
||||
|
|
@ -131,9 +277,15 @@ uint8_t dma16_read(uint16_t addr, void *priv)
|
|||
{
|
||||
case 0: case 2: case 4: case 6: /*Address registers*/
|
||||
dma16.wp ^= 1;
|
||||
if (dma.is_ps2)
|
||||
{
|
||||
if (dma16.wp)
|
||||
return dma16.ac[(addr >> 1) & 3] & 0xff;
|
||||
return (dma16.ac[(addr >> 1) & 3] >> 8) & 0xff;
|
||||
}
|
||||
if (dma16.wp)
|
||||
return dma16.ac[(addr >> 1) & 3] & 0xff;
|
||||
return dma16.ac[(addr >> 1) & 3] >> 8;
|
||||
return (dma16.ac[(addr >> 1) & 3] >> 1) & 0xff;
|
||||
return (dma16.ac[(addr >> 1) & 3] >> 9) & 0xff;
|
||||
|
||||
case 1: case 3: case 5: case 7: /*Count registers*/
|
||||
dma16.wp ^= 1;
|
||||
|
|
@ -158,10 +310,17 @@ void dma16_write(uint16_t addr, uint8_t val, void *priv)
|
|||
{
|
||||
case 0: case 2: case 4: case 6: /*Address registers*/
|
||||
dma16.wp ^= 1;
|
||||
if (dma16.wp) dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0xff00) | val;
|
||||
else dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0x00ff) | (val << 8);
|
||||
if (dma.is_ps2)
|
||||
{
|
||||
if (dma16.wp) dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0xffff00) | val;
|
||||
else dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0xff00ff) | (val << 8);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma16.wp) dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0xfffe00) | (val << 1);
|
||||
else dma16.ab[(addr >> 1) & 3] = (dma16.ab[(addr >> 1) & 3] & 0xfe01ff) | (val << 9);
|
||||
}
|
||||
dma16.ac[(addr >> 1) & 3] = dma16.ab[(addr >> 1) & 3];
|
||||
dma16on[(addr >> 1) & 3] = 1;
|
||||
return;
|
||||
|
||||
case 1: case 3: case 5: case 7: /*Count registers*/
|
||||
|
|
@ -169,7 +328,6 @@ void dma16_write(uint16_t addr, uint8_t val, void *priv)
|
|||
if (dma16.wp) dma16.cb[(addr >> 1) & 3] = (dma16.cb[(addr >> 1) & 3] & 0xff00) | val;
|
||||
else dma16.cb[(addr >> 1) & 3] = (dma16.cb[(addr >> 1) & 3] & 0x00ff) | (val << 8);
|
||||
dma16.cc[(addr >> 1) & 3] = dma16.cb[(addr >> 1) & 3];
|
||||
dma16on[(addr >> 1) & 3] = 1;
|
||||
return;
|
||||
|
||||
case 8: /*Control register*/
|
||||
|
|
@ -207,15 +365,38 @@ void dma_page_write(uint16_t addr, uint8_t val, void *priv)
|
|||
{
|
||||
case 1:
|
||||
dma.page[2] = (AT) ? val : val & 0xf;
|
||||
dma.ab[2] = (dma.ab[2] & 0xffff) | (dma.page[2] << 16);
|
||||
dma.ac[2] = (dma.ac[2] & 0xffff) | (dma.page[2] << 16);
|
||||
break;
|
||||
case 2:
|
||||
dma.page[3] = (AT) ? val : val & 0xf;
|
||||
dma.ab[3] = (dma.ab[3] & 0xffff) | (dma.page[3] << 16);
|
||||
dma.ac[3] = (dma.ac[3] & 0xffff) | (dma.page[3] << 16);
|
||||
break;
|
||||
case 3:
|
||||
dma.page[1] = (AT) ? val : val & 0xf;
|
||||
dma.ab[1] = (dma.ab[1] & 0xffff) | (dma.page[1] << 16);
|
||||
dma.ac[1] = (dma.ac[1] & 0xffff) | (dma.page[1] << 16);
|
||||
break;
|
||||
case 7:
|
||||
dma.page[0] = (AT) ? val : val & 0xf;
|
||||
dma.ab[0] = (dma.ab[0] & 0xffff) | (dma.page[0] << 16);
|
||||
dma.ac[0] = (dma.ac[0] & 0xffff) | (dma.page[0] << 16);
|
||||
break;
|
||||
case 0x9:
|
||||
dma16.page[2] = val & 0xfe;
|
||||
dma16.ab[2] = (dma16.ab[2] & 0x1ffff) | (dma16.page[2] << 16);
|
||||
dma16.ac[2] = (dma16.ac[2] & 0x1ffff) | (dma16.page[2] << 16);
|
||||
break;
|
||||
case 0xa:
|
||||
dma16.page[3] = val & 0xfe;
|
||||
dma16.ab[3] = (dma16.ab[3] & 0x1ffff) | (dma16.page[3] << 16);
|
||||
dma16.ac[3] = (dma16.ac[3] & 0x1ffff) | (dma16.page[3] << 16);
|
||||
break;
|
||||
case 0xb:
|
||||
dma16.page[1] = val;
|
||||
dma16.page[1] = val & 0xfe;
|
||||
dma16.ab[1] = (dma16.ab[1] & 0x1ffff) | (dma16.page[1] << 16);
|
||||
dma16.ac[1] = (dma16.ac[1] & 0x1ffff) | (dma16.page[1] << 16);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
@ -229,6 +410,7 @@ void dma_init()
|
|||
{
|
||||
io_sethandler(0x0000, 0x0010, dma_read, NULL, NULL, dma_write, NULL, NULL, NULL);
|
||||
io_sethandler(0x0080, 0x0008, dma_page_read, NULL, NULL, dma_page_write, NULL, NULL, NULL);
|
||||
dma.is_ps2 = 0;
|
||||
}
|
||||
|
||||
void dma16_init()
|
||||
|
|
@ -237,10 +419,18 @@ void dma16_init()
|
|||
io_sethandler(0x0088, 0x0008, dma_page_read, NULL, NULL, dma_page_write, NULL, NULL, NULL);
|
||||
}
|
||||
|
||||
void ps2_dma_init()
|
||||
{
|
||||
io_sethandler(0x0018, 0x0001, dma_ps2_read, NULL, NULL, dma_ps2_write, NULL, NULL, NULL);
|
||||
io_sethandler(0x001a, 0x0001, dma_ps2_read, NULL, NULL, dma_ps2_write, NULL, NULL, NULL);
|
||||
dma.is_ps2 = 1;
|
||||
}
|
||||
|
||||
|
||||
uint8_t _dma_read(uint32_t addr)
|
||||
{
|
||||
return mem_readb_phys(addr);
|
||||
uint8_t temp = mem_readb_phys(addr);
|
||||
return temp;
|
||||
}
|
||||
|
||||
void _dma_write(uint32_t addr, uint8_t val)
|
||||
|
|
@ -267,10 +457,22 @@ int dma_channel_read(int channel)
|
|||
if ((dma.mode[channel] & 0xC) != 8)
|
||||
return DMA_NODATA;
|
||||
|
||||
temp = _dma_read(dma.ac[channel] + (dma.page[channel] << 16)); //ram[(dma.ac[2]+(dma.page[2]<<16))&rammask];
|
||||
temp = _dma_read(dma.ac[channel]);
|
||||
|
||||
if (dma.mode[channel] & 0x20) dma.ac[channel]--;
|
||||
else dma.ac[channel]++;
|
||||
if (dma.mode[channel] & 0x20)
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma.ac[channel]--;
|
||||
else
|
||||
dma.ac[channel] = (dma.ac[channel] & 0xff0000) | ((dma.ac[channel] - 1) & 0xffff);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma.ac[channel]++;
|
||||
else
|
||||
dma.ac[channel] = (dma.ac[channel] & 0xff0000) | ((dma.ac[channel] + 1) & 0xffff);
|
||||
}
|
||||
dma.cc[channel]--;
|
||||
if (dma.cc[channel] < 0)
|
||||
{
|
||||
|
|
@ -297,11 +499,24 @@ int dma_channel_read(int channel)
|
|||
if ((dma16.mode[channel] & 0xC) != 8)
|
||||
return DMA_NODATA;
|
||||
|
||||
temp = _dma_read((dma16.ac[channel] << 1) + ((dma16.page[channel] & ~1) << 16)) |
|
||||
(_dma_read((dma16.ac[channel] << 1) + ((dma16.page[channel] & ~1) << 16) + 1) << 8);
|
||||
temp = _dma_read(dma16.ac[channel]) |
|
||||
(_dma_read(dma16.ac[channel] + 1) << 8);
|
||||
|
||||
if (dma16.mode[channel] & 0x20)
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma16.ac[channel] -= 2;
|
||||
else
|
||||
dma16.ac[channel] = (dma16.ac[channel] & 0xfe0000) | ((dma16.ac[channel] - 2) & 0x1ffff);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma16.ac[channel] += 2;
|
||||
else
|
||||
dma16.ac[channel] = (dma16.ac[channel] & 0xfe0000) | ((dma16.ac[channel] + 2) & 0x1ffff);
|
||||
}
|
||||
|
||||
if (dma16.mode[channel] & 0x20) dma16.ac[channel]--;
|
||||
else dma16.ac[channel]++;
|
||||
dma16.cc[channel]--;
|
||||
if (dma16.cc[channel] < 0)
|
||||
{
|
||||
|
|
@ -337,10 +552,23 @@ int dma_channel_write(int channel, uint16_t val)
|
|||
if ((dma.mode[channel] & 0xC) != 4)
|
||||
return DMA_NODATA;
|
||||
|
||||
_dma_write(dma.ac[channel] + (dma.page[channel] << 16), val);
|
||||
_dma_write(dma.ac[channel], val);
|
||||
|
||||
if (dma.mode[channel] & 0x20)
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma.ac[channel]--;
|
||||
else
|
||||
dma.ac[channel] = (dma.ac[channel] & 0xff0000) | ((dma.ac[channel] - 1) & 0xffff);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma.ac[channel]++;
|
||||
else
|
||||
dma.ac[channel] = (dma.ac[channel] & 0xff0000) | ((dma.ac[channel] + 1) & 0xffff);
|
||||
}
|
||||
|
||||
if (dma.mode[channel]&0x20) dma.ac[channel]--;
|
||||
else dma.ac[channel]++;
|
||||
dma.cc[channel]--;
|
||||
if (dma.cc[channel] < 0)
|
||||
{
|
||||
|
|
@ -365,11 +593,24 @@ int dma_channel_write(int channel, uint16_t val)
|
|||
if ((dma16.mode[channel] & 0xC) != 4)
|
||||
return DMA_NODATA;
|
||||
|
||||
_dma_write((dma16.ac[channel] << 1) + ((dma16.page[channel] & ~1) << 16), val);
|
||||
_dma_write((dma16.ac[channel] << 1) + ((dma16.page[channel] & ~1) << 16) + 1, val >> 8);
|
||||
_dma_write(dma16.ac[channel], val);
|
||||
_dma_write(dma16.ac[channel] + 1, val >> 8);
|
||||
|
||||
if (dma16.mode[channel] & 0x20)
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma16.ac[channel] -= 2;
|
||||
else
|
||||
dma16.ac[channel] = (dma16.ac[channel] & 0xfe0000) | ((dma16.ac[channel] - 2) & 0x1ffff);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dma.is_ps2)
|
||||
dma16.ac[channel] += 2;
|
||||
else
|
||||
dma16.ac[channel] = (dma16.ac[channel] & 0xfe0000) | ((dma16.ac[channel] + 2) & 0x1ffff);
|
||||
}
|
||||
|
||||
if (dma16.mode[channel]&0x20) dma16.ac[channel]--;
|
||||
else dma16.ac[channel]++;
|
||||
dma16.cc[channel]--;
|
||||
if (dma16.cc[channel] < 0)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
void dma_init();
|
||||
void dma16_init();
|
||||
void ps2_dma_init();
|
||||
void dma_reset();
|
||||
|
||||
#define DMA_NODATA -1
|
||||
|
|
|
|||
|
|
@ -686,6 +686,11 @@ uint8_t fdc_read(uint16_t addr, void *priv)
|
|||
temp &= ~0x40;
|
||||
else
|
||||
temp &= ~0x20;
|
||||
|
||||
if (fdc.dor & 0x10)
|
||||
temp |= 1;
|
||||
if (fdc.dor & 0x20)
|
||||
temp |= 2;
|
||||
break;
|
||||
case 3:
|
||||
drive = (fdc.dor & 1) ^ fdd_swap;
|
||||
|
|
@ -765,6 +770,7 @@ uint8_t fdc_read(uint16_t addr, void *priv)
|
|||
if (fdc.dskchg_activelow) /*PC2086/3086 seem to reverse this bit*/
|
||||
temp ^= 0x80;
|
||||
// printf("- DC %i %02X %02X %i %i - ",fdc.dor & 1, fdc.dor, 0x10 << (fdc.dor & 1), discchanged[fdc.dor & 1], driveempty[fdc.dor & 1]);
|
||||
temp |= 1;
|
||||
// discchanged[fdc.dor&1]=0;
|
||||
break;
|
||||
default:
|
||||
|
|
|
|||
13
src/ibm.h
13
src/ibm.h
|
|
@ -288,7 +288,7 @@ typedef struct PIT
|
|||
void (*set_out_funcs[3])(int new_out, int old_out);
|
||||
} PIT;
|
||||
|
||||
PIT pit;
|
||||
PIT pit, pit2;
|
||||
void setpitclock(float clock);
|
||||
|
||||
float pit_timer0_freq();
|
||||
|
|
@ -302,7 +302,7 @@ float pit_timer0_freq();
|
|||
/*DMA*/
|
||||
typedef struct DMA
|
||||
{
|
||||
uint16_t ab[4],ac[4];
|
||||
uint32_t ab[4],ac[4];
|
||||
uint16_t cb[4];
|
||||
int cc[4];
|
||||
int wp;
|
||||
|
|
@ -310,6 +310,11 @@ typedef struct DMA
|
|||
uint8_t page[4];
|
||||
uint8_t stat;
|
||||
uint8_t command;
|
||||
|
||||
int xfr_command, xfr_channel;
|
||||
int byte_ptr;
|
||||
|
||||
int is_ps2;
|
||||
} DMA;
|
||||
|
||||
DMA dma,dma16;
|
||||
|
|
@ -396,7 +401,8 @@ enum
|
|||
ROM_IBMPS1_2121,
|
||||
ROM_AMI386DX_OPTI495,
|
||||
ROM_MR386DX_OPTI495,
|
||||
ROM_IBMPS2_M30_286,
|
||||
ROM_IBMPS2_M30_286,
|
||||
ROM_IBMPS2_M50,
|
||||
|
||||
ROM_MAX
|
||||
};
|
||||
|
|
@ -511,6 +517,7 @@ void pclog(const char *format, ...);
|
|||
void fatal(const char *format, ...);
|
||||
void warning(const char *format, ...);
|
||||
extern int nmi;
|
||||
extern int nmi_auto_clear;
|
||||
|
||||
|
||||
extern float isa_timing, bus_timing;
|
||||
|
|
|
|||
|
|
@ -20,6 +20,8 @@
|
|||
#define STAT_IFULL 0x02
|
||||
#define STAT_OFULL 0x01
|
||||
|
||||
#define PS2_REFRESH_TIME (16 * TIMER_USEC)
|
||||
|
||||
struct
|
||||
{
|
||||
int initialised;
|
||||
|
|
@ -41,6 +43,11 @@ struct
|
|||
|
||||
void (*mouse_write)(uint8_t val, void *p);
|
||||
void *mouse_p;
|
||||
|
||||
int refresh_time;
|
||||
int refresh;
|
||||
|
||||
int is_ps2;
|
||||
} keyboard_at;
|
||||
|
||||
static uint8_t key_ctrl_queue[16];
|
||||
|
|
@ -448,9 +455,18 @@ uint8_t keyboard_at_read(uint16_t port, void *priv)
|
|||
keyboard_at.last_irq = 0;
|
||||
break;
|
||||
|
||||
case 0x61:
|
||||
if (ppispeakon) return (ppi.pb&~0xC0)|0x20;
|
||||
return ppi.pb&~0xe0;
|
||||
case 0x61:
|
||||
temp = ppi.pb & ~0xe0;
|
||||
if (ppispeakon)
|
||||
temp |= 0x20;
|
||||
if (keyboard_at.is_ps2)
|
||||
{
|
||||
if (keyboard_at.refresh)
|
||||
temp |= 0x10;
|
||||
else
|
||||
temp &= ~0x10;
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x64:
|
||||
temp = keyboard_at.status & ~4;
|
||||
|
|
@ -479,6 +495,12 @@ void keyboard_at_reset()
|
|||
keyboard_scan = 1;
|
||||
}
|
||||
|
||||
static void at_refresh(void *p)
|
||||
{
|
||||
keyboard_at.refresh = !keyboard_at.refresh;
|
||||
keyboard_at.refresh_time += PS2_REFRESH_TIME;
|
||||
}
|
||||
|
||||
void keyboard_at_init()
|
||||
{
|
||||
//return;
|
||||
|
|
@ -488,6 +510,7 @@ void keyboard_at_init()
|
|||
keyboard_poll = keyboard_at_poll;
|
||||
keyboard_at.mouse_write = NULL;
|
||||
keyboard_at.mouse_p = NULL;
|
||||
keyboard_at.is_ps2 = 0;
|
||||
|
||||
timer_add(keyboard_at_poll, &keybsenddelay, TIMER_ALWAYS_ENABLED, NULL);
|
||||
}
|
||||
|
|
@ -497,3 +520,9 @@ void keyboard_at_set_mouse(void (*mouse_write)(uint8_t val, void *p), void *p)
|
|||
keyboard_at.mouse_write = mouse_write;
|
||||
keyboard_at.mouse_p = p;
|
||||
}
|
||||
|
||||
void keyboard_at_init_ps2()
|
||||
{
|
||||
timer_add(at_refresh, &keyboard_at.refresh_time, TIMER_ALWAYS_ENABLED, NULL);
|
||||
keyboard_at.is_ps2 = 1;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
void keyboard_at_init();
|
||||
void keyboard_at_init_ps2();
|
||||
void keyboard_at_reset();
|
||||
void keyboard_at_poll();
|
||||
void keyboard_at_set_mouse(void (*mouse_write)(uint8_t val, void *p), void *p);
|
||||
|
|
|
|||
60
src/mca.c
Normal file
60
src/mca.c
Normal file
|
|
@ -0,0 +1,60 @@
|
|||
#include "ibm.h"
|
||||
#include "io.h"
|
||||
#include "mem.h"
|
||||
|
||||
#include "mca.h"
|
||||
|
||||
void (*mca_card_write[8])(int addr, uint8_t val, void *priv);
|
||||
uint8_t (*mca_card_read[8])(int addr, void *priv);
|
||||
void *mca_priv[8];
|
||||
static int mca_index;
|
||||
static int mca_nr_cards;
|
||||
|
||||
void mca_init(int nr_cards)
|
||||
{
|
||||
int c;
|
||||
|
||||
for (c = 0; c < 8; c++)
|
||||
mca_card_read[c] = mca_card_write[c] = mca_priv[c] = NULL;
|
||||
|
||||
mca_index = 0;
|
||||
mca_nr_cards = nr_cards;
|
||||
}
|
||||
|
||||
void mca_set_index(int index)
|
||||
{
|
||||
mca_index = index;
|
||||
}
|
||||
|
||||
uint8_t mca_read(uint16_t port)
|
||||
{
|
||||
if (mca_index >= mca_nr_cards)
|
||||
return 0xff;
|
||||
if (!mca_card_read[mca_index])
|
||||
return 0xff;
|
||||
return mca_card_read[mca_index](port, mca_priv[mca_index]);
|
||||
}
|
||||
|
||||
void mca_write(uint16_t port, uint8_t val)
|
||||
{
|
||||
if (mca_index >= mca_nr_cards)
|
||||
return;
|
||||
if (mca_card_write[mca_index])
|
||||
mca_card_write[mca_index](port, val, mca_priv[mca_index]);
|
||||
}
|
||||
|
||||
void mca_add(uint8_t (*read)(int addr, void *priv), void (*write)(int addr, uint8_t val, void *priv), void *priv)
|
||||
{
|
||||
int c;
|
||||
|
||||
for (c = 0; c < mca_nr_cards; c++)
|
||||
{
|
||||
if (!mca_card_read[c] && !mca_card_write[c])
|
||||
{
|
||||
mca_card_read[c] = read;
|
||||
mca_card_write[c] = write;
|
||||
mca_priv[c] = priv;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
5
src/mca.h
Normal file
5
src/mca.h
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
void mca_init(int nr_cards);
|
||||
void mca_add(uint8_t (*read)(int addr, void *priv), void (*write)(int addr, uint8_t val, void *priv), void *priv);
|
||||
void mca_set_index(int index);
|
||||
uint8_t mca_read(uint16_t port);
|
||||
void mca_write(uint16_t port, uint8_t val);
|
||||
25
src/mem.c
25
src/mem.c
|
|
@ -579,7 +579,30 @@ int loadbios()
|
|||
fclose(f);
|
||||
biosmask = 0x1ffff;
|
||||
return 1;
|
||||
|
||||
|
||||
case ROM_IBMPS2_M50:
|
||||
f=romfopen("roms/i8550021/90x7423.zm14","rb");
|
||||
ff=romfopen("roms/i8550021/90x7426.zm16","rb");
|
||||
if (!f || !ff) break;
|
||||
for (c = 0x0000; c < 0x10000; c += 2)
|
||||
{
|
||||
rom[c] = getc(f);
|
||||
rom[c+1] = getc(ff);
|
||||
}
|
||||
fclose(ff);
|
||||
fclose(f);
|
||||
f=romfopen("roms/i8550021/90x7420.zm13","rb");
|
||||
ff=romfopen("roms/i8550021/90x7429.zm18","rb");
|
||||
if (!f || !ff) break;
|
||||
for (c = 0x10000; c < 0x20000; c += 2)
|
||||
{
|
||||
rom[c] = getc(f);
|
||||
rom[c+1] = getc(ff);
|
||||
}
|
||||
fclose(ff);
|
||||
fclose(f);
|
||||
biosmask = 0x1ffff;
|
||||
return 1;
|
||||
}
|
||||
printf("Failed to load ROM!\n");
|
||||
if (f) fclose(f);
|
||||
|
|
|
|||
20
src/model.c
20
src/model.c
|
|
@ -38,6 +38,7 @@
|
|||
#include "pit.h"
|
||||
#include "ps1.h"
|
||||
#include "ps2.h"
|
||||
#include "ps2_mca.h"
|
||||
#include "scat.h"
|
||||
#include "serial.h"
|
||||
#include "sis496.h"
|
||||
|
|
@ -65,6 +66,7 @@ void deskpro386_init();
|
|||
void ps1_m2011_init();
|
||||
void ps1_m2121_init();
|
||||
void ps2_m30_286_init();
|
||||
void ps2_init();
|
||||
void at_neat_init();
|
||||
void at_scat_init();
|
||||
void at_acer386sx_init();
|
||||
|
|
@ -111,6 +113,7 @@ MODEL models[] =
|
|||
{"DELL System 200", ROM_DELL200, "dells200", { "", cpus_286, "", NULL, "", NULL}, 0, MODEL_AT, 1, 16, 1, at_init, NULL},
|
||||
{"IBM PS/1 model 2011", ROM_IBMPS1_2011, "ibmps1es", { "", cpus_ps1_m2011, "", NULL, "", NULL}, 1, MODEL_AT|MODEL_PS2, 1, 16, 1, ps1_m2011_init, NULL},
|
||||
{"IBM PS/2 Model 30-286", ROM_IBMPS2_M30_286, "ibmps2_m30_286", { "", cpus_ps2_m30_286, "", NULL, "", NULL}, 1, MODEL_AT|MODEL_PS2, 1, 16, 1, ps2_m30_286_init, NULL},
|
||||
{"IBM PS/2 Model 50", ROM_IBMPS2_M50, "ibmps2_m50", { "", cpus_ps2_m30_286, "", NULL, "", NULL}, 1, MODEL_AT|MODEL_PS2|MODEL_MCA, 1, 16, 1, ps2_init, NULL},
|
||||
{"IBM PS/1 model 2121", ROM_IBMPS1_2121, "ibmps1_2121", { "Intel", cpus_i386SX, "AMD", cpus_Am386SX, "Cyrix", cpus_486SLC}, 1, MODEL_AT|MODEL_PS2|MODEL_HAS_IDE, 1, 16, 1, ps1_m2121_init, NULL},
|
||||
{"Compaq Deskpro 386", ROM_DESKPRO_386, "deskpro386", { "Intel", cpus_i386DX, "AMD", cpus_Am386DX, "Cyrix", cpus_486DLC}, 0, MODEL_AT, 1, 15, 1, deskpro386_init, NULL},
|
||||
{"Acer 386SX25/N", ROM_ACER386, "acer386", { "Intel", cpus_acer, "", NULL, "", NULL}, 1, MODEL_AT|MODEL_PS2|MODEL_HAS_IDE, 1, 16, 1, at_acer386sx_init, NULL},
|
||||
|
|
@ -350,6 +353,23 @@ void ps2_m30_286_init()
|
|||
fdc_set_dskchg_activelow();
|
||||
}
|
||||
|
||||
void ps2_init()
|
||||
{
|
||||
AT = 1;
|
||||
common_init();
|
||||
mem_add_bios();
|
||||
dma16_init();
|
||||
ps2_dma_init();
|
||||
ide_init();
|
||||
keyboard_at_init();
|
||||
keyboard_at_init_ps2();
|
||||
mouse_ps2_init();
|
||||
nvr_init();
|
||||
pic2_init();
|
||||
ps2_mca_board_init();
|
||||
pit_ps2_init();
|
||||
}
|
||||
|
||||
void at_neat_init()
|
||||
{
|
||||
at_init();
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@
|
|||
#define MODEL_AMSTRAD 4
|
||||
#define MODEL_OLIM24 8
|
||||
#define MODEL_HAS_IDE 0x10
|
||||
#define MODEL_MCA 0x20
|
||||
|
||||
typedef struct
|
||||
{
|
||||
|
|
|
|||
|
|
@ -209,6 +209,7 @@ void loadnvr()
|
|||
case ROM_IBMPS1_2011: f = romfopen("nvr/ibmps1_2011.nvr", "rb"); /*nvrmask = 127; */break;
|
||||
case ROM_IBMPS1_2121: f = romfopen("nvr/ibmps1_2121.nvr", "rb"); nvrmask = 127; break;
|
||||
case ROM_IBMPS2_M30_286: f = romfopen("nvr/ibmps2_m30_286.nvr", "rb"); /*nvrmask = 127; */break;
|
||||
case ROM_IBMPS2_M50: f = romfopen("nvr/ibmps2_m50.nvr", "rb"); break;
|
||||
case ROM_CMDPC30: f = romfopen("nvr/cmdpc30.nvr", "rb"); nvrmask = 127; break;
|
||||
case ROM_AMI286: f = romfopen("nvr/ami286.nvr", "rb"); nvrmask = 127; break;
|
||||
case ROM_AWARD286: f = romfopen("nvr/award286.nvr", "rb"); nvrmask = 127; break;
|
||||
|
|
@ -269,6 +270,7 @@ void savenvr()
|
|||
case ROM_IBMPS1_2011: f = romfopen("nvr/ibmps1_2011.nvr", "wb"); break;
|
||||
case ROM_IBMPS1_2121: f = romfopen("nvr/ibmps1_2121.nvr", "wb"); break;
|
||||
case ROM_IBMPS2_M30_286: f = romfopen("nvr/ibmps2_m30_286.nvr", "wb"); break;
|
||||
case ROM_IBMPS2_M50: f = romfopen("nvr/ibmps2_m50.nvr", "wb"); break;
|
||||
case ROM_CMDPC30: f = romfopen("nvr/cmdpc30.nvr", "wb"); break;
|
||||
case ROM_AMI286: f = romfopen("nvr/ami286.nvr", "wb"); break;
|
||||
case ROM_AWARD286: f = romfopen("nvr/award286.nvr", "wb"); break;
|
||||
|
|
|
|||
2
src/pc.c
2
src/pc.c
|
|
@ -184,7 +184,6 @@ void pc_reset()
|
|||
dma_reset();
|
||||
fdc_reset();
|
||||
pic_reset();
|
||||
pit_reset();
|
||||
serial_reset();
|
||||
|
||||
if (AT)
|
||||
|
|
@ -302,7 +301,6 @@ void initpc(int argc, char *argv[])
|
|||
}
|
||||
}
|
||||
|
||||
pit_reset();
|
||||
/* if (romset==ROM_AMI386 || romset==ROM_AMI486) */fullspeed();
|
||||
ali1429_reset();
|
||||
// CPUID=(is486 && (cpuspeed==7 || cpuspeed>=9));
|
||||
|
|
|
|||
|
|
@ -365,7 +365,10 @@ uint8_t picinterrupt()
|
|||
pic.pend &= ~(1 << c);
|
||||
pic.ins |= (1 << c);
|
||||
pic_update_mask(&pic.mask2, pic.ins);
|
||||
|
||||
pic_updatepending();
|
||||
if (!c)
|
||||
pit_set_gate(&pit2, 0, 0);
|
||||
|
||||
if (pic.icw4 & 0x02)
|
||||
pic_autoeoi();
|
||||
|
|
|
|||
41
src/pit.c
41
src/pit.c
|
|
@ -573,6 +573,20 @@ void pit_irq0_timer_pcjr(int new_out, int old_out)
|
|||
picintc(1);
|
||||
}
|
||||
|
||||
void pit_irq0_ps2(int new_out, int old_out)
|
||||
{
|
||||
//pclog("pit_irq0_ps2 %i %i\n", new_out, old_out);
|
||||
if (new_out && !old_out)
|
||||
{
|
||||
picint(1);
|
||||
pit_set_gate_no_timer(&pit2, 0, 1);
|
||||
}
|
||||
if (!new_out)
|
||||
picintc(1);
|
||||
if (!new_out && old_out)
|
||||
pit_clock(&pit2, 0);
|
||||
}
|
||||
|
||||
void pit_refresh_timer_xt(int new_out, int old_out)
|
||||
{
|
||||
if (new_out && !old_out)
|
||||
|
|
@ -599,6 +613,12 @@ void pit_speaker_timer(int new_out, int old_out)
|
|||
ppispeakon = new_out;
|
||||
}
|
||||
|
||||
void pit_nmi_ps2(int new_out, int old_out)
|
||||
{
|
||||
nmi = new_out;
|
||||
if (nmi)
|
||||
nmi_auto_clear = 1;
|
||||
}
|
||||
|
||||
void pit_init()
|
||||
{
|
||||
|
|
@ -622,3 +642,24 @@ void pit_init()
|
|||
pit_set_out_func(&pit, 1, pit_null_timer);
|
||||
pit_set_out_func(&pit, 2, pit_speaker_timer);
|
||||
}
|
||||
|
||||
void pit_ps2_init()
|
||||
{
|
||||
pit_reset(&pit2);
|
||||
|
||||
io_sethandler(0x0044, 0x0001, pit_read, NULL, NULL, pit_write, NULL, NULL, &pit2);
|
||||
io_sethandler(0x0047, 0x0001, pit_read, NULL, NULL, pit_write, NULL, NULL, &pit2);
|
||||
|
||||
pit2.gate[0] = 0;
|
||||
pit2.using_timer[0] = 0;
|
||||
pit2.disabled[0] = 1;
|
||||
|
||||
pit2.pit_nr[0].nr = 0;
|
||||
pit2.pit_nr[0].pit = &pit2;
|
||||
|
||||
timer_add(pit_timer_over, &pit2.c[0], &pit2.running[0], (void *)&pit2.pit_nr[0]);
|
||||
|
||||
pit_set_out_func(&pit, 0, pit_irq0_ps2);
|
||||
pit_set_out_func(&pit2, 0, pit_nmi_ps2);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,10 +1,11 @@
|
|||
extern double PITCONST;
|
||||
void pit_init();
|
||||
void pit_ps2_init();
|
||||
void pit_reset();
|
||||
void pit_set_gate(int channel, int gate);
|
||||
void pit_set_using_timer(int t, int using_timer);
|
||||
void pit_set_out_func(int t, void (*func)(int new_out, int old_out));
|
||||
void pit_clock(int t);
|
||||
void pit_set_gate(PIT *pit, int channel, int gate);
|
||||
void pit_set_using_timer(PIT *pit, int t, int using_timer);
|
||||
void pit_set_out_func(PIT *pit, int t, void (*func)(int new_out, int old_out));
|
||||
void pit_clock(PIT *pit, int t);
|
||||
|
||||
|
||||
void pit_null_timer(int new_out, int old_out);
|
||||
|
|
|
|||
254
src/ps2_mca.c
Normal file
254
src/ps2_mca.c
Normal file
|
|
@ -0,0 +1,254 @@
|
|||
#include "ibm.h"
|
||||
#include "mem.h"
|
||||
#include "ps2_mca.h"
|
||||
#include "rom.h"
|
||||
#include "lpt.h"
|
||||
#include "mca.h"
|
||||
|
||||
//static uint8_t ps2_92, ps2_94, ps2_102, ps2_103, ps2_104, ps2_105, ps2_190;
|
||||
|
||||
/*static struct
|
||||
{
|
||||
uint8_t status, int_status;
|
||||
uint8_t attention, ctrl;
|
||||
} ps2_hd;*/
|
||||
|
||||
static struct
|
||||
{
|
||||
uint8_t adapter_setup;
|
||||
uint8_t option[4];
|
||||
uint8_t pos_vga;
|
||||
uint8_t setup;
|
||||
uint8_t sys_ctrl_port_a;
|
||||
uint8_t subaddr_lo, subaddr_hi;
|
||||
|
||||
uint8_t io_id;
|
||||
} ps2;
|
||||
|
||||
#define PS2_SETUP_IO 0x80
|
||||
#define PS2_SETUP_VGA 0x20
|
||||
|
||||
#define PS2_ADAPTER_SETUP 0x08
|
||||
|
||||
uint8_t ps2_mca_read(uint16_t port, void *p)
|
||||
{
|
||||
uint8_t temp;
|
||||
|
||||
switch (port)
|
||||
{
|
||||
case 0x91:
|
||||
fatal("Read 91 setup=%02x adapter=%02x\n", ps2.setup, ps2.adapter_setup);
|
||||
case 0x92:
|
||||
temp = ps2.sys_ctrl_port_a;
|
||||
break;
|
||||
case 0x94:
|
||||
temp = ps2.setup;
|
||||
break;
|
||||
case 0x96:
|
||||
temp = ps2.adapter_setup | 0x70;
|
||||
break;
|
||||
case 0x100:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.io_id;
|
||||
else if (!(ps2.setup & PS2_SETUP_VGA))
|
||||
temp = 0xfd;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x101:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = 0xfb;
|
||||
else if (!(ps2.setup & PS2_SETUP_VGA))
|
||||
temp = 0xef;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x102:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.option[0];
|
||||
else if (!(ps2.setup & PS2_SETUP_VGA))
|
||||
temp = ps2.pos_vga;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x103:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.option[1];
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x104:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.option[2];
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x105:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.option[3];
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x106:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.subaddr_lo;
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
case 0x107:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
temp = ps2.subaddr_hi;
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
temp = mca_read(port);
|
||||
else
|
||||
temp = 0xff;
|
||||
break;
|
||||
|
||||
default:
|
||||
temp = 0xff;
|
||||
break;
|
||||
}
|
||||
|
||||
// pclog("ps2_read: port=%04x temp=%02x\n", port, temp);
|
||||
|
||||
return temp;
|
||||
}
|
||||
|
||||
static void ps2_mca_write(uint16_t port, uint8_t val, void *p)
|
||||
{
|
||||
// pclog("ps2_write: port=%04x val=%02x\n", port, val);
|
||||
|
||||
switch (port)
|
||||
{
|
||||
case 0x0092:
|
||||
if ((val & 1) && !(ps2.sys_ctrl_port_a & 1))
|
||||
{
|
||||
softresetx86();
|
||||
cpu_set_edx();
|
||||
}
|
||||
ps2.sys_ctrl_port_a = val;
|
||||
mem_a20_alt = val & 2;
|
||||
mem_a20_recalc();
|
||||
break;
|
||||
case 0x94:
|
||||
ps2.setup = val;
|
||||
break;
|
||||
case 0x96:
|
||||
ps2.adapter_setup = val;
|
||||
mca_set_index(val & 7);
|
||||
break;
|
||||
case 0x100:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.io_id = val;
|
||||
else if ((ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x101:
|
||||
if ((ps2.setup & PS2_SETUP_VGA) && (ps2.setup & PS2_SETUP_VGA) && (ps2.adapter_setup & PS2_ADAPTER_SETUP))
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x102:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
{
|
||||
lpt1_remove();
|
||||
serial1_remove();
|
||||
if (val & 0x04)
|
||||
{
|
||||
if (val & 0x08)
|
||||
serial1_init(0x3f8, 4);
|
||||
else
|
||||
serial1_init(0x2f8, 3);
|
||||
}
|
||||
else
|
||||
serial1_remove();
|
||||
if (val & 0x10)
|
||||
{
|
||||
switch ((val >> 5) & 3)
|
||||
{
|
||||
case 0:
|
||||
lpt1_init(0x3bc);
|
||||
break;
|
||||
case 1:
|
||||
lpt1_init(0x378);
|
||||
break;
|
||||
case 2:
|
||||
lpt1_init(0x278);
|
||||
break;
|
||||
}
|
||||
}
|
||||
ps2.option[0] = val;
|
||||
}
|
||||
else if (!(ps2.setup & PS2_SETUP_VGA))
|
||||
ps2.pos_vga = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x103:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.option[1] = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x104:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.option[2] = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x105:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.option[3] = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x106:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.subaddr_lo = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
case 0x107:
|
||||
if (!(ps2.setup & PS2_SETUP_IO))
|
||||
ps2.subaddr_hi = val;
|
||||
else if (ps2.adapter_setup & PS2_ADAPTER_SETUP)
|
||||
mca_write(port, val);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void ps2_mca_board_init()
|
||||
{
|
||||
io_sethandler(0x0091, 0x0002, ps2_mca_read, NULL, NULL, ps2_mca_write, NULL, NULL, NULL);
|
||||
io_sethandler(0x0094, 0x0001, ps2_mca_read, NULL, NULL, ps2_mca_write, NULL, NULL, NULL);
|
||||
io_sethandler(0x0096, 0x0001, ps2_mca_read, NULL, NULL, ps2_mca_write, NULL, NULL, NULL);
|
||||
io_sethandler(0x0100, 0x0008, ps2_mca_read, NULL, NULL, ps2_mca_write, NULL, NULL, NULL);
|
||||
|
||||
ps2.setup = 0xff;
|
||||
|
||||
lpt1_remove();
|
||||
lpt2_remove();
|
||||
lpt1_init(0x3bc);
|
||||
|
||||
serial1_remove();
|
||||
serial2_remove();
|
||||
|
||||
ps2.io_id = 0xfb;
|
||||
|
||||
mem_remap_top_384k();
|
||||
|
||||
mca_init(4);
|
||||
}
|
||||
1
src/ps2_mca.h
Normal file
1
src/ps2_mca.h
Normal file
|
|
@ -0,0 +1 @@
|
|||
void ps2_mca_board_init();
|
||||
|
|
@ -296,6 +296,7 @@ void video_init()
|
|||
|
||||
case ROM_IBMPS1_2011:
|
||||
case ROM_IBMPS2_M30_286:
|
||||
case ROM_IBMPS2_M50:
|
||||
device_add(&ps1vga_device);
|
||||
return;
|
||||
|
||||
|
|
|
|||
|
|
@ -37,6 +37,39 @@ static int mouse_valid(int type, int model)
|
|||
return 1;
|
||||
}
|
||||
|
||||
static void recalc_snd_list(HWND hdlg, int model)
|
||||
{
|
||||
HWND h = GetDlgItem(hdlg, IDC_COMBOSND);
|
||||
int c = 0, d = 0;
|
||||
|
||||
SendMessage(h, CB_RESETCONTENT, 0, 0);
|
||||
|
||||
while (1)
|
||||
{
|
||||
char *s = sound_card_getname(c);
|
||||
|
||||
if (!s[0])
|
||||
break;
|
||||
|
||||
settings_sound_to_list[c] = d;
|
||||
|
||||
if (sound_card_available(c))
|
||||
{
|
||||
device_t *sound_dev = sound_card_getdevice(c);
|
||||
|
||||
if (!sound_dev || (sound_dev->flags & DEVICE_MCA) == (models[model].flags & MODEL_MCA))
|
||||
{
|
||||
SendMessage(h, CB_ADDSTRING, 0, (LPARAM)(LPCSTR)s);
|
||||
settings_list_to_sound[d] = c;
|
||||
d++;
|
||||
}
|
||||
}
|
||||
|
||||
c++;
|
||||
}
|
||||
SendMessage(h, CB_SETCURSEL, settings_sound_to_list[sound_card_current], 0);
|
||||
}
|
||||
|
||||
static void recalc_hdd_list(HWND hdlg, int model, int use_selected_hdd)
|
||||
{
|
||||
HWND h;
|
||||
|
|
@ -76,7 +109,8 @@ static void recalc_hdd_list(HWND hdlg, int model, int use_selected_hdd)
|
|||
s = hdd_controller_get_name(c);
|
||||
if (s[0] == 0)
|
||||
break;
|
||||
if ((hdd_controller_get_flags(c) & DEVICE_AT) && !(models[model].flags & MODEL_AT))
|
||||
if ((((hdd_controller_get_flags(c) & DEVICE_AT) && !(models[model].flags & MODEL_AT)) ||
|
||||
(hdd_controller_get_flags(c) & DEVICE_MCA) != (models[model].flags & MODEL_MCA)) && c)
|
||||
{
|
||||
c++;
|
||||
continue;
|
||||
|
|
@ -191,27 +225,7 @@ static BOOL CALLBACK config_dlgproc(HWND hdlg, UINT message, WPARAM wParam, LPAR
|
|||
EnableWindow(h, TRUE);
|
||||
SendMessage(h, CB_SETCURSEL, cpu, 0);
|
||||
|
||||
h = GetDlgItem(hdlg, IDC_COMBOSND);
|
||||
c = d = 0;
|
||||
while (1)
|
||||
{
|
||||
char *s = sound_card_getname(c);
|
||||
|
||||
if (!s[0])
|
||||
break;
|
||||
|
||||
settings_sound_to_list[c] = d;
|
||||
|
||||
if (sound_card_available(c))
|
||||
{
|
||||
SendMessage(h, CB_ADDSTRING, 0, (LPARAM)(LPCSTR)s);
|
||||
settings_list_to_sound[d] = c;
|
||||
d++;
|
||||
}
|
||||
|
||||
c++;
|
||||
}
|
||||
SendMessage(h, CB_SETCURSEL, settings_sound_to_list[sound_card_current], 0);
|
||||
recalc_snd_list(hdlg, romstomodel[romset]);
|
||||
|
||||
h=GetDlgItem(hdlg, IDC_CHECK3);
|
||||
SendMessage(h, BM_SETCHECK, GAMEBLASTER, 0);
|
||||
|
|
@ -629,6 +643,7 @@ static BOOL CALLBACK config_dlgproc(HWND hdlg, UINT message, WPARAM wParam, LPAR
|
|||
|
||||
recalc_hdd_list(hdlg, temp_model, 1);
|
||||
|
||||
recalc_snd_list(hdlg, temp_model);
|
||||
}
|
||||
break;
|
||||
case IDC_COMBOCPUM:
|
||||
|
|
|
|||
Loading…
Reference in a new issue