diff --git a/int-8018x.c b/int-8018x.c index 4d017ee..dc36f7d 100644 --- a/int-8018x.c +++ b/int-8018x.c @@ -22,35 +22,46 @@ #define INT_REG_I2CON 13 #define INT_REG_I3CON 14 +// REQST and MASK register bits +#define BIT_TMR 0 +// Bit 1 is reserved on all models +// Bits 2 & 3 are for DMA in XL variant +// Bits 2 & 3 are for serial and INT4 for EB variant +#define BIT_SER 2 +#define BIT_INT4 3 +#define BIT_INT0 4 +#define BIT_INT1 5 +#define BIT_INT2 6 +#define BIT_INT3 7 + int _int_line_max = INT_LINE_MAX; int _int_prio_max = INT_PRIO_MAX; -// Timer & serial are edge triggered - int _pri_mask = 7; +// Timers & serial are edge triggered int _int_mode [INT_LINE_MAX] = - { 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1}; + { 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1}; +// Default priority for timers is 0 +// Default priority for serial is 1 int _int_prio [INT_LINE_MAX] = - { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1}; int _int_vect [INT_LINE_MAX] = - { 8, 0, 20, 17, 12, 13, 14, 15, 21, 18, 19 }; + { 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21}; int _int_mask [INT_LINE_MAX] = - { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}; + { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}; -int _int_req [INT_LINE_MAX] = - { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; - -int _int_serv [INT_LINE_MAX] = - { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; +// Initialized to zero by CRT +int _int_req [INT_LINE_MAX]; +int _int_serv [INT_LINE_MAX]; word_t imask; +// PIC I/O read -// PIC I/O write int int_io_read (word_t p, word_t * w) { int err = 0; @@ -61,12 +72,12 @@ int int_io_read (word_t p, word_t * w) { word_t out = 0; for (size_t i = 0; i < 8; i++) { - if (i == 0) { - if (_int_req[i] || _int_req[INT_LINE_TIMER1] || _int_req[INT_LINE_TIMER2]) { + if (i == BIT_TMR) { + if (_int_req[INT_LINE_TIMER0] || _int_req[INT_LINE_TIMER1] || _int_req[INT_LINE_TIMER2]) { out |= 1 << i; } - } else if (i == 2) { - if (_int_req[i] || _int_req[INT_LINE_SERIALTX]) { + } else if (i == BIT_SER) { + if (_int_req[INT_LINE_SERIAL_RX] || _int_req[INT_LINE_SERIAL_TX]) { out |= 1 << i; } } else if (_int_req[i]) { @@ -79,7 +90,15 @@ int int_io_read (word_t p, word_t * w) { word_t out = 0; for (size_t i = 0; i < 8; i++) { - if (_int_mask[i]) { + if (i == BIT_TMR) { + if (_int_mask[INT_LINE_TIMER0]) { + out |= 1 << i; + } + } else if (i == BIT_SER) { + if (_int_mask[INT_LINE_SERIAL_RX]) { + out |= 1 << i; + } + } else if (_int_mask[i]) { out |= 1 << i; } } @@ -95,6 +114,8 @@ int int_io_read (word_t p, word_t * w) return err; } +// PIC I/O write + int int_io_write (word_t p, word_t w) { int err = 0; @@ -133,8 +154,8 @@ int int_io_write (word_t p, word_t w) int_end_line (INT_LINE_INT4); break; case 20: - int_end_line (INT_LINE_SERIAL); - int_end_line (INT_LINE_SERIALTX); + int_end_line (INT_LINE_SERIAL_RX); + int_end_line (INT_LINE_SERIAL_TX); break; default: printf("nemam %d\n", w & 0x1f); @@ -143,18 +164,22 @@ int int_io_write (word_t p, word_t w) } else if (r == INT_REG_MASK) { - for (int i = 8-1; i >= 0; i--) { - int mask = (w & 0x80) ? 1 : 0; - _int_mask[i] = mask; + for (int i = 0; i < 8; i++) { + int mask = (w & 0x01) ? 1 : 0; - if (i == INT_LINE_SERIAL) { - _int_mask[INT_LINE_SERIALTX] = mask; - } - if (i == INT_LINE_TIMER0) { + if (i == BIT_TMR) { + _int_mask[INT_LINE_TIMER0] = mask; _int_mask[INT_LINE_TIMER1] = mask; _int_mask[INT_LINE_TIMER2] = mask; } - w <<= 1; + else if (i == BIT_SER) { + _int_mask[INT_LINE_SERIAL_RX] = mask; + _int_mask[INT_LINE_SERIAL_TX] = mask; + } + else { + _int_mask[i] = mask; + } + w >>= 1; } } else if (r == INT_REG_PRIMSK) @@ -176,10 +201,10 @@ int int_io_write (word_t p, word_t w) else if (r == INT_REG_SCUCON) { // TODO: level ? - _int_mask[INT_LINE_SERIAL] = (p >> 3) & 1; - _int_mask[INT_LINE_SERIALTX] = (p >> 3) & 1; - _int_prio[INT_LINE_SERIAL] = p & 7; - _int_prio[INT_LINE_SERIALTX] = p & 7; + _int_mask[INT_LINE_SERIAL_RX] = (p >> 3) & 1; + _int_mask[INT_LINE_SERIAL_TX] = (p >> 3) & 1; + _int_prio[INT_LINE_SERIAL_RX] = p & 7; + _int_prio[INT_LINE_SERIAL_TX] = p & 7; // printf("int scu pri %d mask %d\n", p & 7, (p >> 3) & 1); } else if (r == INT_REG_I4CON) diff --git a/int-8018x.h b/int-8018x.h index 92dc096..a915591 100644 --- a/int-8018x.h +++ b/int-8018x.h @@ -7,22 +7,23 @@ #include "emu-types.h" // Interrupt lines -// 8018X EB variant - -#define INT_LINE_TIMER0 0 -#define INT_LINE_CASC 1 // reserved -#define INT_LINE_SERIAL 2 -#define INT_LINE_INT4 3 -#define INT_LINE_INT0 4 -#define INT_LINE_INT1 5 -#define INT_LINE_INT2 6 -#define INT_LINE_INT3 7 - -#define INT_LINE_TIMER1 8 -#define INT_LINE_TIMER2 9 -#define INT_LINE_SERIALTX 10 - -#define INT_LINE_MAX (8+3) +// Merge 8018X XL/EA/EB/EC variants + +#define INT_LINE_TIMER0 0 +#define INT_LINE_CASC 1 +#define INT_LINE_DMA0 2 +#define INT_LINE_DMA1 3 +#define INT_LINE_INT0 4 +#define INT_LINE_INT1 5 +#define INT_LINE_INT2 6 +#define INT_LINE_INT3 7 +#define INT_LINE_INT4 9 +#define INT_LINE_TIMER1 10 +#define INT_LINE_TIMER2 11 +#define INT_LINE_SERIAL_RX 12 +#define INT_LINE_SERIAL_TX 13 + +#define INT_LINE_MAX 14 // Interrupt controller diff --git a/serial-8018x.c b/serial-8018x.c index 1678536..44f3bbe 100644 --- a/serial-8018x.c +++ b/serial-8018x.c @@ -37,7 +37,7 @@ void serial_int (void) stat = 1; */ - int_line_set (INT_LINE_SERIAL, stat); + int_line_set (INT_LINE_SERIAL_RX, stat); } diff --git a/timer-8018x.c b/timer-8018x.c index 4221fba..b1dc0c2 100644 --- a/timer-8018x.c +++ b/timer-8018x.c @@ -5,7 +5,6 @@ #include "emu-int.h" #include "emu-timer.h" -#include "emu-int.h" #include "int-8018x.h" #include "timer-8018x.h"