Fixes for FDC and AT keyboard (showing when running AT&T System V/386 R3.2 UNIX.)
Added memory context dumping for debugging.
This commit is contained in:
@@ -9,7 +9,7 @@
|
|||||||
* Implementation of the NEC uPD-765 and compatible floppy disk
|
* Implementation of the NEC uPD-765 and compatible floppy disk
|
||||||
* controller.
|
* controller.
|
||||||
*
|
*
|
||||||
* Version: @(#)fdc.c 1.0.13 2018/05/14
|
* Version: @(#)fdc.c 1.0.14 2018/06/25
|
||||||
*
|
*
|
||||||
* Authors: Miran Grca, <mgrca8@gmail.com>
|
* Authors: Miran Grca, <mgrca8@gmail.com>
|
||||||
* Sarah Walker, <tommowalker@tommowalker.co.uk>
|
* Sarah Walker, <tommowalker@tommowalker.co.uk>
|
||||||
|
|||||||
@@ -10,7 +10,7 @@
|
|||||||
* data in the form of FM/MFM-encoded transitions) which also
|
* data in the form of FM/MFM-encoded transitions) which also
|
||||||
* forms the core of the emulator's floppy disk emulation.
|
* forms the core of the emulator's floppy disk emulation.
|
||||||
*
|
*
|
||||||
* Version: @(#)fdd_86f.c 1.0.10 2018/05/06
|
* Version: @(#)fdd_86f.c 1.0.11 2018/06/25
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -1566,6 +1566,12 @@ d86f_read_sector_data(int drive, int side)
|
|||||||
dev->data_find.bytes_obtained++;
|
dev->data_find.bytes_obtained++;
|
||||||
|
|
||||||
if (dev->data_find.bytes_obtained == (crc_pos + fdc_get_gap(d86f_fdc))) {
|
if (dev->data_find.bytes_obtained == (crc_pos + fdc_get_gap(d86f_fdc))) {
|
||||||
|
#if 0
|
||||||
|
/*
|
||||||
|
* This code causes errors on Wyse UNIX
|
||||||
|
* System V/386 V3.2.1A and was disabled
|
||||||
|
* at Miran Grca's request. --FvK
|
||||||
|
*/
|
||||||
/* We've got the data. */
|
/* We've got the data. */
|
||||||
if (dev->dma_over > 1) {
|
if (dev->dma_over > 1) {
|
||||||
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
||||||
@@ -1579,6 +1585,7 @@ d86f_read_sector_data(int drive, int side)
|
|||||||
dev->data_find.bits_obtained++;
|
dev->data_find.bits_obtained++;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if ((dev->calc_crc.word != dev->track_crc.word) && (dev->state != STATE_02_READ_DATA)) {
|
if ((dev->calc_crc.word != dev->track_crc.word) && (dev->state != STATE_02_READ_DATA)) {
|
||||||
d86f_log("86F: Data CRC error: %04X != %04X (%08X)\n", dev->track_crc.word, dev->calc_crc.word, dev->last_sector.dword);
|
d86f_log("86F: Data CRC error: %04X != %04X (%08X)\n", dev->track_crc.word, dev->calc_crc.word, dev->last_sector.dword);
|
||||||
@@ -1700,6 +1707,12 @@ d86f_write_sector_data(int drive, int side, int mfm, uint16_t am)
|
|||||||
dev->data_find.bytes_obtained++;
|
dev->data_find.bytes_obtained++;
|
||||||
|
|
||||||
if (dev->data_find.bytes_obtained == (crc_pos + fdc_get_gap(d86f_fdc))) {
|
if (dev->data_find.bytes_obtained == (crc_pos + fdc_get_gap(d86f_fdc))) {
|
||||||
|
#if 0
|
||||||
|
/*
|
||||||
|
* This code causes errors on Wyse UNIX
|
||||||
|
* System V/386 V3.2.1A and was disabled
|
||||||
|
* at Miran Grca's request. --FvK
|
||||||
|
*/
|
||||||
if (dev->dma_over > 1) {
|
if (dev->dma_over > 1) {
|
||||||
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
||||||
dev->error_condition = 0;
|
dev->error_condition = 0;
|
||||||
@@ -1710,6 +1723,7 @@ d86f_write_sector_data(int drive, int side, int mfm, uint16_t am)
|
|||||||
dev->data_find.bits_obtained++;
|
dev->data_find.bits_obtained++;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/* We've written the data. */
|
/* We've written the data. */
|
||||||
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
||||||
@@ -2139,6 +2153,12 @@ d86f_turbo_read(int drive, int side)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
/*
|
||||||
|
* This code causes errors on Wyse UNIX
|
||||||
|
* System V/386 V3.2.1A and was disabled
|
||||||
|
* at Miran Grca's request. --FvK
|
||||||
|
*/
|
||||||
if (dev->dma_over > 1) {
|
if (dev->dma_over > 1) {
|
||||||
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
dev->data_find.sync_marks = dev->data_find.bits_obtained = dev->data_find.bytes_obtained = 0;
|
||||||
dev->error_condition = 0;
|
dev->error_condition = 0;
|
||||||
@@ -2147,6 +2167,7 @@ d86f_turbo_read(int drive, int side)
|
|||||||
fdc_overrun(d86f_fdc);
|
fdc_overrun(d86f_fdc);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if (dev->turbo_pos >= (128 << dev->last_sector.id.n)) {
|
if (dev->turbo_pos >= (128 << dev->last_sector.id.n)) {
|
||||||
/* CRC is valid. */
|
/* CRC is valid. */
|
||||||
|
|||||||
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Intel 8042 (AT keyboard controller) emulation.
|
* Intel 8042 (AT keyboard controller) emulation.
|
||||||
*
|
*
|
||||||
* Version: @(#)keyboard_at.c 1.0.12 2018/05/06
|
* Version: @(#)keyboard_at.c 1.0.13 2018/06/26
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -84,7 +84,7 @@
|
|||||||
#define CCB_ENABLEKINT 0x01
|
#define CCB_ENABLEKINT 0x01
|
||||||
|
|
||||||
#define CCB_MASK 0x68
|
#define CCB_MASK 0x68
|
||||||
#define MODE_MASK 0x6C
|
#define MODE_MASK 0x6c
|
||||||
|
|
||||||
#define KBC_TYPE_ISA 0x00
|
#define KBC_TYPE_ISA 0x00
|
||||||
#define KBC_TYPE_PS2_1 0x01
|
#define KBC_TYPE_PS2_1 0x01
|
||||||
@@ -94,9 +94,9 @@
|
|||||||
#define KBC_VEN_GENERIC 0x00
|
#define KBC_VEN_GENERIC 0x00
|
||||||
#define KBC_VEN_AMI 0x04
|
#define KBC_VEN_AMI 0x04
|
||||||
#define KBC_VEN_IBM_MCA 0x08
|
#define KBC_VEN_IBM_MCA 0x08
|
||||||
#define KBC_VEN_QUADTEL 0x0C
|
#define KBC_VEN_QUADTEL 0x0c
|
||||||
#define KBC_VEN_TOSHIBA 0x10
|
#define KBC_VEN_TOSHIBA 0x10
|
||||||
#define KBC_VEN_MASK 0x1C
|
#define KBC_VEN_MASK 0x1c
|
||||||
|
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
@@ -168,38 +168,38 @@ static atkbd_t *CurrentKbd = NULL; // FIXME: remove!!! --FvK
|
|||||||
|
|
||||||
/* Non-translated to translated scan codes. */
|
/* Non-translated to translated scan codes. */
|
||||||
static const uint8_t nont_to_t[256] = {
|
static const uint8_t nont_to_t[256] = {
|
||||||
0xFF, 0x43, 0x41, 0x3F, 0x3D, 0x3B, 0x3C, 0x58,
|
0xff, 0x43, 0x41, 0x3f, 0x3d, 0x3b, 0x3c, 0x58,
|
||||||
0x64, 0x44, 0x42, 0x40, 0x3E, 0x0F, 0x29, 0x59,
|
0x64, 0x44, 0x42, 0x40, 0x3e, 0x0f, 0x29, 0x59,
|
||||||
0x65, 0x38, 0x2A, 0x70, 0x1D, 0x10, 0x02, 0x5A,
|
0x65, 0x38, 0x2a, 0x70, 0x1d, 0x10, 0x02, 0x5a,
|
||||||
0x66, 0x71, 0x2C, 0x1F, 0x1E, 0x11, 0x03, 0x5B,
|
0x66, 0x71, 0x2c, 0x1f, 0x1e, 0x11, 0x03, 0x5b,
|
||||||
0x67, 0x2E, 0x2D, 0x20, 0x12, 0x05, 0x04, 0x5C,
|
0x67, 0x2e, 0x2d, 0x20, 0x12, 0x05, 0x04, 0x5c,
|
||||||
0x68, 0x39, 0x2F, 0x21, 0x14, 0x13, 0x06, 0x5D,
|
0x68, 0x39, 0x2f, 0x21, 0x14, 0x13, 0x06, 0x5d,
|
||||||
0x69, 0x31, 0x30, 0x23, 0x22, 0x15, 0x07, 0x5E,
|
0x69, 0x31, 0x30, 0x23, 0x22, 0x15, 0x07, 0x5e,
|
||||||
0x6A, 0x72, 0x32, 0x24, 0x16, 0x08, 0x09, 0x5F,
|
0x6a, 0x72, 0x32, 0x24, 0x16, 0x08, 0x09, 0x5f,
|
||||||
0x6B, 0x33, 0x25, 0x17, 0x18, 0x0B, 0x0A, 0x60,
|
0x6b, 0x33, 0x25, 0x17, 0x18, 0x0b, 0x0a, 0x60,
|
||||||
0x6C, 0x34, 0x35, 0x26, 0x27, 0x19, 0x0C, 0x61,
|
0x6c, 0x34, 0x35, 0x26, 0x27, 0x19, 0x0c, 0x61,
|
||||||
0x6D, 0x73, 0x28, 0x74, 0x1A, 0x0D, 0x62, 0x6E,
|
0x6d, 0x73, 0x28, 0x74, 0x1a, 0x0d, 0x62, 0x6e,
|
||||||
0x3A, 0x36, 0x1C, 0x1B, 0x75, 0x2B, 0x63, 0x76,
|
0x3a, 0x36, 0x1c, 0x1b, 0x75, 0x2b, 0x63, 0x76,
|
||||||
0x55, 0x56, 0x77, 0x78, 0x79, 0x7A, 0x0E, 0x7B,
|
0x55, 0x56, 0x77, 0x78, 0x79, 0x7a, 0x0e, 0x7b,
|
||||||
0x7C, 0x4F, 0x7D, 0x4B, 0x47, 0x7E, 0x7F, 0x6F,
|
0x7c, 0x4f, 0x7d, 0x4b, 0x47, 0x7e, 0x7f, 0x6f,
|
||||||
0x52, 0x53, 0x50, 0x4C, 0x4D, 0x48, 0x01, 0x45,
|
0x52, 0x53, 0x50, 0x4c, 0x4d, 0x48, 0x01, 0x45,
|
||||||
0x57, 0x4E, 0x51, 0x4A, 0x37, 0x49, 0x46, 0x54,
|
0x57, 0x4e, 0x51, 0x4a, 0x37, 0x49, 0x46, 0x54,
|
||||||
0x80, 0x81, 0x82, 0x41, 0x54, 0x85, 0x86, 0x87,
|
0x80, 0x81, 0x82, 0x41, 0x54, 0x85, 0x86, 0x87,
|
||||||
0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F,
|
0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
|
||||||
0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
|
0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
|
||||||
0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F,
|
0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
|
||||||
0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7,
|
0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
|
||||||
0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF,
|
0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
|
||||||
0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7,
|
0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
|
||||||
0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF,
|
0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
|
||||||
0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7,
|
0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
|
||||||
0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF,
|
0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
|
||||||
0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7,
|
0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
|
||||||
0xD8, 0xD9, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF,
|
0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
|
||||||
0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7,
|
0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
|
||||||
0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF,
|
0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
|
||||||
0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7,
|
0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
|
||||||
0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF
|
0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
|
||||||
};
|
};
|
||||||
|
|
||||||
static const scancode scancode_set1[512] = {
|
static const scancode scancode_set1[512] = {
|
||||||
@@ -742,7 +742,7 @@ kbd_adddata_keyboard(uint16_t val)
|
|||||||
/* Allow for scan code translation. */
|
/* Allow for scan code translation. */
|
||||||
if (translate && (val == 0xf0)) {
|
if (translate && (val == 0xf0)) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Translate is on, F0 prefix detected\n");
|
kbd_log("ATkbd: translate is on, F0 prefix detected\n");
|
||||||
#endif
|
#endif
|
||||||
sc_or = 0x80;
|
sc_or = 0x80;
|
||||||
return;
|
return;
|
||||||
@@ -751,7 +751,7 @@ kbd_adddata_keyboard(uint16_t val)
|
|||||||
/* Skip break code if translated make code has bit 7 set. */
|
/* Skip break code if translated make code has bit 7 set. */
|
||||||
if (translate && (sc_or == 0x80) && (val & 0x80)) {
|
if (translate && (sc_or == 0x80) && (val & 0x80)) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Translate is on, skipping scan code: %02X (original: F0 %02X)\n", nont_to_t[val], val);
|
kbd_log("ATkbd: translate is on, skipping scan code: %02X (original: F0 %02X)\n", nont_to_t[val], val);
|
||||||
#endif
|
#endif
|
||||||
sc_or = 0;
|
sc_or = 0;
|
||||||
return;
|
return;
|
||||||
@@ -779,7 +779,7 @@ kbd_adddata_keyboard(uint16_t val)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Translate is %s, ", translate ? "on" : "off");
|
kbd_log("ATkbd: translate is %s, ", translate ? "on" : "off");
|
||||||
#endif
|
#endif
|
||||||
switch(val) {
|
switch(val) {
|
||||||
case FAKE_LSHIFT_ON:
|
case FAKE_LSHIFT_ON:
|
||||||
@@ -949,7 +949,7 @@ static void
|
|||||||
kbd_output_write(atkbd_t *kbd, uint8_t val)
|
kbd_output_write(atkbd_t *kbd, uint8_t val)
|
||||||
{
|
{
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Write output port: %02X (old: %02X)\n", val, kbd->output_port);
|
kbd_log("ATkbd: write output port: %02X (old: %02X)\n", val, kbd->output_port);
|
||||||
#endif
|
#endif
|
||||||
if ((kbd->output_port ^ val) & 0x20) { /*IRQ 12*/
|
if ((kbd->output_port ^ val) & 0x20) { /*IRQ 12*/
|
||||||
if (val & 0x20)
|
if (val & 0x20)
|
||||||
@@ -983,7 +983,7 @@ static void
|
|||||||
kbd_cmd_write(atkbd_t *kbd, uint8_t val)
|
kbd_cmd_write(atkbd_t *kbd, uint8_t val)
|
||||||
{
|
{
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Write command byte: %02X (old: %02X)\n", val, kbd->mem[0]);
|
kbd_log("ATkbd: write command byte: %02X (old: %02X)\n", val, kbd->mem[0]);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if ((val & 1) && (kbd->status & STAT_OFULL))
|
if ((val & 1) && (kbd->status & STAT_OFULL))
|
||||||
@@ -1003,7 +1003,7 @@ kbd_cmd_write(atkbd_t *kbd, uint8_t val)
|
|||||||
|
|
||||||
keyboard_scan = !(val & 0x10);
|
keyboard_scan = !(val & 0x10);
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: keyboard is now %s\n", mouse_scan ? "enabled" : "disabled");
|
kbd_log("ATkbd: keyboard is now %s\n", keyboard_scan ? "enabled" : "disabled");
|
||||||
kbd_log("ATkbd: keyboard interrupt is now %s\n", (val & 0x01) ? "enabled" : "disabled");
|
kbd_log("ATkbd: keyboard interrupt is now %s\n", (val & 0x01) ? "enabled" : "disabled");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -1049,6 +1049,12 @@ kbd_keyboard_set(atkbd_t *kbd, uint8_t enable)
|
|||||||
{
|
{
|
||||||
kbd->mem[0] &= 0xef;
|
kbd->mem[0] &= 0xef;
|
||||||
kbd->mem[0] |= (enable ? 0x00 : 0x10);
|
kbd->mem[0] |= (enable ? 0x00 : 0x10);
|
||||||
|
|
||||||
|
if (enable)
|
||||||
|
kbd->status |= STAT_LOCK;
|
||||||
|
else
|
||||||
|
kbd->status &= ~STAT_LOCK;
|
||||||
|
|
||||||
keyboard_scan = enable;
|
keyboard_scan = enable;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1194,7 +1200,7 @@ kbd_write60_ami(void *p, uint8_t val)
|
|||||||
case 0x58: case 0x59: case 0x5a: case 0x5b:
|
case 0x58: case 0x59: case 0x5a: case 0x5b:
|
||||||
case 0x5c: case 0x5d: case 0x5e: case 0x5f:
|
case 0x5c: case 0x5d: case 0x5e: case 0x5f:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - alias write to register %08X\n", kbd->command);
|
kbd_log("ATkbd: AMI - alias write to %08X\n", kbd->command);
|
||||||
#endif
|
#endif
|
||||||
kbd->mem[kbd->command & 0x1f] = val;
|
kbd->mem[kbd->command & 0x1f] = val;
|
||||||
if (kbd->command == 0x60)
|
if (kbd->command == 0x60)
|
||||||
@@ -1203,7 +1209,7 @@ kbd_write60_ami(void *p, uint8_t val)
|
|||||||
|
|
||||||
case 0xaf: /*AMI - set extended controller RAM*/
|
case 0xaf: /*AMI - set extended controller RAM*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - set extended controller RAM\n");
|
kbd_log("ATkbd: AMI - set extended controller RAM\n");
|
||||||
#endif
|
#endif
|
||||||
if (kbd->secr_phase == 1) {
|
if (kbd->secr_phase == 1) {
|
||||||
kbd->mem_addr = val;
|
kbd->mem_addr = val;
|
||||||
@@ -1214,9 +1220,10 @@ kbd_write60_ami(void *p, uint8_t val)
|
|||||||
kbd->secr_phase = 0;
|
kbd->secr_phase = 0;
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xcb: /*AMI - set keyboard mode*/
|
case 0xcb: /*AMI - set keyboard mode*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - set keyboard mode\n");
|
kbd_log("ATkbd: AMI - set keyboard mode\n");
|
||||||
#endif
|
#endif
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -1240,7 +1247,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0x18: case 0x19: case 0x1a: case 0x1b:
|
case 0x18: case 0x19: case 0x1a: case 0x1b:
|
||||||
case 0x1c: case 0x1d: case 0x1e: case 0x1f:
|
case 0x1c: case 0x1d: case 0x1e: case 0x1f:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - alias read from register %08X\n", val);
|
kbd_log("ATkbd: AMI - alias read from %08X\n", val);
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata(kbd->mem[val]);
|
kbd_adddata(kbd->mem[val]);
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1254,21 +1261,21 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0x58: case 0x59: case 0x5a: case 0x5b:
|
case 0x58: case 0x59: case 0x5a: case 0x5b:
|
||||||
case 0x5c: case 0x5d: case 0x5e: case 0x5f:
|
case 0x5c: case 0x5d: case 0x5e: case 0x5f:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - alias write to register %08X\n", kbd->command);
|
kbd_log("ATkbd: AMI - alias write to %08X\n", kbd->command);
|
||||||
#endif
|
#endif
|
||||||
kbd->want60 = 1;
|
kbd->want60 = 1;
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xa1: /*AMI - get controller version*/
|
case 0xa1: /*AMI - get controller version*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - get controller version\n");
|
kbd_log("ATkbd: AMI - get controller version\n");
|
||||||
#endif
|
#endif
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xa2: /*AMI - reset keyboard controller lines P22 and P23 low*/
|
case 0xa2: /*AMI - reset keyboard controller lines P22 and P23 low*/
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - reset keyboard controller lines P22 and P23 low\n");
|
kbd_log("ATkbd: AMI - clear KBC lines P22 and P23\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_output_write(kbd, kbd->output_port & 0xf3);
|
kbd_output_write(kbd, kbd->output_port & 0xf3);
|
||||||
kbd_adddata(0x00);
|
kbd_adddata(0x00);
|
||||||
@@ -1279,7 +1286,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa3: /*AMI - set keyboard controller lines P22 and P23 high*/
|
case 0xa3: /*AMI - set keyboard controller lines P22 and P23 high*/
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - set keyboard controller lines P22 and P23 high\n");
|
kbd_log("ATkbd: AMI - set KBC lines P22 and P23\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_output_write(kbd, kbd->output_port | 0x0c);
|
kbd_output_write(kbd, kbd->output_port | 0x0c);
|
||||||
kbd_adddata(0x00);
|
kbd_adddata(0x00);
|
||||||
@@ -1290,7 +1297,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa4: /* AMI - write clock = low */
|
case 0xa4: /* AMI - write clock = low */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - write clock = low\n");
|
kbd_log("ATkbd: AMI - write clock = low\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->ami_stat &= 0xfe;
|
kbd->ami_stat &= 0xfe;
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1300,16 +1307,17 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa5: /* AMI - write clock = high */
|
case 0xa5: /* AMI - write clock = high */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - write clock = high\n");
|
kbd_log("ATkbd: AMI - write clock = high\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->ami_stat |= 0x01;
|
kbd->ami_stat |= 0x01;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xa6: /* AMI - read clock */
|
case 0xa6: /* AMI - read clock */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - read clock\n");
|
kbd_log("ATkbd: AMI - read clock\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata(!!(kbd->ami_stat & 1));
|
kbd_adddata(!!(kbd->ami_stat & 1));
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1319,7 +1327,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa7: /* AMI - write cache bad */
|
case 0xa7: /* AMI - write cache bad */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - write cache bad\n");
|
kbd_log("ATkbd: AMI - write cache bad\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->ami_stat &= 0xfd;
|
kbd->ami_stat &= 0xfd;
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1329,7 +1337,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa8: /* AMI - write cache good */
|
case 0xa8: /* AMI - write cache good */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - write cache good\n");
|
kbd_log("ATkbd: AMI - write cache good\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->ami_stat |= 0x02;
|
kbd->ami_stat |= 0x02;
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1339,7 +1347,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
case 0xa9: /* AMI - read cache */
|
case 0xa9: /* AMI - read cache */
|
||||||
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
if ((kbd->flags & KBC_TYPE_MASK) < KBC_TYPE_PS2_1) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - read cache\n");
|
kbd_log("ATkbd: AMI - read cache\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata(!!(kbd->ami_stat & 2));
|
kbd_adddata(!!(kbd->ami_stat & 2));
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1386,7 +1394,7 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
(allow command D1 to change bits 2 and 3 of the output
|
(allow command D1 to change bits 2 and 3 of the output
|
||||||
port)*/
|
port)*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - unblock keyboard controller lines P22 and P23\n");
|
kbd_log("ATkbd: AMI - unblock KBC lines P22 and P23\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->output_locked = 1;
|
kbd->output_locked = 1;
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1395,28 +1403,28 @@ kbd_write64_ami(void *p, uint8_t val)
|
|||||||
(prevent command D1 from changing bits 2 and 3 of the
|
(prevent command D1 from changing bits 2 and 3 of the
|
||||||
output port)*/
|
output port)*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - block keyboard controller lines P22 and P23\n");
|
kbd_log("ATkbd: AMI - block KBC lines P22 and P23\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->output_locked = 1;
|
kbd->output_locked = 1;
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xca: /*AMI - read keyboard mode*/
|
case 0xca: /*AMI - read keyboard mode*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - read keyboard mode\n");
|
kbd_log("ATkbd: AMI - read keyboard mode\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata(0x00); /*ISA mode*/
|
kbd_adddata(0x00); /*ISA mode*/
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xcb: /*AMI - set keyboard mode*/
|
case 0xcb: /*AMI - set keyboard mode*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("AMI - set keyboard mode\n");
|
kbd_log("ATkbd: AMI - set keyboard mode\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->want60 = 1;
|
kbd->want60 = 1;
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xef: /*??? - sent by AMI486*/
|
case 0xef: /*??? - sent by AMI486*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("??? - sent by AMI486\n");
|
kbd_log("ATkbd: ??? - sent by AMI486\n");
|
||||||
#endif
|
#endif
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -1449,7 +1457,7 @@ kbd_write64_ibm_mca(void *p, uint8_t val)
|
|||||||
|
|
||||||
case 0xaf:
|
case 0xaf:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: bad kbc command AF\n");
|
kbd_log("ATkbd: bad KBC command AF\n");
|
||||||
#endif
|
#endif
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
@@ -1476,7 +1484,7 @@ kbd_write60_quadtel(void *p, uint8_t val)
|
|||||||
switch(kbd->command) {
|
switch(kbd->command) {
|
||||||
case 0xcf: /*??? - sent by MegaPC BIOS*/
|
case 0xcf: /*??? - sent by MegaPC BIOS*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("??? - sent by MegaPC BIOS\n");
|
kbd_log("ATkbd: ??? - sent by MegaPC BIOS\n");
|
||||||
#endif
|
#endif
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -1493,13 +1501,13 @@ kbd_write64_quadtel(void *p, uint8_t val)
|
|||||||
switch (val) {
|
switch (val) {
|
||||||
case 0xaf:
|
case 0xaf:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: bad kbc command AF\n");
|
kbd_log("ATkbd: bad KBC command AF\n");
|
||||||
#endif
|
#endif
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
case 0xcf: /*??? - sent by MegaPC BIOS*/
|
case 0xcf: /*??? - sent by MegaPC BIOS*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("??? - sent by MegaPC BIOS\n");
|
kbd_log("ATkbd: ??? - sent by MegaPC BIOS\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->want60 = 1;
|
kbd->want60 = 1;
|
||||||
return 0;
|
return 0;
|
||||||
@@ -1515,7 +1523,7 @@ kbd_write60_toshiba(void *p, uint8_t val)
|
|||||||
atkbd_t *kbd = (atkbd_t *) p;
|
atkbd_t *kbd = (atkbd_t *) p;
|
||||||
|
|
||||||
switch(kbd->command) {
|
switch(kbd->command) {
|
||||||
case 0xb6: /* T3100e - set colour/mono switch */
|
case 0xb6: /* T3100e - set color/mono switch */
|
||||||
t3100e_mono_set(val);
|
t3100e_mono_set(val);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -1532,7 +1540,7 @@ kbd_write64_toshiba(void *p, uint8_t val)
|
|||||||
switch (val) {
|
switch (val) {
|
||||||
case 0xaf:
|
case 0xaf:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: bad kbc command AF\n");
|
kbd_log("ATkbd: bad KBC command AF\n");
|
||||||
#endif
|
#endif
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
@@ -1589,7 +1597,7 @@ kbd_write64_toshiba(void *p, uint8_t val)
|
|||||||
|
|
||||||
/* The T3100e returns all bits set except bit 6 which
|
/* The T3100e returns all bits set except bit 6 which
|
||||||
* is set by t3100e_mono_set() */
|
* is set by t3100e_mono_set() */
|
||||||
kbd->input_port = (t3100e_mono_get() & 1) ? 0xFF : 0xBF;
|
kbd->input_port = (t3100e_mono_get() & 1) ? 0xff : 0xbf;
|
||||||
kbd_adddata(kbd->input_port);
|
kbd_adddata(kbd->input_port);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
@@ -1610,6 +1618,9 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
if (romset == ROM_XI8088 && port == 0x63)
|
if (romset == ROM_XI8088 && port == 0x63)
|
||||||
port = 0x61;
|
port = 0x61;
|
||||||
|
|
||||||
|
#ifdef _DEBUG
|
||||||
|
kbd_log("ATkbd: write(%04X, %02X)\n", port, val);
|
||||||
|
#endif
|
||||||
switch (port) {
|
switch (port) {
|
||||||
case 0x60:
|
case 0x60:
|
||||||
if (kbd->want60) {
|
if (kbd->want60) {
|
||||||
@@ -1631,7 +1642,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
|
|
||||||
case 0xd1: /*Write output port*/
|
case 0xd1: /*Write output port*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
// kbd_log("Write output port\n");
|
// kbd_log("ATkbd: write output port\n");
|
||||||
#endif
|
#endif
|
||||||
if (kbd->output_locked) {
|
if (kbd->output_locked) {
|
||||||
/*If keyboard controller lines P22-P23 are blocked,
|
/*If keyboard controller lines P22-P23 are blocked,
|
||||||
@@ -1666,7 +1677,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
mouse_write(val, mouse_p);
|
mouse_write(val, mouse_p);
|
||||||
else if (!mouse_write && ((kbd->flags & KBC_TYPE_MASK) >= KBC_TYPE_PS2_1)) {
|
else if (!mouse_write && ((kbd->flags & KBC_TYPE_MASK) >= KBC_TYPE_PS2_1)) {
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
pclog("Adding 0xFF to queue\n");
|
kbd_log("ATkbd: adding 0xFF to queue\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_at_adddata_mouse(0xff);
|
keyboard_at_adddata_mouse(0xff);
|
||||||
}
|
}
|
||||||
@@ -1718,9 +1729,15 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#endif
|
#endif
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Keyboard command is now done. */
|
||||||
|
kbd->key_command = 0x00;
|
||||||
} else {
|
} else {
|
||||||
kbd->key_command = val;
|
/* No keyboard command in progress. */
|
||||||
|
kbd->key_command = 0x00;
|
||||||
|
|
||||||
kbd_keyboard_set(kbd, 1);
|
kbd_keyboard_set(kbd, 1);
|
||||||
|
|
||||||
switch (val) {
|
switch (val) {
|
||||||
case 0x00:
|
case 0x00:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
@@ -1731,7 +1748,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
|
|
||||||
case 0x05: /*??? - sent by NT 4.0*/
|
case 0x05: /*??? - sent by NT 4.0*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: nt 4.0 command fe\n");
|
kbd_log("ATkbd: NT4.0 command FE\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata_keyboard(0xfe);
|
kbd_adddata_keyboard(0xfe);
|
||||||
break;
|
break;
|
||||||
@@ -1739,7 +1756,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
case 0x71: /*These two commands are sent by Pentium-era AMI BIOS'es.*/
|
case 0x71: /*These two commands are sent by Pentium-era AMI BIOS'es.*/
|
||||||
case 0x82:
|
case 0x82:
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: pentium-era ami bios command %02x\n", val);
|
kbd_log("ATkbd: Pentium-era AMI BIOS command %02X\n", val);
|
||||||
#endif
|
#endif
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1747,20 +1764,22 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set/reset leds\n");
|
kbd_log("ATkbd: set/reset leds\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->key_wantdata = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
|
||||||
|
kbd->key_wantdata = 1;
|
||||||
|
kbd->key_command = val;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xee: /*Diagnostic echo*/
|
case 0xee: /*Diagnostic echo*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: diagnostic echo\n");
|
kbd_log("ATkbd: ECHO\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_adddata_keyboard(0xee);
|
kbd_adddata_keyboard(0xee);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xef: /*NOP (No OPeration). Reserved for future use.*/
|
case 0xef: /*NOP (No OPeration). Reserved for future use.*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: kbd nop\n");
|
kbd_log("ATkbd: NOP\n");
|
||||||
#endif
|
#endif
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1768,8 +1787,9 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: scan code set\n");
|
kbd_log("ATkbd: scan code set\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->key_wantdata = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
kbd->key_wantdata = 1;
|
||||||
|
kbd->key_command = val;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf2: /*Read ID*/
|
case 0xf2: /*Read ID*/
|
||||||
@@ -1786,35 +1806,37 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set typematic rate/delay\n");
|
kbd_log("ATkbd: set typematic rate/delay\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->key_wantdata = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
kbd->key_wantdata = 1;
|
||||||
|
kbd->key_command = val;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf4: /*Enable keyboard*/
|
case 0xf4: /*Enable keyboard*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: enable keyboard via keyboard\n");
|
kbd_log("ATkbd: enable keyboard via keyboard\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_scan = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
keyboard_scan = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf5: /*Disable keyboard*/
|
case 0xf5: /*Disable keyboard*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: disable keyboard via keyboard\n");
|
kbd_log("ATkbd: disable keyboard via keyboard\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_scan = 0;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
keyboard_scan = 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf6: /*Set defaults*/
|
case 0xf6: /*Set defaults*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set defaults\n");
|
kbd_log("ATkbd: set defaults\n");
|
||||||
#endif
|
#endif
|
||||||
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
|
||||||
keyboard_set3_all_break = 0;
|
keyboard_set3_all_break = 0;
|
||||||
keyboard_set3_all_repeat = 0;
|
keyboard_set3_all_repeat = 0;
|
||||||
memset(keyboard_set3_flags, 0, 512);
|
memset(keyboard_set3_flags, 0, 512);
|
||||||
keyboard_mode = (keyboard_mode & 0xFC) | 0x02;
|
keyboard_mode = (keyboard_mode & 0xFC) | 0x02;
|
||||||
kbd_adddata_keyboard(0xfa);
|
|
||||||
kbd_setmap(kbd);
|
kbd_setmap(kbd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1822,33 +1844,33 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set all keys to repeat\n");
|
kbd_log("ATkbd: set all keys to repeat\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_set3_all_break = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
keyboard_set3_all_break = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf8: /*Set all keys to give make/break codes*/
|
case 0xf8: /*Set all keys to give make/break codes*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set all keys to give make/break codes\n");
|
kbd_log("ATkbd: set all keys to give make/break codes\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_set3_all_break = 1;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
keyboard_set3_all_break = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xf9: /*Set all keys to give make codes only*/
|
case 0xf9: /*Set all keys to give make codes only*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set all keys to give make codes only\n");
|
kbd_log("ATkbd: set all keys to give make codes only\n");
|
||||||
#endif
|
#endif
|
||||||
keyboard_set3_all_break = 0;
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
keyboard_set3_all_break = 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xfa: /*Set all keys to repeat and give make/break codes*/
|
case 0xfa: /*Set all keys to repeat and give make/break codes*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: set all keys to repeat and give make/break codes\n");
|
kbd_log("ATkbd: set all keys to repeat and give make/break codes\n");
|
||||||
#endif
|
#endif
|
||||||
|
kbd_adddata_keyboard(0xfa);
|
||||||
keyboard_set3_all_repeat = 1;
|
keyboard_set3_all_repeat = 1;
|
||||||
keyboard_set3_all_break = 1;
|
keyboard_set3_all_break = 1;
|
||||||
kbd_adddata_keyboard(0xfa);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xfe: /*Resend last scan code*/
|
case 0xfe: /*Resend last scan code*/
|
||||||
@@ -1862,8 +1884,8 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: kbd reset\n");
|
kbd_log("ATkbd: kbd reset\n");
|
||||||
#endif
|
#endif
|
||||||
key_queue_start = key_queue_end = 0; /*Clear key queue*/
|
|
||||||
kbd_adddata_keyboard(0xfa);
|
kbd_adddata_keyboard(0xfa);
|
||||||
|
key_queue_start = key_queue_end = 0; /*Clear key queue*/
|
||||||
kbd_adddata_keyboard(0xaa);
|
kbd_adddata_keyboard(0xaa);
|
||||||
/* Set system flag to 1 and scan code set to 2. */
|
/* Set system flag to 1 and scan code set to 2. */
|
||||||
keyboard_mode &= 0xFC;
|
keyboard_mode &= 0xFC;
|
||||||
@@ -1903,8 +1925,26 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x64:
|
case 0x64:
|
||||||
|
/*
|
||||||
|
* Try to recover from bad commands.
|
||||||
|
*
|
||||||
|
* If we get a command here, but seem to be still in
|
||||||
|
* keyboard-command data mode, abort that...
|
||||||
|
*/
|
||||||
|
if (kbd->key_wantdata || kbd->key_command) {
|
||||||
|
kbd_log("ATkbd: *** BUG ALERT *** aborting previous keyboard command 0x%02X (data %d)\n", kbd->key_command, kbd->key_wantdata);
|
||||||
|
|
||||||
|
/* If they were waiting for data.. */
|
||||||
|
kbd_adddata(0xfa);
|
||||||
|
|
||||||
|
/* Abort the previous command. */
|
||||||
|
kbd->key_command = 0x00;
|
||||||
|
kbd->key_wantdata = 0;
|
||||||
|
}
|
||||||
|
|
||||||
kbd->want60 = 0;
|
kbd->want60 = 0;
|
||||||
kbd->command = val;
|
kbd->command = val;
|
||||||
|
|
||||||
/*New controller command*/
|
/*New controller command*/
|
||||||
switch (val) {
|
switch (val) {
|
||||||
case 0x20: case 0x21: case 0x22: case 0x23:
|
case 0x20: case 0x21: case 0x22: case 0x23:
|
||||||
@@ -1931,7 +1971,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
|
|
||||||
case 0xaa: /*Self-test*/
|
case 0xaa: /*Self-test*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("Self-test\n");
|
kbd_log("ATkbd: self-test\n");
|
||||||
#endif
|
#endif
|
||||||
if ((kbd->flags & KBC_VEN_MASK) == KBC_VEN_TOSHIBA)
|
if ((kbd->flags & KBC_VEN_MASK) == KBC_VEN_TOSHIBA)
|
||||||
kbd->status |= STAT_IFULL;
|
kbd->status |= STAT_IFULL;
|
||||||
@@ -1960,7 +2000,7 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: diagnostic dump\n");
|
kbd_log("ATkbd: diagnostic dump\n");
|
||||||
#endif
|
#endif
|
||||||
for (i=0; i<16; i++)
|
for (i = 0; i < 16; i++)
|
||||||
kbd_adddata(kbd->mem[i]);
|
kbd_adddata(kbd->mem[i]);
|
||||||
kbd_adddata((kbd->input_port & 0xf0) | 0x80);
|
kbd_adddata((kbd->input_port & 0xf0) | 0x80);
|
||||||
kbd_adddata(kbd->output_port);
|
kbd_adddata(kbd->output_port);
|
||||||
@@ -1986,16 +2026,16 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
kbd_log("ATkbd: read output port\n");
|
kbd_log("ATkbd: read output port\n");
|
||||||
#endif
|
#endif
|
||||||
mask = 0xff;
|
mask = 0xff;
|
||||||
if(!keyboard_scan)
|
if (! keyboard_scan)
|
||||||
mask &= 0xbf;
|
mask &= 0xbf;
|
||||||
if(!mouse_scan && ((kbd->flags & KBC_TYPE_MASK) >= KBC_TYPE_PS2_1))
|
if (!mouse_scan && ((kbd->flags & KBC_TYPE_MASK) >= KBC_TYPE_PS2_1))
|
||||||
mask &= 0xf7;
|
mask &= 0xf7;
|
||||||
kbd_adddata(kbd->output_port & mask);
|
kbd_adddata(kbd->output_port & mask);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xd1: /*Write output port*/
|
case 0xd1: /*Write output port*/
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
// kbd_log("ATkbd: write output port\n");
|
kbd_log("ATkbd: write output port\n");
|
||||||
#endif
|
#endif
|
||||||
kbd->want60 = 1;
|
kbd->want60 = 1;
|
||||||
break;
|
break;
|
||||||
@@ -2009,14 +2049,14 @@ kbd_write(uint16_t port, uint8_t val, void *priv)
|
|||||||
|
|
||||||
case 0xdd: /* Disable A20 Address Line */
|
case 0xdd: /* Disable A20 Address Line */
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: disable A20 Address Line\n");
|
kbd_log("ATkbd: disable A20\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_output_write(kbd, kbd->output_port & 0xfd);
|
kbd_output_write(kbd, kbd->output_port & 0xfd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xdf: /* Enable A20 Address Line */
|
case 0xdf: /* Enable A20 Address Line */
|
||||||
#ifdef ENABLE_KEYBOARD_LOG
|
#ifdef ENABLE_KEYBOARD_LOG
|
||||||
kbd_log("ATkbd: enable A20 address line\n");
|
kbd_log("ATkbd: enable A20\n");
|
||||||
#endif
|
#endif
|
||||||
kbd_output_write(kbd, kbd->output_port | 0x02);
|
kbd_output_write(kbd, kbd->output_port | 0x02);
|
||||||
break;
|
break;
|
||||||
@@ -2081,13 +2121,19 @@ kbd_read(uint16_t port, void *priv)
|
|||||||
|
|
||||||
case 0x64:
|
case 0x64:
|
||||||
ret = (kbd->status & 0xFB) | (keyboard_mode & CCB_SYSTEM);
|
ret = (kbd->status & 0xFB) | (keyboard_mode & CCB_SYSTEM);
|
||||||
|
#if 0
|
||||||
ret |= STAT_LOCK;
|
ret |= STAT_LOCK;
|
||||||
|
#endif
|
||||||
/* The transmit timeout (TTIMEOUT) flag should *NOT* be cleared, otherwise
|
/* The transmit timeout (TTIMEOUT) flag should *NOT* be cleared, otherwise
|
||||||
the IBM PS/2 Model 80's BIOS gives error 8601 (mouse error). */
|
the IBM PS/2 Model 80's BIOS gives error 8601 (mouse error). */
|
||||||
kbd->status &= ~(STAT_RTIMEOUT/* | STAT_TTIMEOUT*/);
|
kbd->status &= ~(STAT_RTIMEOUT/* | STAT_TTIMEOUT*/);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef _DEBUG
|
||||||
|
kbd_log("ATkbd: read(%04X) = %02X\n", port, ret);
|
||||||
|
#endif
|
||||||
|
|
||||||
return(ret);
|
return(ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Implementation of the Intel DMA controllers.
|
* Implementation of the Intel DMA controllers.
|
||||||
*
|
*
|
||||||
* Version: @(#)dma.c 1.0.5 2018/05/06
|
* Version: @(#)dma.c 1.0.6 2018/06/25
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -81,118 +81,110 @@ static struct {
|
|||||||
#define DMA_PS2_SIZE16 (1 << 6)
|
#define DMA_PS2_SIZE16 (1 << 6)
|
||||||
|
|
||||||
|
|
||||||
static void dma_ps2_run(int channel);
|
|
||||||
|
|
||||||
|
|
||||||
static uint8_t
|
static uint8_t
|
||||||
dma_read(uint16_t addr, UNUSED(void *priv))
|
_dma_read(int32_t addr)
|
||||||
{
|
{
|
||||||
int channel = (addr >> 1) & 3;
|
uint8_t temp = mem_readb_phys_dma(addr);
|
||||||
uint8_t temp;
|
|
||||||
|
|
||||||
switch (addr & 0xf) {
|
|
||||||
case 0:
|
|
||||||
case 2:
|
|
||||||
case 4:
|
|
||||||
case 6: /*Address registers*/
|
|
||||||
dma_wp ^= 1;
|
|
||||||
if (dma_wp)
|
|
||||||
return(dma[channel].ac & 0xff);
|
|
||||||
return((dma[channel].ac >> 8) & 0xff);
|
|
||||||
|
|
||||||
case 1:
|
|
||||||
case 3:
|
|
||||||
case 5:
|
|
||||||
case 7: /*Count registers*/
|
|
||||||
dma_wp ^= 1;
|
|
||||||
if (dma_wp)
|
|
||||||
temp = dma[channel].cc & 0xff;
|
|
||||||
else
|
|
||||||
temp = dma[channel].cc >> 8;
|
|
||||||
return(temp);
|
return(temp);
|
||||||
|
|
||||||
case 8: /*Status register*/
|
|
||||||
temp = dma_stat & 0xf;
|
|
||||||
dma_stat &= ~0xf;
|
|
||||||
return(temp);
|
|
||||||
|
|
||||||
case 0xd:
|
|
||||||
return(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
return(dmaregs[addr & 0xf]);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
dma_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
_dma_write(uint32_t addr, uint8_t val)
|
||||||
{
|
{
|
||||||
int channel = (addr >> 1) & 3;
|
mem_writeb_phys_dma(addr, val);
|
||||||
|
mem_invalidate_range(addr, addr);
|
||||||
|
}
|
||||||
|
|
||||||
dmaregs[addr & 0xf] = val;
|
|
||||||
switch (addr & 0xf) {
|
static void
|
||||||
case 0:
|
dma_ps2_run(int channel)
|
||||||
case 2:
|
{
|
||||||
case 4:
|
dma_t *dma_c = &dma[channel];
|
||||||
case 6: /*Address registers*/
|
|
||||||
dma_wp ^= 1;
|
switch (dma_c->ps2_mode & DMA_PS2_XFER_MASK) {
|
||||||
if (dma_wp)
|
case DMA_PS2_XFER_MEM_TO_IO:
|
||||||
dma[channel].ab = (dma[channel].ab & 0xffff00) | val;
|
do {
|
||||||
|
if (! dma_c->size) {
|
||||||
|
uint8_t temp = _dma_read(dma_c->ac);
|
||||||
|
|
||||||
|
outb(dma_c->io_addr, temp);
|
||||||
|
|
||||||
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
|
dma_c->ac--;
|
||||||
else
|
else
|
||||||
dma[channel].ab = (dma[channel].ab & 0xff00ff) | (val << 8);
|
dma_c->ac++;
|
||||||
dma[channel].ac = dma[channel].ab;
|
} else {
|
||||||
return;
|
uint16_t temp = _dma_read(dma_c->ac) | (_dma_read(dma_c->ac + 1) << 8);
|
||||||
|
|
||||||
case 1:
|
outw(dma_c->io_addr, temp);
|
||||||
case 3:
|
|
||||||
case 5:
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
case 7: /*Count registers*/
|
dma_c->ac -= 2;
|
||||||
dma_wp ^= 1;
|
|
||||||
if (dma_wp)
|
|
||||||
dma[channel].cb = (dma[channel].cb & 0xff00) | val;
|
|
||||||
else
|
else
|
||||||
dma[channel].cb = (dma[channel].cb & 0x00ff) | (val << 8);
|
dma_c->ac += 2;
|
||||||
dma[channel].cc = dma[channel].cb;
|
|
||||||
return;
|
|
||||||
|
|
||||||
case 8: /*Control register*/
|
|
||||||
dma_command = val;
|
|
||||||
return;
|
|
||||||
|
|
||||||
case 0xa: /*Mask*/
|
|
||||||
if (val & 4)
|
|
||||||
dma_m |= (1 << (val & 3));
|
|
||||||
else
|
|
||||||
dma_m &= ~(1 << (val & 3));
|
|
||||||
//pclog("DMA: %s mask for channel %d\n", (val&4)?"set":"clear", val&3);
|
|
||||||
return;
|
|
||||||
|
|
||||||
case 0xb: /*Mode*/
|
|
||||||
channel = (val & 3);
|
|
||||||
dma[channel].mode = val;
|
|
||||||
if (dma_ps2.is_ps2) {
|
|
||||||
dma[channel].ps2_mode &= ~0x1c;
|
|
||||||
if (val & 0x20)
|
|
||||||
dma[channel].ps2_mode |= 0x10;
|
|
||||||
if ((val & 0xc) == 8)
|
|
||||||
dma[channel].ps2_mode |= 4;
|
|
||||||
else if ((val & 0xc) == 4)
|
|
||||||
dma[channel].ps2_mode |= 0xc;
|
|
||||||
}
|
}
|
||||||
return;
|
|
||||||
|
|
||||||
case 0xc: /*Clear FF*/
|
dma_stat_rq |= (1 << channel);
|
||||||
dma_wp = 0;
|
dma_c->cc--;
|
||||||
return;
|
} while (dma_c->cc > 0);
|
||||||
|
|
||||||
case 0xd: /*Master clear*/
|
dma_stat |= (1 << channel);
|
||||||
dma_wp = 0;
|
break;
|
||||||
dma_m |= 0xf;
|
|
||||||
return;
|
case DMA_PS2_XFER_IO_TO_MEM:
|
||||||
|
do {
|
||||||
|
if (! dma_c->size) {
|
||||||
|
uint8_t temp = inb(dma_c->io_addr);
|
||||||
|
|
||||||
|
_dma_write(dma_c->ac, temp);
|
||||||
|
|
||||||
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
|
dma_c->ac--;
|
||||||
|
else
|
||||||
|
dma_c->ac++;
|
||||||
|
} else {
|
||||||
|
uint16_t temp = inw(dma_c->io_addr);
|
||||||
|
|
||||||
|
_dma_write(dma_c->ac, temp & 0xff);
|
||||||
|
_dma_write(dma_c->ac + 1, temp >> 8);
|
||||||
|
|
||||||
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
|
dma_c->ac -= 2;
|
||||||
|
else
|
||||||
|
dma_c->ac += 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
dma_stat_rq |= (1 << channel);
|
||||||
|
dma_c->cc--;
|
||||||
|
} while (dma_c->cc > 0);
|
||||||
|
|
||||||
|
ps2_cache_clean();
|
||||||
|
dma_stat |= (1 << channel);
|
||||||
|
break;
|
||||||
|
|
||||||
|
default: /*Memory verify*/
|
||||||
|
do {
|
||||||
|
if (! dma_c->size) {
|
||||||
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
|
dma_c->ac--;
|
||||||
|
else
|
||||||
|
dma_c->ac++;
|
||||||
|
} else {
|
||||||
|
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
||||||
|
dma_c->ac -= 2;
|
||||||
|
else
|
||||||
|
dma_c->ac += 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
dma_stat_rq |= (1 << channel);
|
||||||
|
dma->cc--;
|
||||||
|
} while (dma->cc > 0);
|
||||||
|
|
||||||
|
dma_stat |= (1 << channel);
|
||||||
|
break;
|
||||||
|
|
||||||
case 0xf: /*Mask write*/
|
|
||||||
dma_m = (dma_m & 0xf0) | (val & 0xf);
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -355,6 +347,118 @@ dma_ps2_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static uint8_t
|
||||||
|
dma_read(uint16_t addr, UNUSED(void *priv))
|
||||||
|
{
|
||||||
|
int channel = (addr >> 1) & 3;
|
||||||
|
uint8_t temp;
|
||||||
|
|
||||||
|
switch (addr & 0xf) {
|
||||||
|
case 0:
|
||||||
|
case 2:
|
||||||
|
case 4:
|
||||||
|
case 6: /*Address registers*/
|
||||||
|
dma_wp ^= 1;
|
||||||
|
if (dma_wp)
|
||||||
|
return(dma[channel].ac & 0xff);
|
||||||
|
return((dma[channel].ac >> 8) & 0xff);
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
case 3:
|
||||||
|
case 5:
|
||||||
|
case 7: /*Count registers*/
|
||||||
|
dma_wp ^= 1;
|
||||||
|
if (dma_wp)
|
||||||
|
temp = dma[channel].cc & 0xff;
|
||||||
|
else
|
||||||
|
temp = dma[channel].cc >> 8;
|
||||||
|
return(temp);
|
||||||
|
|
||||||
|
case 8: /*Status register*/
|
||||||
|
temp = dma_stat & 0xf;
|
||||||
|
dma_stat &= ~0xf;
|
||||||
|
return(temp);
|
||||||
|
|
||||||
|
case 0xd:
|
||||||
|
return(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
return(dmaregs[addr & 0xf]);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
dma_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
||||||
|
{
|
||||||
|
int channel = (addr >> 1) & 3;
|
||||||
|
|
||||||
|
dmaregs[addr & 0xf] = val;
|
||||||
|
switch (addr & 0xf) {
|
||||||
|
case 0:
|
||||||
|
case 2:
|
||||||
|
case 4:
|
||||||
|
case 6: /*Address registers*/
|
||||||
|
dma_wp ^= 1;
|
||||||
|
if (dma_wp)
|
||||||
|
dma[channel].ab = (dma[channel].ab & 0xffff00) | val;
|
||||||
|
else
|
||||||
|
dma[channel].ab = (dma[channel].ab & 0xff00ff) | (val << 8);
|
||||||
|
dma[channel].ac = dma[channel].ab;
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
case 3:
|
||||||
|
case 5:
|
||||||
|
case 7: /*Count registers*/
|
||||||
|
dma_wp ^= 1;
|
||||||
|
if (dma_wp)
|
||||||
|
dma[channel].cb = (dma[channel].cb & 0xff00) | val;
|
||||||
|
else
|
||||||
|
dma[channel].cb = (dma[channel].cb & 0x00ff) | (val << 8);
|
||||||
|
dma[channel].cc = dma[channel].cb;
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 8: /*Control register*/
|
||||||
|
dma_command = val;
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 0xa: /*Mask*/
|
||||||
|
if (val & 4)
|
||||||
|
dma_m |= (1 << (val & 3));
|
||||||
|
else
|
||||||
|
dma_m &= ~(1 << (val & 3));
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 0xb: /*Mode*/
|
||||||
|
channel = (val & 3);
|
||||||
|
dma[channel].mode = val;
|
||||||
|
if (dma_ps2.is_ps2) {
|
||||||
|
dma[channel].ps2_mode &= ~0x1c;
|
||||||
|
if (val & 0x20)
|
||||||
|
dma[channel].ps2_mode |= 0x10;
|
||||||
|
if ((val & 0xc) == 8)
|
||||||
|
dma[channel].ps2_mode |= 4;
|
||||||
|
else if ((val & 0xc) == 4)
|
||||||
|
dma[channel].ps2_mode |= 0xc;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 0xc: /*Clear FF*/
|
||||||
|
dma_wp = 0;
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 0xd: /*Master clear*/
|
||||||
|
dma_wp = 0;
|
||||||
|
dma_m |= 0xf;
|
||||||
|
return;
|
||||||
|
|
||||||
|
case 0xf: /*Mask write*/
|
||||||
|
dma_m = (dma_m & 0xf0) | (val & 0xf);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static uint8_t
|
static uint8_t
|
||||||
dma16_read(uint16_t addr, UNUSED(void *priv))
|
dma16_read(uint16_t addr, UNUSED(void *priv))
|
||||||
{
|
{
|
||||||
@@ -477,6 +581,13 @@ dma16_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static uint8_t
|
||||||
|
dma_page_read(uint16_t addr, UNUSED(void *priv))
|
||||||
|
{
|
||||||
|
return(dmapages[addr & 0xf]);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
dma_page_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
dma_page_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
||||||
{
|
{
|
||||||
@@ -534,13 +645,6 @@ dma_page_write(uint16_t addr, uint8_t val, UNUSED(void *priv))
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static uint8_t
|
|
||||||
dma_page_read(uint16_t addr, UNUSED(void *priv))
|
|
||||||
{
|
|
||||||
return(dmapages[addr & 0xf]);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
dma_reset(void)
|
dma_reset(void)
|
||||||
{
|
{
|
||||||
@@ -624,23 +728,6 @@ ps2_dma_init(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
uint8_t
|
|
||||||
_dma_read(int32_t addr)
|
|
||||||
{
|
|
||||||
uint8_t temp = mem_readb_phys_dma(addr);
|
|
||||||
|
|
||||||
return(temp);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void
|
|
||||||
_dma_write(uint32_t addr, uint8_t val)
|
|
||||||
{
|
|
||||||
mem_writeb_phys_dma(addr, val);
|
|
||||||
mem_invalidate_range(addr, addr);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int
|
int
|
||||||
dma_channel_read(int channel)
|
dma_channel_read(int channel)
|
||||||
{
|
{
|
||||||
@@ -786,97 +873,6 @@ dma_channel_write(int channel, uint16_t val)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
|
||||||
dma_ps2_run(int channel)
|
|
||||||
{
|
|
||||||
dma_t *dma_c = &dma[channel];
|
|
||||||
|
|
||||||
switch (dma_c->ps2_mode & DMA_PS2_XFER_MASK) {
|
|
||||||
case DMA_PS2_XFER_MEM_TO_IO:
|
|
||||||
do {
|
|
||||||
if (! dma_c->size) {
|
|
||||||
uint8_t temp = _dma_read(dma_c->ac);
|
|
||||||
|
|
||||||
outb(dma_c->io_addr, temp);
|
|
||||||
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac--;
|
|
||||||
else
|
|
||||||
dma_c->ac++;
|
|
||||||
} else {
|
|
||||||
uint16_t temp = _dma_read(dma_c->ac) | (_dma_read(dma_c->ac + 1) << 8);
|
|
||||||
|
|
||||||
outw(dma_c->io_addr, temp);
|
|
||||||
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac -= 2;
|
|
||||||
else
|
|
||||||
dma_c->ac += 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
dma_stat_rq |= (1 << channel);
|
|
||||||
dma_c->cc--;
|
|
||||||
} while (dma_c->cc > 0);
|
|
||||||
|
|
||||||
dma_stat |= (1 << channel);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case DMA_PS2_XFER_IO_TO_MEM:
|
|
||||||
do {
|
|
||||||
if (! dma_c->size) {
|
|
||||||
uint8_t temp = inb(dma_c->io_addr);
|
|
||||||
|
|
||||||
_dma_write(dma_c->ac, temp);
|
|
||||||
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac--;
|
|
||||||
else
|
|
||||||
dma_c->ac++;
|
|
||||||
} else {
|
|
||||||
uint16_t temp = inw(dma_c->io_addr);
|
|
||||||
|
|
||||||
_dma_write(dma_c->ac, temp & 0xff);
|
|
||||||
_dma_write(dma_c->ac + 1, temp >> 8);
|
|
||||||
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac -= 2;
|
|
||||||
else
|
|
||||||
dma_c->ac += 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
dma_stat_rq |= (1 << channel);
|
|
||||||
dma_c->cc--;
|
|
||||||
} while (dma_c->cc > 0);
|
|
||||||
|
|
||||||
ps2_cache_clean();
|
|
||||||
dma_stat |= (1 << channel);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default: /*Memory verify*/
|
|
||||||
do {
|
|
||||||
if (! dma_c->size) {
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac--;
|
|
||||||
else
|
|
||||||
dma_c->ac++;
|
|
||||||
} else {
|
|
||||||
if (dma_c->ps2_mode & DMA_PS2_DEC2)
|
|
||||||
dma_c->ac -= 2;
|
|
||||||
else
|
|
||||||
dma_c->ac += 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
dma_stat_rq |= (1 << channel);
|
|
||||||
dma->cc--;
|
|
||||||
} while (dma->cc > 0);
|
|
||||||
|
|
||||||
dma_stat |= (1 << channel);
|
|
||||||
break;
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int
|
int
|
||||||
dma_mode(int channel)
|
dma_mode(int channel)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Definitions for the Intel DMA controller.
|
* Definitions for the Intel DMA controller.
|
||||||
*
|
*
|
||||||
* Version: @(#)dma.h 1.0.2 2018/03/12
|
* Version: @(#)dma.h 1.0.3 2018/06/25
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -71,24 +71,26 @@ extern void ps2_dma_init(void);
|
|||||||
extern void dma_reset(void);
|
extern void dma_reset(void);
|
||||||
extern int dma_mode(int channel);
|
extern int dma_mode(int channel);
|
||||||
|
|
||||||
extern void readdma0(void);
|
|
||||||
extern int readdma1(void);
|
|
||||||
extern uint8_t readdma2(void);
|
|
||||||
extern int readdma3(void);
|
|
||||||
|
|
||||||
extern void writedma2(uint8_t temp);
|
|
||||||
|
|
||||||
extern int dma_channel_read(int channel);
|
extern int dma_channel_read(int channel);
|
||||||
extern int dma_channel_write(int channel, uint16_t val);
|
extern int dma_channel_write(int channel, uint16_t val);
|
||||||
|
|
||||||
extern void dma_alias_set(void);
|
|
||||||
extern void dma_alias_remove(void);
|
|
||||||
extern void dma_alias_remove_piix(void);
|
|
||||||
|
|
||||||
extern void DMAPageRead(uint32_t PhysAddress, uint8_t *DataRead,
|
extern void DMAPageRead(uint32_t PhysAddress, uint8_t *DataRead,
|
||||||
uint32_t TotalSize);
|
uint32_t TotalSize);
|
||||||
extern void DMAPageWrite(uint32_t PhysAddress, const uint8_t *DataWrite,
|
extern void DMAPageWrite(uint32_t PhysAddress, const uint8_t *DataWrite,
|
||||||
uint32_t TotalSize);
|
uint32_t TotalSize);
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
extern void readdma0(void);
|
||||||
|
extern int readdma1(void);
|
||||||
|
extern uint8_t readdma2(void);
|
||||||
|
extern int readdma3(void);
|
||||||
|
|
||||||
|
extern void writedma2(uint8_t temp);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
extern void dma_alias_set(void);
|
||||||
|
extern void dma_alias_remove(void);
|
||||||
|
extern void dma_alias_remove_piix(void);
|
||||||
|
|
||||||
|
|
||||||
#endif /*EMU_DMA_H*/
|
#endif /*EMU_DMA_H*/
|
||||||
|
|||||||
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Main include file for the application.
|
* Main include file for the application.
|
||||||
*
|
*
|
||||||
* Version: @(#)emu.h 1.0.25 2018/06/02
|
* Version: @(#)emu.h 1.0.26 2018/06/25
|
||||||
*
|
*
|
||||||
* Author: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Author: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
*
|
*
|
||||||
@@ -167,6 +167,8 @@ extern int config_changed; /* config has changed */
|
|||||||
extern void pclog_ex(const char *fmt, va_list);
|
extern void pclog_ex(const char *fmt, va_list);
|
||||||
#endif
|
#endif
|
||||||
extern void pclog(const char *fmt, ...);
|
extern void pclog(const char *fmt, ...);
|
||||||
|
extern void pclog_repeat(int enabled);
|
||||||
|
extern void pclog_dump(int num);
|
||||||
extern void fatal(const char *fmt, ...);
|
extern void fatal(const char *fmt, ...);
|
||||||
extern void pc_version(const char *platform);
|
extern void pc_version(const char *platform);
|
||||||
extern void pc_path(wchar_t *dest, int dest_sz, const wchar_t *src);
|
extern void pc_path(wchar_t *dest, int dest_sz, const wchar_t *src);
|
||||||
|
|||||||
@@ -260,7 +260,7 @@ Note: the block address is forced to be a multiple of the block size by
|
|||||||
ignoring the appropriate number of the least-significant bits
|
ignoring the appropriate number of the least-significant bits
|
||||||
SeeAlso: #P0178,#P0187
|
SeeAlso: #P0178,#P0187
|
||||||
*
|
*
|
||||||
* Version: @(#)m_at_opti495.c 1.0.5 2018/05/06
|
* Version: @(#)m_at_opti495.c 1.0.6 2018/06/25
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -316,7 +316,9 @@ opti495_write(uint16_t addr, uint8_t val, void *p)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x24:
|
case 0x24:
|
||||||
|
#if 0
|
||||||
pclog("OPTI: writing reg %02X %02X\n", optireg, val);
|
pclog("OPTI: writing reg %02X %02X\n", optireg, val);
|
||||||
|
#endif
|
||||||
if (optireg >= 0x20 && optireg <= 0x2C) {
|
if (optireg >= 0x20 && optireg <= 0x2C) {
|
||||||
optiregs[optireg - 0x20] = val;
|
optiregs[optireg - 0x20] = val;
|
||||||
if (optireg == 0x21) {
|
if (optireg == 0x21) {
|
||||||
|
|||||||
67
src/pc.c
67
src/pc.c
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Main emulator module where most things are controlled.
|
* Main emulator module where most things are controlled.
|
||||||
*
|
*
|
||||||
* Version: @(#)pc.c 1.0.47 2018/06/10
|
* Version: @(#)pc.c 1.0.48 2018/06/26
|
||||||
*
|
*
|
||||||
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
* Miran Grca, <mgrca8@gmail.com>
|
* Miran Grca, <mgrca8@gmail.com>
|
||||||
@@ -215,8 +215,16 @@ pclog_ex(const char *fmt, va_list ap)
|
|||||||
#ifndef RELEASE_BUILD
|
#ifndef RELEASE_BUILD
|
||||||
static char buff[PCLOG_BUFF_SIZE];
|
static char buff[PCLOG_BUFF_SIZE];
|
||||||
static int seen = 0;
|
static int seen = 0;
|
||||||
|
static int detect = 1;
|
||||||
char temp[PCLOG_BUFF_SIZE];
|
char temp[PCLOG_BUFF_SIZE];
|
||||||
|
|
||||||
|
if (fmt == NULL) {
|
||||||
|
/* Initialize. */
|
||||||
|
detect = (ap != NULL) ? 1 : 0;
|
||||||
|
seen = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (stdlog == NULL) {
|
if (stdlog == NULL) {
|
||||||
if (log_path[0] != L'\0') {
|
if (log_path[0] != L'\0') {
|
||||||
stdlog = plat_fopen(log_path, L"w");
|
stdlog = plat_fopen(log_path, L"w");
|
||||||
@@ -236,7 +244,7 @@ pclog_ex(const char *fmt, va_list ap)
|
|||||||
}
|
}
|
||||||
|
|
||||||
vsprintf(temp, fmt, ap);
|
vsprintf(temp, fmt, ap);
|
||||||
if (! strcmp(buff, temp)) {
|
if (detect && !strcmp(buff, temp)) {
|
||||||
seen++;
|
seen++;
|
||||||
} else {
|
} else {
|
||||||
if (seen) {
|
if (seen) {
|
||||||
@@ -266,6 +274,61 @@ pclog(const char *fmt, ...)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Enable or disable detection of repeated info being logged. */
|
||||||
|
void
|
||||||
|
pclog_repeat(int enabled)
|
||||||
|
{
|
||||||
|
pclog_ex(NULL, (va_list)enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef _DEBUG
|
||||||
|
/* Log a block of code around the current CS:IP. */
|
||||||
|
void
|
||||||
|
pclog_dump(int num)
|
||||||
|
{
|
||||||
|
char buff[128];
|
||||||
|
char *sp = NULL;
|
||||||
|
int i, k;
|
||||||
|
|
||||||
|
/* We make the current PC be in the middle of the block. */
|
||||||
|
num >>= 1;
|
||||||
|
i = -num;
|
||||||
|
|
||||||
|
/* Disable the repeat-detection. */
|
||||||
|
pclog_repeat(0);
|
||||||
|
|
||||||
|
while (i < num) {
|
||||||
|
if (sp == NULL) {
|
||||||
|
sp = buff;
|
||||||
|
sprintf(sp, "%08lx:", cpu_state.pc + i);
|
||||||
|
sp += strlen(sp);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Get byte from memory. */
|
||||||
|
k = readmembl(cpu_state.pc + i);
|
||||||
|
i++;
|
||||||
|
|
||||||
|
sprintf(sp, " %02x", k & 0xff);
|
||||||
|
sp += strlen(sp);
|
||||||
|
|
||||||
|
if ((i % 16) == 0) {
|
||||||
|
strcat(sp, "\n");
|
||||||
|
pclog(buff);
|
||||||
|
sp = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (sp != NULL) {
|
||||||
|
strcat(sp, "\n");
|
||||||
|
pclog(buff);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Re-enable the repeat-detection. */
|
||||||
|
pclog_repeat(1);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
/* Log a fatal error, and display a UI message before exiting. */
|
/* Log a fatal error, and display a UI message before exiting. */
|
||||||
void
|
void
|
||||||
fatal(const char *fmt, ...)
|
fatal(const char *fmt, ...)
|
||||||
|
|||||||
@@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
* Define application version and build info.
|
* Define application version and build info.
|
||||||
*
|
*
|
||||||
* Version: @(#)version.h 1.0.15 2018/05/29
|
* Version: @(#)version.h 1.0.16 2018/06/25
|
||||||
*
|
*
|
||||||
* Author: Fred N. van Kempen, <decwiz@yahoo.com>
|
* Author: Fred N. van Kempen, <decwiz@yahoo.com>
|
||||||
*
|
*
|
||||||
@@ -55,7 +55,7 @@
|
|||||||
#define EMU_VER_MAJOR 0
|
#define EMU_VER_MAJOR 0
|
||||||
#define EMU_VER_MINOR 1
|
#define EMU_VER_MINOR 1
|
||||||
#define EMU_VER_REV 6
|
#define EMU_VER_REV 6
|
||||||
//#define EMU_VER_PATCH 1
|
#define EMU_VER_PATCH 1
|
||||||
|
|
||||||
|
|
||||||
/* Standard C preprocessor macros. */
|
/* Standard C preprocessor macros. */
|
||||||
|
|||||||
Reference in New Issue
Block a user