summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLeo C2014-08-19 11:55:02 +0200
committerLeo C2014-08-19 11:55:02 +0200
commit62f624d3e4c6333563d6bf3019bcdcb3dc2836ac (patch)
tree360ffb68fad36c04b9b062cfdaadc3fe74a48bee
parentf338df2abc35f85961aa6266458f94ea2a102b81 (diff)
downloadz180-stamp-62f624d3e4c6333563d6bf3019bcdcb3dc2836ac.zip
Rework z80 bus control
-rw-r--r--avr/cmd_boot.c30
-rw-r--r--avr/cmd_mem.c34
-rw-r--r--avr/z180-serv.c4
-rw-r--r--avr/z80-if.c328
-rw-r--r--avr/z80-if.h24
5 files changed, 189 insertions, 231 deletions
diff --git a/avr/cmd_boot.c b/avr/cmd_boot.c
index 8c17799..1699a5c 100644
--- a/avr/cmd_boot.c
+++ b/avr/cmd_boot.c
@@ -30,11 +30,11 @@ static void z80_load_mem(void)
hdrom_address[sec]+hdrom_length_of_sections[sec] - 1,
hdrom_length_of_sections[sec]);
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
z80_write_block((const FLASH unsigned char *) &hdrom[sec_base], /* src */
hdrom_address[sec], /* dest */
hdrom_length_of_sections[sec]); /* len */
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
sec_base+=hdrom_length_of_sections[sec];
sec++;
}
@@ -44,7 +44,7 @@ int do_loadf(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
(void) cmdtp; (void) flag; (void) argc; (void) argv;
- if (z80_runstate() & ZST_RUNNING) {
+ if (z80_bus_state() & ZST_RUNNING) {
printf_P(PSTR("## Can't load while CPU is running!\n"));
return 1;
}
@@ -61,7 +61,7 @@ int do_busreq_pulse(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
(void) cmdtp; (void) flag;
- if (!(z80_runstate() & ZST_RUNNING)) {
+ if (!(z80_bus_state() & ZST_RUNNING)) {
printf_P(PSTR("## CPU is not running!\n"));
return 1;
}
@@ -69,9 +69,9 @@ int do_busreq_pulse(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
if (argc > 1)
count = (uint16_t) strtoul(argv[2], NULL, 16);
- z80_request_bus();
+ z80_bus_cmd(Request);
while (count--)
- z80_busreq_hpulse();
+ z80_bus_cmd(M_Cycle);
return 0;
}
@@ -93,7 +93,7 @@ int do_go(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
return 1;
}
- if (z80_runstate() & ZST_RUNNING) {
+ if (z80_bus_state() & ZST_RUNNING) {
printf_P(PSTR("## CPU allready running!\n"));
return 1;
}
@@ -104,22 +104,22 @@ int do_go(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
uint8_t tmp[3];
uint_fast8_t i;
- z80_request_bus();
+ z80_bus_cmd(Request);
for (i = 0; i < 3; i++)
tmp[i] = z80_read(i);
z80_write(0, 0xc3);
z80_write(1, addr);
z80_write(2, (addr >> 8));
- z80_run();
- z80_busreq_hpulse();
- z80_busreq_hpulse();
+ z80_bus_cmd(Run);
+ z80_bus_cmd(M_Cycle);
+ z80_bus_cmd(M_Cycle);
for (i = 0; i < 3; i++)
z80_write(i, tmp[i]);
} else
- z80_run();
+ z80_bus_cmd(Run);
- z80_release_bus();
+ z80_bus_cmd(Release);
return 0;
}
@@ -129,8 +129,8 @@ int do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
(void) cmdtp; (void) flag; (void) argc; (void) argv;
printf_P(PSTR("## CPU now in reset state.\n"));
- z80_reset();
+ z80_bus_cmd(Reset);
return 0;
}
@@ -138,7 +138,7 @@ int do_restart(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
(void) cmdtp; (void) flag; (void) argc; (void) argv;
- z80_reset_pulse();
+ z80_bus_cmd(Restart);
return 0;
}
diff --git a/avr/cmd_mem.c b/avr/cmd_mem.c
index 49a46f6..253f02f 100644
--- a/avr/cmd_mem.c
+++ b/avr/cmd_mem.c
@@ -65,10 +65,10 @@ int z180_dump_mem(uint32_t startaddr, uint32_t len, const char *title)
if (len < 16)
llen = len;
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
for (i = pre; i < llen; i++)
buf[i] = z80_read(addr + i);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
printf_P(PSTR("%.5lx:"), addr);
#if 0
@@ -193,12 +193,12 @@ int do_mem_mw(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
count = 1;
}
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
while (count-- > 0) {
z80_write(addr, writeval);
++addr;
}
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
return 0;
}
@@ -281,10 +281,10 @@ int do_mem_cmp(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
count = strtoul(argv[3], NULL, 16);
for (ngood = 0; ngood < count; ++ngood) {
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
byte1 = z80_read(addr1);
byte2 = z80_read(addr2);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
if (byte1 != byte2) {
printf( "byte at 0x%05lx (%#02x) != "
"byte at 0x%05lx (%#02x)\n",
@@ -337,10 +337,10 @@ int do_mem_cp(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
while (count-- > 0) {
uint8_t data;
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
data = z80_read(src);
z80_write(dest, data);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
src += step;
dest += step;
@@ -390,20 +390,20 @@ int do_mem_loop(cmd_tbl_t *cmdtp, int flag, int argc,
* If we have only one object, just run infinite loops.
*/
if (length == 1) {
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
for (;;)
z80_read(addr);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
}
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
for (;;) {
uint32_t i = length;
uint32_t p = addr;
while (i-- > 0)
z80_read(p++);
}
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
return 0;
}
@@ -432,7 +432,7 @@ int do_mem_loopw (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
* If we have only one object, just run infinite loops.
*/
if (length == 1) {
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
for (;;)
z80_write(addr, data);
}
@@ -844,10 +844,10 @@ mod_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char * const argv[])
* the next value. A non-converted value exits.
*/
do {
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
data = z80_read(addr);
printf("%05lx: %02x", addr, data);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
nbytes = cli_readline(PSTR(" ? "));
if (nbytes == 0 || (nbytes == 1 && console_buffer[0] == '-')) {
@@ -863,9 +863,9 @@ mod_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char * const argv[])
data = strtoul(console_buffer, &endp, 16);
nbytes = endp - console_buffer;
if (nbytes) {
- zstate_t state = z80_request_bus_save();
+ z80_bus_cmd(Request);
z80_write(addr, data);
- z80_release_bus_save(state);
+ z80_bus_cmd(Release);
if (incrflag)
addr++;
}
diff --git a/avr/z180-serv.c b/avr/z180-serv.c
index 051d6ef..193b23f 100644
--- a/avr/z180-serv.c
+++ b/avr/z180-serv.c
@@ -95,9 +95,9 @@ uint8_t z80_get_byte(uint32_t adr)
{
uint8_t data;
- z80_request_bus();
+ z80_bus_cmd(Request);
data = z80_read(adr),
- z80_release_bus();
+ z80_bus_cmd(Release);
return data;
}
diff --git a/avr/z80-if.c b/avr/z80-if.c
index ab8e293..392597e 100644
--- a/avr/z80-if.c
+++ b/avr/z80-if.c
@@ -186,18 +186,27 @@ static void z80_setup_addrbus_active(void)
}
-
static void z80_setup_dbus_in(void)
{
DDR_DB = 0;
P_DB = 0;
}
+
static void z80_setup_dbus_out(void)
{
DDR_DB = 0xff;
}
+
+static void z80_reset_pulse(void)
+{
+ Z80_O_RST = 0;
+ _delay_us(10);
+ Z80_O_RST = 1;
+}
+
+
void z80_setup_bus(void)
{
/* /ZRESET: Output and low */
@@ -220,215 +229,162 @@ void z80_setup_bus(void)
z80_setup_dbus_in();
zstate = RESET;
-// Stat &= ~S_Z180_RUNNING;
}
-/*--------------------------------------------------------------------------*/
-#if 0
- switch (zstate) {
- case RESET:
- break;
- case RESET_AQRD:
- break;
- case RUN:
- break;
- case RUN_AQRD:
- break;
- }
-#endif
-/*--------------------------------------------------------------------------*/
-
-#if 0
-void z80_busreq(level_t level)
-{
- Z80_O_BUSREQ = level;
-}
-
-int z80_stat_reset(void)
-{
-// return Z80_O_RESET;
-}
-
-int z80_stat_halt(void)
-{
- return Z80_I_HALT;
-}
-#endif
-
-zstate_t z80_runstate(void)
+zstate_t z80_bus_state(void)
{
return zstate;
}
-void z80_reset(void)
+
+static void z80_busreq_hpulse(void)
{
-#if DEBUG
- zstate_t old = zstate;
-#endif
z80_setup_dbus_in();
z80_setup_addrbus_tristate();
- Z80_O_RST = 0;
- Z80_O_BUSREQ = 1;
- zstate = RESET;
-
- debug("z80_reset: state: %02x --> %02x\n", old, zstate);
-}
-void z80_reset_pulse(void)
-{
-#if DEBUG
- zstate_t old = zstate;
-#endif
- switch (zstate) {
- case RESET:
- case RESET_AQRD:
- break;
-
- case RUN:
- case RUN_AQRD:
- Z80_O_RST = 0;
- _delay_us(10);
- Z80_O_RST = 1;
- break;
+ ATOMIC_BLOCK(ATOMIC_RESTORESTATE) {
+ Z80_O_BUSREQ = 1;
+ Z80_O_BUSREQ = 1; /* 2 AVR clock cycles */
+ Z80_O_BUSREQ = 0; /* 2 AVR clock cycles */
}
- debug("z80_reset_pulse: state: %02x --> %02x\n", old, zstate);
-}
-
-void z80_request_bus(void)
-{
-#if DEBUG
- zstate_t old = zstate;
-#endif
-
- switch (zstate) {
- case RESET:
- Z80_O_BUSREQ = 0;
- Z80_O_RST = 1;
+ if (zstate & ZST_ACQUIRED) {
while(Z80_I_BUSACK == 1)
;
z80_setup_addrbus_active();
- zstate = RESET_AQRD;
- break;
-
- case RESET_AQRD:
- break;
-
- case RUN:
- Z80_O_BUSREQ = 0;
- while(Z80_I_BUSACK == 1);
- z80_setup_addrbus_active();
- zstate = RUN_AQRD;
- break;
-
- case RUN_AQRD:
- break;
}
- debug("z80_request_bus: state: %02x --> %02x\n", old, zstate);
}
-void z80_release_bus(void)
-{
-#if DEBUG
- zstate_t old = zstate;
-#endif
- switch (zstate) {
- case RESET:
- break;
- case RESET_AQRD:
- z80_setup_dbus_in();
- z80_setup_addrbus_tristate();
- Z80_O_RST = 0;
- Z80_O_BUSREQ = 1;
- zstate = RESET;
- break;
- case RUN:
- break;
- case RUN_AQRD:
- z80_setup_dbus_in();
- z80_setup_addrbus_tristate();
- Z80_O_BUSREQ = 1;
- zstate = RUN;
- break;
- }
-
- debug("z80_release_bus: state: %02x --> %02x\n", old, zstate);
-}
/*
- * Do nothing, if we have the bus allready
- *
- * return previous state
- */
-zstate_t z80_request_bus_save(void)
-{
- zstate_t state;
-
- state = z80_runstate();
- if (!(state & ZST_ACQUIRED))
- z80_request_bus();
-
- return state;
-}
-/*
- * Do nothing, if we had the bus before
- */
-void z80_release_bus_save(zstate_t prev)
-{
- if (!(prev & ZST_ACQUIRED))
- z80_release_bus();
-}
+ + | | | | |
+ + State | RESET | RESET_AQRD | RUNNING | RUNNING_AQRD |
+ + | | | | |
+ + | 0 | 1 | 2 | 3 |
+Event + | | | | |
+----------------+---------------+---------------+---------------+---------------+
+ | | | | |
+Reset | 0 | 0 | 0 | 0 |
+ | | | | |
+ | | | | |
+Request | 1 | | 3 | |
+ | | | | |
+ | | | | |
+Release | | 0 | | 2 |
+ | | | | |
+ | | | | |
+Run | 2 | 3 | | |
+ | | | | |
+ | | | | |
+Restart | | | 2 | 3 |
+ | | | | |
+ | | | | |
+M_Cycle | | | | 3 |
+ | | | | |
+ | | | | |
+*/
-void z80_run(void)
+zstate_t z80_bus_cmd(bus_cmd_t cmd)
{
-#if DEBUG
- zstate_t old = zstate;
-#endif
- switch (zstate) {
- case RESET:
- Z80_O_RST = 1;
- zstate = RUN;
- break;
+ switch (cmd) {
- case RESET_AQRD:
+ case Reset:
z80_setup_dbus_in();
z80_setup_addrbus_tristate();
Z80_O_RST = 0;
- _delay_us(10);
- Z80_O_RST = 1;
- z80_setup_addrbus_active();
- zstate = RUN_AQRD;
+ Z80_O_BUSREQ = 1;
+ zstate = RESET;
break;
- case RUN:
- break;
- case RUN_AQRD:
+ case Request:
+ switch (zstate) {
+ case RESET:
+ Z80_O_BUSREQ = 0;
+ Z80_O_RST = 1;
+ while(Z80_I_BUSACK == 1)
+ ;
+ z80_setup_addrbus_active();
+ zstate = RESET_AQRD;
+ break;
+
+ case RUNNING:
+ Z80_O_BUSREQ = 0;
+ while(Z80_I_BUSACK == 1)
+ ;
+ z80_setup_addrbus_active();
+ zstate = RUNNING_AQRD;
+ break;
+
+ default:
+ break;
+ }
break;
- }
- debug("z80_run: state: %02x --> %02x\n", old, zstate);
-}
+ case Release:
+ switch (zstate) {
+ case RESET_AQRD:
+ z80_setup_dbus_in();
+ z80_setup_addrbus_tristate();
+ Z80_O_RST = 0;
+ Z80_O_BUSREQ = 1;
+ zstate = RESET;
+ break;
+ case RUNNING_AQRD:
+ z80_setup_dbus_in();
+ z80_setup_addrbus_tristate();
+ Z80_O_BUSREQ = 1;
+ zstate = RUNNING;
+ break;
+ default:
+ break;
+ }
+ break;
-void z80_busreq_hpulse(void)
-{
- z80_setup_dbus_in();
- z80_setup_addrbus_tristate();
+ case Run:
+ switch (zstate) {
+ case RESET:
+ Z80_O_RST = 1;
+ zstate = RUNNING;
+ break;
+
+ case RESET_AQRD:
+ z80_setup_dbus_in();
+ z80_setup_addrbus_tristate();
+ z80_reset_pulse();
+ z80_setup_addrbus_active();
+ zstate = RUNNING_AQRD;
+ break;
+ default:
+ break;
+ }
+ break;
- ATOMIC_BLOCK(ATOMIC_RESTORESTATE) {
- Z80_O_BUSREQ = 1;
- Z80_O_BUSREQ = 1; /* 2 AVR clock cycles */
- Z80_O_BUSREQ = 0; /* 2 AVR clock cycles */
- }
+ case Restart:
+ switch (zstate) {
+ case RUNNING:
+ case RUNNING_AQRD:
+ z80_reset_pulse();
+ break;
+ default:
+ break;
+ }
+ break;
- if (zstate & ZST_ACQUIRED) {
- while(Z80_I_BUSACK == 1)
- ;
- z80_setup_addrbus_active();
+ case M_Cycle:
+ switch (zstate) {
+ case RUNNING_AQRD:
+ z80_busreq_hpulse();
+ break;
+ default:
+ break;
+ }
}
+ return zstate;
}
+
/*--------------------------------------------------------------------------*/
static
@@ -550,13 +506,13 @@ DBG_P(2, "z80_memfifo_init: %i, %lx\n", f, adr);
fifo_dsc[f].base = adr;
- z80_request_bus();
+ z80_bus_cmd(Request);
fifo_dsc[f].mask = z80_read(adr + FIFO_BUFSIZE_MASK);
fifo_dsc[f].idx_in = z80_read(adr + FIFO_INDEX_IN);
fifo_dsc[f].idx_out = z80_read(adr + FIFO_INDEX_OUT);
- z80_release_bus();
+ z80_bus_cmd(Release);
}
@@ -569,9 +525,9 @@ int z80_memfifo_is_empty(const fifo_t f)
uint32_t adr = fifo_dsc[f].base + FIFO_INDEX_IN;
uint8_t idx;
- z80_request_bus();
+ z80_bus_cmd(Request);
idx = z80_read(adr);
- z80_release_bus();
+ z80_bus_cmd(Release);
rc = idx == fifo_dsc[f].idx_out;
}
@@ -583,10 +539,10 @@ int z80_memfifo_is_full(const fifo_t f)
int rc = 1;
if (fifo_dsc[f].base != 0) {
- z80_request_bus();
+ z80_bus_cmd(Request);
rc = ((fifo_dsc[f].idx_in + 1) & fifo_dsc[f].mask)
== z80_read(fifo_dsc[f].base+FIFO_INDEX_OUT);
- z80_release_bus();
+ z80_bus_cmd(Release);
}
return rc;
}
@@ -598,12 +554,12 @@ uint8_t z80_memfifo_getc(const fifo_t f)
while (z80_memfifo_is_empty(f))
;
- z80_request_bus();
+ z80_bus_cmd(Request);
idx = fifo_dsc[f].idx_out;
rc = z80_read(fifo_dsc[f].base+idx);
fifo_dsc[f].idx_out = ++idx & fifo_dsc[f].mask;
z80_write(fifo_dsc[f].base+FIFO_INDEX_OUT, fifo_dsc[f].idx_out);
- z80_release_bus();
+ z80_bus_cmd(Release);
return rc;
}
@@ -616,12 +572,12 @@ void z80_memfifo_putc(fifo_t f, uint8_t val)
while (z80_memfifo_is_full(f))
;
- z80_request_bus();
+ z80_bus_cmd(Request);
idx = fifo_dsc[f].idx_in;
z80_write(fifo_dsc[f].base+idx, val);
fifo_dsc[f].idx_in = ++idx & fifo_dsc[f].mask;
z80_write(fifo_dsc[f].base+FIFO_INDEX_IN, fifo_dsc[f].idx_in);
- z80_release_bus();
+ z80_bus_cmd(Release);
}
/*--------------------------------------------------------------------------*/
@@ -687,9 +643,9 @@ void z80_init_msg_fifo(uint32_t addr)
DBG_P(1, "z80_init_msg_fifo: %lx\n", addr);
- z80_request_bus();
+ z80_bus_cmd(Request);
z80_write(addr+FIFO_INDEX_OUT, z80_read(addr+FIFO_INDEX_IN));
- z80_release_bus();
+ z80_bus_cmd(Release);
msg_fifo.base = addr;
}
@@ -705,9 +661,9 @@ int z80_msg_fifo_getc(void)
msg_fifo.count = 0;
if (msg_fifo.base != 0) {
- z80_request_bus();
+ z80_bus_cmd(Request);
z80_write(msg_fifo.base+FIFO_INDEX_OUT, msg_fifo.count);
- z80_release_bus();
+ z80_bus_cmd(Release);
}
}
#endif
diff --git a/avr/z80-if.h b/avr/z80-if.h
index b656447..b02fe23 100644
--- a/avr/z80-if.h
+++ b/avr/z80-if.h
@@ -5,24 +5,26 @@
typedef enum {
RESET = 0x00,
RESET_AQRD = ZST_ACQUIRED,
- RUN = ZST_RUNNING,
- RUN_AQRD = ZST_RUNNING | ZST_ACQUIRED,
+ RUNNING = ZST_RUNNING,
+ RUNNING_AQRD = ZST_RUNNING | ZST_ACQUIRED,
} zstate_t;
+typedef enum {
+ Reset,
+ Request,
+ Release,
+ Run,
+ Restart,
+ M_Cycle
+} bus_cmd_t;
+
typedef enum {LOW, HIGH} level_t;
-zstate_t z80_runstate(void);
+zstate_t z80_bus_state(void);
+zstate_t z80_bus_cmd(bus_cmd_t cmd);
void z80_setup_bus(void);
-void z80_request_bus(void);
-void z80_release_bus(void);
-zstate_t z80_request_bus_save(void);
-void z80_release_bus_save(zstate_t prev);
-void z80_reset(void);
-void z80_reset_pulse(void);
-void z80_run(void);
int z80_stat_reset(void);
//void z80_busreq(level_t level);
-void z80_busreq_hpulse(void);
int z80_stat_halt(void);
void z80_write(uint32_t addr, uint8_t data);