mirror of
https://github.com/hoglet67/AtomBusMon.git
synced 2025-02-21 19:29:07 +00:00
Working Z80 memory access and disassembler in the small GODIL, incremented version to 0.44
Change-Id: I718be7476ec330743c206e737389856fc4b41fc8
This commit is contained in:
parent
e4e0f864df
commit
0c0fde6a32
@ -4,9 +4,7 @@
|
||||
#include <ctype.h>
|
||||
#include <avr/pgmspace.h>
|
||||
|
||||
#include "hd44780.h"
|
||||
#include "status.h"
|
||||
|
||||
#include "AtomBusMon.h"
|
||||
|
||||
#if (CPU == Z80)
|
||||
#define NAME "ICE-T80"
|
||||
@ -14,198 +12,7 @@
|
||||
#define NAME "ICE-T65"
|
||||
#endif
|
||||
|
||||
#ifdef CPUEMBEDDED
|
||||
|
||||
unsigned int disMem(unsigned int addr);
|
||||
|
||||
enum
|
||||
{
|
||||
IMP, IMPA, MARK2, BRA, IMM, ZP, ZPX, ZPY, INDX, INDY, IND, MARK3, ABS, ABSX, ABSY, IND16, IND1X
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
I_ADC,
|
||||
I_AND,
|
||||
I_ASL,
|
||||
I_BCC,
|
||||
I_BCS,
|
||||
I_BEQ,
|
||||
I_BIT,
|
||||
I_BMI,
|
||||
I_BNE,
|
||||
I_BPL,
|
||||
I_BRA,
|
||||
I_BRK,
|
||||
I_BVC,
|
||||
I_BVS,
|
||||
I_CLC,
|
||||
I_CLD,
|
||||
I_CLI,
|
||||
I_CLV,
|
||||
I_CMP,
|
||||
I_CPX,
|
||||
I_CPY,
|
||||
I_DEC,
|
||||
I_DEX,
|
||||
I_DEY,
|
||||
I_EOR,
|
||||
I_INC,
|
||||
I_INX,
|
||||
I_INY,
|
||||
I_JMP,
|
||||
I_JSR,
|
||||
I_LDA,
|
||||
I_LDX,
|
||||
I_LDY,
|
||||
I_LSR,
|
||||
I_NOP,
|
||||
I_ORA,
|
||||
I_PHA,
|
||||
I_PHP,
|
||||
I_PHX,
|
||||
I_PHY,
|
||||
I_PLA,
|
||||
I_PLP,
|
||||
I_PLX,
|
||||
I_PLY,
|
||||
I_ROL,
|
||||
I_ROR,
|
||||
I_RTI,
|
||||
I_RTS,
|
||||
I_SBC,
|
||||
I_SEC,
|
||||
I_SED,
|
||||
I_SEI,
|
||||
I_STA,
|
||||
I_STP,
|
||||
I_STX,
|
||||
I_STY,
|
||||
I_STZ,
|
||||
I_TAX,
|
||||
I_TAY,
|
||||
I_TRB,
|
||||
I_TSB,
|
||||
I_TSX,
|
||||
I_TXA,
|
||||
I_TXS,
|
||||
I_TYA,
|
||||
I_WAI,
|
||||
I_XXX
|
||||
};
|
||||
|
||||
char *opStrings[67] = {
|
||||
"ADC",
|
||||
"AND",
|
||||
"ASL",
|
||||
"BCC",
|
||||
"BCS",
|
||||
"BEQ",
|
||||
"BIT",
|
||||
"BMI",
|
||||
"BNE",
|
||||
"BPL",
|
||||
"BRA",
|
||||
"BRK",
|
||||
"BVC",
|
||||
"BVS",
|
||||
"CLC",
|
||||
"CLD",
|
||||
"CLI",
|
||||
"CLV",
|
||||
"CMP",
|
||||
"CPX",
|
||||
"CPY",
|
||||
"DEC",
|
||||
"DEX",
|
||||
"DEY",
|
||||
"EOR",
|
||||
"INC",
|
||||
"INX",
|
||||
"INY",
|
||||
"JMP",
|
||||
"JSR",
|
||||
"LDA",
|
||||
"LDX",
|
||||
"LDY",
|
||||
"LSR",
|
||||
"NOP",
|
||||
"ORA",
|
||||
"PHA",
|
||||
"PHP",
|
||||
"PHX",
|
||||
"PHY",
|
||||
"PLA",
|
||||
"PLP",
|
||||
"PLX",
|
||||
"PLY",
|
||||
"ROL",
|
||||
"ROR",
|
||||
"RTI",
|
||||
"RTS",
|
||||
"SBC",
|
||||
"SEC",
|
||||
"SED",
|
||||
"SEI",
|
||||
"STA",
|
||||
"STP",
|
||||
"STX",
|
||||
"STY",
|
||||
"STZ",
|
||||
"TAX",
|
||||
"TAY",
|
||||
"TRB",
|
||||
"TSB",
|
||||
"TSX",
|
||||
"TXA",
|
||||
"TXS",
|
||||
"TYA",
|
||||
"WAI",
|
||||
"---"
|
||||
};
|
||||
|
||||
unsigned char dopname[256] =
|
||||
{
|
||||
/*00*/ I_BRK, I_ORA, I_XXX, I_XXX, I_TSB, I_ORA, I_ASL, I_XXX, I_PHP, I_ORA, I_ASL, I_XXX, I_TSB, I_ORA, I_ASL, I_XXX,
|
||||
/*10*/ I_BPL, I_ORA, I_ORA, I_XXX, I_TRB, I_ORA, I_ASL, I_XXX, I_CLC, I_ORA, I_INC, I_XXX, I_TRB, I_ORA, I_ASL, I_XXX,
|
||||
/*20*/ I_JSR, I_AND, I_XXX, I_XXX, I_BIT, I_AND, I_ROL, I_XXX, I_PLP, I_AND, I_ROL, I_XXX, I_BIT, I_AND, I_ROL, I_XXX,
|
||||
/*30*/ I_BMI, I_AND, I_AND, I_XXX, I_BIT, I_AND, I_ROL, I_XXX, I_SEC, I_AND, I_DEC, I_XXX, I_BIT, I_AND, I_ROL, I_XXX,
|
||||
/*40*/ I_RTI, I_EOR, I_XXX, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX, I_PHA, I_EOR, I_LSR, I_XXX, I_JMP, I_EOR, I_LSR, I_XXX,
|
||||
/*50*/ I_BVC, I_EOR, I_EOR, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX, I_CLI, I_EOR, I_PHY, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX,
|
||||
/*60*/ I_RTS, I_ADC, I_XXX, I_XXX, I_STZ, I_ADC, I_ROR, I_XXX, I_PLA, I_ADC, I_ROR, I_XXX, I_JMP, I_ADC, I_ROR, I_XXX,
|
||||
/*70*/ I_BVS, I_ADC, I_ADC, I_XXX, I_STZ, I_ADC, I_ROR, I_XXX, I_SEI, I_ADC, I_PLY, I_XXX, I_JMP, I_ADC, I_ROR, I_XXX,
|
||||
/*80*/ I_BRA, I_STA, I_XXX, I_XXX, I_STY, I_STA, I_STX, I_XXX, I_DEY, I_BIT, I_TXA, I_XXX, I_STY, I_STA, I_STX, I_XXX,
|
||||
/*90*/ I_BCC, I_STA, I_STA, I_XXX, I_STY, I_STA, I_STX, I_XXX, I_TYA, I_STA, I_TXS, I_XXX, I_STZ, I_STA, I_STZ, I_XXX,
|
||||
/*A0*/ I_LDY, I_LDA, I_LDX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX, I_TAY, I_LDA, I_TAX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX,
|
||||
/*B0*/ I_BCS, I_LDA, I_LDA, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX, I_CLV, I_LDA, I_TSX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX,
|
||||
/*C0*/ I_CPY, I_CMP, I_XXX, I_XXX, I_CPY, I_CMP, I_DEC, I_XXX, I_INY, I_CMP, I_DEX, I_WAI, I_CPY, I_CMP, I_DEC, I_XXX,
|
||||
/*D0*/ I_BNE, I_CMP, I_CMP, I_XXX, I_XXX, I_CMP, I_DEC, I_XXX, I_CLD, I_CMP, I_PHX, I_STP, I_XXX, I_CMP, I_DEC, I_XXX,
|
||||
/*E0*/ I_CPX, I_SBC, I_XXX, I_XXX, I_CPX, I_SBC, I_INC, I_XXX, I_INX, I_SBC, I_NOP, I_XXX, I_CPX, I_SBC, I_INC, I_XXX,
|
||||
/*F0*/ I_BEQ, I_SBC, I_SBC, I_XXX, I_XXX, I_SBC, I_INC, I_XXX, I_SED, I_SBC, I_PLX, I_XXX, I_XXX, I_SBC, I_INC, I_XXX
|
||||
};
|
||||
|
||||
unsigned char dopaddr[256] =
|
||||
{
|
||||
/*00*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*10*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMPA, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*20*/ ABS, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*30*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPX, IMP, IMP, ABSY, IMPA, IMP, ABSX, ABSX, ABSX, IMP,
|
||||
/*40*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*50*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*60*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, IND16, ABS, ABS, IMP,
|
||||
/*70*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, IND1X, ABSX, ABSX, IMP,
|
||||
/*80*/ BRA, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*90*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPY, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*A0*/ IMM, INDX, IMM, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*B0*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPY, IMP, IMP, ABSY, IMP, IMP, ABSX, ABSX, ABSY, IMP,
|
||||
/*C0*/ IMM, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*D0*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*E0*/ IMM, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*F0*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP
|
||||
};
|
||||
#endif
|
||||
|
||||
#define CRC_POLY 0x002d
|
||||
#define CRC_POLY 0x002d
|
||||
|
||||
#define CTRL_PORT PORTB
|
||||
#define CTRL_DDR DDRB
|
||||
@ -242,20 +49,29 @@ unsigned char dopaddr[256] =
|
||||
|
||||
// Processor registers
|
||||
#if (CPU == Z80)
|
||||
#define OFFSET_REG_F 16
|
||||
#define OFFSET_REG_A 17
|
||||
#define OFFSET_REG_Fp 18
|
||||
#define OFFSET_REG_Ap 19
|
||||
#define OFFSET_REG_BC 32
|
||||
#define OFFSET_REG_DE 34
|
||||
#define OFFSET_REG_HL 36
|
||||
#define OFFSET_REG_IX 38
|
||||
#define OFFSET_REG_BCp 40
|
||||
#define OFFSET_REG_DEp 42
|
||||
#define OFFSET_REG_HLp 44
|
||||
#define OFFSET_REG_IY 46
|
||||
#define OFFSET_REG_AF 48
|
||||
#define OFFSET_REG_AFp 50
|
||||
#define OFFSET_REG_SP 52
|
||||
#define OFFSET_REG_PC 54
|
||||
#define OFFSET_REG_I 56
|
||||
#define OFFSET_REG_R 57
|
||||
#define OFFSET_REG_IFF 58
|
||||
#else
|
||||
#define OFFSET_REG_A 16
|
||||
#define OFFSET_REG_X 17
|
||||
#define OFFSET_REG_Y 18
|
||||
#define OFFSET_REG_P 19
|
||||
#define OFFSET_REG_A 32
|
||||
#define OFFSET_REG_X 33
|
||||
#define OFFSET_REG_Y 34
|
||||
#define OFFSET_REG_P 35
|
||||
#define OFFSET_REG_SP 36
|
||||
#define OFFSET_REG_PC 38
|
||||
#endif
|
||||
#define OFFSET_REG_SPL 20
|
||||
#define OFFSET_REG_SPH 21
|
||||
#define OFFSET_REG_PCL 22
|
||||
#define OFFSET_REG_PCH 23
|
||||
|
||||
// Commands
|
||||
// 000x Enable/Disable single strpping
|
||||
@ -280,7 +96,7 @@ unsigned char dopaddr[256] =
|
||||
// Control bits
|
||||
#define CMD_MASK 0x3F
|
||||
#define CMD_EDGE 0x20
|
||||
#define MUXSEL_MASK 0x1F
|
||||
#define MUXSEL_MASK 0x3F
|
||||
#define MUXSEL_BIT 0
|
||||
|
||||
// Status bits
|
||||
@ -344,17 +160,18 @@ char *triggerStrings[NUM_TRIGGERS] = {
|
||||
};
|
||||
|
||||
|
||||
#define VERSION "0.43"
|
||||
#define VERSION "0.44"
|
||||
|
||||
#ifdef CPUEMBEDDED
|
||||
#define NUM_CMDS 22
|
||||
#if (CPU != Z80)
|
||||
#define NUM_CMDS 22
|
||||
#else
|
||||
#define NUM_CMDS 21
|
||||
#endif
|
||||
#else
|
||||
#define NUM_CMDS 14
|
||||
#define NUM_CMDS 14
|
||||
#endif
|
||||
|
||||
#define MAXBKPTS 8
|
||||
|
||||
int numbkpts = 0;
|
||||
|
||||
long trace;
|
||||
long instructions = 1;
|
||||
@ -367,58 +184,18 @@ char statusString[8] = "SZIH-P-C";
|
||||
char statusString[8] = "NV-BDIZC";
|
||||
#endif
|
||||
|
||||
unsigned int breakpoints[MAXBKPTS] = {
|
||||
#if (CPU != Z80)
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
#endif
|
||||
0
|
||||
};
|
||||
int numbkpts = 0;
|
||||
|
||||
unsigned int masks[MAXBKPTS] = {
|
||||
#if (CPU != Z80)
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
#if (CPU == Z80)
|
||||
#define MAXBKPTS 4
|
||||
#else
|
||||
#define MAXBKPTS 8
|
||||
#endif
|
||||
0
|
||||
};
|
||||
|
||||
unsigned int modes[MAXBKPTS] = {
|
||||
#if (CPU != Z80)
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
#endif
|
||||
0
|
||||
};
|
||||
|
||||
int triggers[MAXBKPTS] = {
|
||||
#if (CPU != Z80)
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
#endif
|
||||
0
|
||||
};
|
||||
|
||||
unsigned int breakpoints[MAXBKPTS];
|
||||
unsigned int masks[MAXBKPTS];
|
||||
unsigned int modes[MAXBKPTS];
|
||||
int triggers[MAXBKPTS];
|
||||
|
||||
char *cmdStrings[NUM_CMDS] = {
|
||||
"help",
|
||||
@ -431,7 +208,9 @@ char *cmdStrings[NUM_CMDS] = {
|
||||
"write",
|
||||
"fill",
|
||||
"crc",
|
||||
#if (CPU != Z80)
|
||||
"test",
|
||||
#endif
|
||||
#endif
|
||||
"reset",
|
||||
"step",
|
||||
@ -687,81 +466,6 @@ void writeByteInc() {
|
||||
hwCmd(CMD_WR_MEM_INC, 0);
|
||||
}
|
||||
|
||||
unsigned int disassemble(unsigned int addr)
|
||||
{
|
||||
unsigned int temp;
|
||||
unsigned int op = readByteInc();
|
||||
int mode = dopaddr[op];
|
||||
unsigned int p1 = (mode > MARK2) ? readByteInc() : 0;
|
||||
unsigned int p2 = (mode > MARK3) ? readByteInc() : 0;
|
||||
|
||||
log0("%04X : %s ", addr, opStrings[dopname[op]]);
|
||||
switch (mode)
|
||||
{
|
||||
case IMP:
|
||||
log0(" ");
|
||||
break;
|
||||
case IMPA:
|
||||
log0("A ");
|
||||
break;
|
||||
case BRA:
|
||||
temp = addr + 2 + (signed char)p1;
|
||||
log0("%04X ", temp);
|
||||
addr++;
|
||||
break;
|
||||
case IMM:
|
||||
log0("#%02X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZP:
|
||||
log0("%02X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZPX:
|
||||
log0("%02X,X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZPY:
|
||||
log0("%02X,Y ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case IND:
|
||||
log0("(%02X) ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case INDX:
|
||||
log0("(%02X,X) ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case INDY:
|
||||
log0("(%02X),Y ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ABS:
|
||||
log0("%02X%02X ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case ABSX:
|
||||
log0("%02X%02X,X ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case ABSY:
|
||||
log0("%02X%02X,Y ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case IND16:
|
||||
log0("(%02X%02X) ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case IND1X:
|
||||
log0("(%02X%02X,X)", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
}
|
||||
log0("\n");
|
||||
addr++;
|
||||
return addr;
|
||||
}
|
||||
|
||||
unsigned int disMem(unsigned int addr) {
|
||||
loadAddr(addr);
|
||||
@ -838,20 +542,34 @@ void doCmdReset(char *params) {
|
||||
void doCmdRegs(char *params) {
|
||||
int i;
|
||||
#if (CPU == Z80)
|
||||
unsigned int p = hwRead16(OFFSET_REG_F);
|
||||
log0("Z80 Registers:\n AF=%04X AF'=%04X SP=%04X PC=%04X\n",
|
||||
unsigned int p = hwRead16(OFFSET_REG_AF);
|
||||
log0("Z80 Registers:\n");
|
||||
log0(" AF=%04X BC=%04X DE=%04X HL=%04X\n",
|
||||
p,
|
||||
hwRead16(OFFSET_REG_Fp),
|
||||
hwRead16(OFFSET_REG_SPL),
|
||||
hwRead16(OFFSET_REG_PCL));
|
||||
hwRead16(OFFSET_REG_BC),
|
||||
hwRead16(OFFSET_REG_DE),
|
||||
hwRead16(OFFSET_REG_HL));
|
||||
log0(" 'AF=%04X 'BC=%04X 'DE=%04X 'HL=%04X\n",
|
||||
hwRead16(OFFSET_REG_AFp),
|
||||
hwRead16(OFFSET_REG_BCp),
|
||||
hwRead16(OFFSET_REG_DEp),
|
||||
hwRead16(OFFSET_REG_HLp));
|
||||
log0(" IX=%04X IY=%04X PC=%04X SP=%04X I=%02X R=%02X IFF=%02X\n",
|
||||
hwRead16(OFFSET_REG_IX),
|
||||
hwRead16(OFFSET_REG_IY),
|
||||
hwRead16(OFFSET_REG_PC),
|
||||
hwRead16(OFFSET_REG_SP),
|
||||
hwRead8(OFFSET_REG_I),
|
||||
hwRead8(OFFSET_REG_R),
|
||||
hwRead8(OFFSET_REG_IFF));
|
||||
#else
|
||||
unsigned int p = hwRead8(OFFSET_REG_P);
|
||||
log0("6502 Registers:\n A=%02X X=%02X Y=%02X SP=%04X PC=%04X\n",
|
||||
hwRead8(OFFSET_REG_A),
|
||||
hwRead8(OFFSET_REG_X),
|
||||
hwRead8(OFFSET_REG_Y),
|
||||
hwRead16(OFFSET_REG_SPL),
|
||||
hwRead16(OFFSET_REG_PCL));
|
||||
hwRead16(OFFSET_REG_SP),
|
||||
hwRead16(OFFSET_REG_PC));
|
||||
#endif
|
||||
char *sp = statusString;
|
||||
log0(" Status: ");
|
||||
@ -965,6 +683,7 @@ void doCmdCrc(char *params) {
|
||||
log0("crc: %04X\n", crc);
|
||||
}
|
||||
|
||||
#if (CPU != Z80)
|
||||
unsigned int getData(unsigned int addr, int data) {
|
||||
if (data == -1) {
|
||||
// checkerboard
|
||||
@ -1049,6 +768,8 @@ void doCmdTest(char *params) {
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
void doCmdTrace(char *params) {
|
||||
long i;
|
||||
sscanf(params, "%ld", &i);
|
||||
@ -1304,7 +1025,9 @@ void (*cmdFuncs[NUM_CMDS])(char *params) = {
|
||||
doCmdWrite,
|
||||
doCmdFill,
|
||||
doCmdCrc,
|
||||
#if (CPU != Z80)
|
||||
doCmdTest,
|
||||
#endif
|
||||
#endif
|
||||
doCmdReset,
|
||||
doCmdStep,
|
||||
|
22
firmware/AtomBusMon.h
Normal file
22
firmware/AtomBusMon.h
Normal file
@ -0,0 +1,22 @@
|
||||
#ifndef __ATOMBUSMON_DEFINES__
|
||||
#define __ATOMBUSMON_DEFINES__
|
||||
|
||||
#include "status.h"
|
||||
#include "dis.h"
|
||||
|
||||
#ifdef LCD
|
||||
#include "hd44780.h"
|
||||
#endif
|
||||
|
||||
#ifdef CPUEMBEDDED
|
||||
unsigned int disMem(unsigned int addr);
|
||||
void loadData(unsigned int data);
|
||||
void loadAddr(unsigned int addr);
|
||||
unsigned int readByte();
|
||||
unsigned int readByteInc();
|
||||
void writeByte();
|
||||
void writeByteInc();
|
||||
unsigned int disMem(unsigned int addr);
|
||||
#endif
|
||||
|
||||
#endif
|
@ -25,7 +25,7 @@ OBJCOPY=avr-objcopy
|
||||
|
||||
CFLAGS=-DCPU=6502 -DCPUEMBEDDED -DF_CPU=${F_CPU}UL -DSERIAL_STATUS -DCOOKED_SERIAL -DNOUSART1 -mmcu=$(MCU) -Wall -Os -mcall-prologues
|
||||
|
||||
OBJECTS=AtomBusMon.o hd44780.o status.o
|
||||
OBJECTS=AtomBusMon.o dis6502.o status.o
|
||||
|
||||
build: avr6502cpu.bit
|
||||
|
||||
|
@ -25,7 +25,7 @@ OBJCOPY=avr-objcopy
|
||||
|
||||
CFLAGS=-DCPU=Z80 -DCPUEMBEDDED -DF_CPU=${F_CPU}UL -DSERIAL_STATUS -DCOOKED_SERIAL -DNOUSART1 -mmcu=$(MCU) -Wall -Os -mcall-prologues
|
||||
|
||||
OBJECTS=AtomBusMon.o hd44780.o status.o
|
||||
OBJECTS=AtomBusMon.o disz80.o status.o
|
||||
|
||||
build: avrz80cpu.bit
|
||||
|
||||
|
6
firmware/dis.h
Normal file
6
firmware/dis.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef __DIS_DEFINES__
|
||||
#define __DIS_DEFINES__
|
||||
|
||||
unsigned int disassemble(unsigned int addr);
|
||||
|
||||
#endif
|
263
firmware/dis6502.c
Normal file
263
firmware/dis6502.c
Normal file
@ -0,0 +1,263 @@
|
||||
#include "AtomBusMon.h"
|
||||
|
||||
enum
|
||||
{
|
||||
IMP, IMPA, MARK2, BRA, IMM, ZP, ZPX, ZPY, INDX, INDY, IND, MARK3, ABS, ABSX, ABSY, IND16, IND1X
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
I_ADC,
|
||||
I_AND,
|
||||
I_ASL,
|
||||
I_BCC,
|
||||
I_BCS,
|
||||
I_BEQ,
|
||||
I_BIT,
|
||||
I_BMI,
|
||||
I_BNE,
|
||||
I_BPL,
|
||||
I_BRA,
|
||||
I_BRK,
|
||||
I_BVC,
|
||||
I_BVS,
|
||||
I_CLC,
|
||||
I_CLD,
|
||||
I_CLI,
|
||||
I_CLV,
|
||||
I_CMP,
|
||||
I_CPX,
|
||||
I_CPY,
|
||||
I_DEC,
|
||||
I_DEX,
|
||||
I_DEY,
|
||||
I_EOR,
|
||||
I_INC,
|
||||
I_INX,
|
||||
I_INY,
|
||||
I_JMP,
|
||||
I_JSR,
|
||||
I_LDA,
|
||||
I_LDX,
|
||||
I_LDY,
|
||||
I_LSR,
|
||||
I_NOP,
|
||||
I_ORA,
|
||||
I_PHA,
|
||||
I_PHP,
|
||||
I_PHX,
|
||||
I_PHY,
|
||||
I_PLA,
|
||||
I_PLP,
|
||||
I_PLX,
|
||||
I_PLY,
|
||||
I_ROL,
|
||||
I_ROR,
|
||||
I_RTI,
|
||||
I_RTS,
|
||||
I_SBC,
|
||||
I_SEC,
|
||||
I_SED,
|
||||
I_SEI,
|
||||
I_STA,
|
||||
I_STP,
|
||||
I_STX,
|
||||
I_STY,
|
||||
I_STZ,
|
||||
I_TAX,
|
||||
I_TAY,
|
||||
I_TRB,
|
||||
I_TSB,
|
||||
I_TSX,
|
||||
I_TXA,
|
||||
I_TXS,
|
||||
I_TYA,
|
||||
I_WAI,
|
||||
I_XXX
|
||||
};
|
||||
|
||||
char *opStrings[67] = {
|
||||
"ADC",
|
||||
"AND",
|
||||
"ASL",
|
||||
"BCC",
|
||||
"BCS",
|
||||
"BEQ",
|
||||
"BIT",
|
||||
"BMI",
|
||||
"BNE",
|
||||
"BPL",
|
||||
"BRA",
|
||||
"BRK",
|
||||
"BVC",
|
||||
"BVS",
|
||||
"CLC",
|
||||
"CLD",
|
||||
"CLI",
|
||||
"CLV",
|
||||
"CMP",
|
||||
"CPX",
|
||||
"CPY",
|
||||
"DEC",
|
||||
"DEX",
|
||||
"DEY",
|
||||
"EOR",
|
||||
"INC",
|
||||
"INX",
|
||||
"INY",
|
||||
"JMP",
|
||||
"JSR",
|
||||
"LDA",
|
||||
"LDX",
|
||||
"LDY",
|
||||
"LSR",
|
||||
"NOP",
|
||||
"ORA",
|
||||
"PHA",
|
||||
"PHP",
|
||||
"PHX",
|
||||
"PHY",
|
||||
"PLA",
|
||||
"PLP",
|
||||
"PLX",
|
||||
"PLY",
|
||||
"ROL",
|
||||
"ROR",
|
||||
"RTI",
|
||||
"RTS",
|
||||
"SBC",
|
||||
"SEC",
|
||||
"SED",
|
||||
"SEI",
|
||||
"STA",
|
||||
"STP",
|
||||
"STX",
|
||||
"STY",
|
||||
"STZ",
|
||||
"TAX",
|
||||
"TAY",
|
||||
"TRB",
|
||||
"TSB",
|
||||
"TSX",
|
||||
"TXA",
|
||||
"TXS",
|
||||
"TYA",
|
||||
"WAI",
|
||||
"---"
|
||||
};
|
||||
|
||||
unsigned char dopname[256] =
|
||||
{
|
||||
/*00*/ I_BRK, I_ORA, I_XXX, I_XXX, I_TSB, I_ORA, I_ASL, I_XXX, I_PHP, I_ORA, I_ASL, I_XXX, I_TSB, I_ORA, I_ASL, I_XXX,
|
||||
/*10*/ I_BPL, I_ORA, I_ORA, I_XXX, I_TRB, I_ORA, I_ASL, I_XXX, I_CLC, I_ORA, I_INC, I_XXX, I_TRB, I_ORA, I_ASL, I_XXX,
|
||||
/*20*/ I_JSR, I_AND, I_XXX, I_XXX, I_BIT, I_AND, I_ROL, I_XXX, I_PLP, I_AND, I_ROL, I_XXX, I_BIT, I_AND, I_ROL, I_XXX,
|
||||
/*30*/ I_BMI, I_AND, I_AND, I_XXX, I_BIT, I_AND, I_ROL, I_XXX, I_SEC, I_AND, I_DEC, I_XXX, I_BIT, I_AND, I_ROL, I_XXX,
|
||||
/*40*/ I_RTI, I_EOR, I_XXX, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX, I_PHA, I_EOR, I_LSR, I_XXX, I_JMP, I_EOR, I_LSR, I_XXX,
|
||||
/*50*/ I_BVC, I_EOR, I_EOR, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX, I_CLI, I_EOR, I_PHY, I_XXX, I_XXX, I_EOR, I_LSR, I_XXX,
|
||||
/*60*/ I_RTS, I_ADC, I_XXX, I_XXX, I_STZ, I_ADC, I_ROR, I_XXX, I_PLA, I_ADC, I_ROR, I_XXX, I_JMP, I_ADC, I_ROR, I_XXX,
|
||||
/*70*/ I_BVS, I_ADC, I_ADC, I_XXX, I_STZ, I_ADC, I_ROR, I_XXX, I_SEI, I_ADC, I_PLY, I_XXX, I_JMP, I_ADC, I_ROR, I_XXX,
|
||||
/*80*/ I_BRA, I_STA, I_XXX, I_XXX, I_STY, I_STA, I_STX, I_XXX, I_DEY, I_BIT, I_TXA, I_XXX, I_STY, I_STA, I_STX, I_XXX,
|
||||
/*90*/ I_BCC, I_STA, I_STA, I_XXX, I_STY, I_STA, I_STX, I_XXX, I_TYA, I_STA, I_TXS, I_XXX, I_STZ, I_STA, I_STZ, I_XXX,
|
||||
/*A0*/ I_LDY, I_LDA, I_LDX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX, I_TAY, I_LDA, I_TAX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX,
|
||||
/*B0*/ I_BCS, I_LDA, I_LDA, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX, I_CLV, I_LDA, I_TSX, I_XXX, I_LDY, I_LDA, I_LDX, I_XXX,
|
||||
/*C0*/ I_CPY, I_CMP, I_XXX, I_XXX, I_CPY, I_CMP, I_DEC, I_XXX, I_INY, I_CMP, I_DEX, I_WAI, I_CPY, I_CMP, I_DEC, I_XXX,
|
||||
/*D0*/ I_BNE, I_CMP, I_CMP, I_XXX, I_XXX, I_CMP, I_DEC, I_XXX, I_CLD, I_CMP, I_PHX, I_STP, I_XXX, I_CMP, I_DEC, I_XXX,
|
||||
/*E0*/ I_CPX, I_SBC, I_XXX, I_XXX, I_CPX, I_SBC, I_INC, I_XXX, I_INX, I_SBC, I_NOP, I_XXX, I_CPX, I_SBC, I_INC, I_XXX,
|
||||
/*F0*/ I_BEQ, I_SBC, I_SBC, I_XXX, I_XXX, I_SBC, I_INC, I_XXX, I_SED, I_SBC, I_PLX, I_XXX, I_XXX, I_SBC, I_INC, I_XXX
|
||||
};
|
||||
|
||||
unsigned char dopaddr[256] =
|
||||
{
|
||||
/*00*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*10*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMPA, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*20*/ ABS, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*30*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPX, IMP, IMP, ABSY, IMPA, IMP, ABSX, ABSX, ABSX, IMP,
|
||||
/*40*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, ABS, ABS, ABS, IMP,
|
||||
/*50*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*60*/ IMP, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMPA, IMP, IND16, ABS, ABS, IMP,
|
||||
/*70*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, IND1X, ABSX, ABSX, IMP,
|
||||
/*80*/ BRA, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*90*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPY, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*A0*/ IMM, INDX, IMM, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*B0*/ BRA, INDY, IND, IMP, ZPX, ZPX, ZPY, IMP, IMP, ABSY, IMP, IMP, ABSX, ABSX, ABSY, IMP,
|
||||
/*C0*/ IMM, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*D0*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP,
|
||||
/*E0*/ IMM, INDX, IMP, IMP, ZP, ZP, ZP, IMP, IMP, IMM, IMP, IMP, ABS, ABS, ABS, IMP,
|
||||
/*F0*/ BRA, INDY, IND, IMP, ZP, ZPX, ZPX, IMP, IMP, ABSY, IMP, IMP, ABS, ABSX, ABSX, IMP
|
||||
};
|
||||
|
||||
unsigned int disassemble(unsigned int addr)
|
||||
{
|
||||
unsigned int temp;
|
||||
unsigned int op = readByteInc();
|
||||
int mode = dopaddr[op];
|
||||
unsigned int p1 = (mode > MARK2) ? readByteInc() : 0;
|
||||
unsigned int p2 = (mode > MARK3) ? readByteInc() : 0;
|
||||
|
||||
log0("%04X : %s ", addr, opStrings[dopname[op]]);
|
||||
switch (mode)
|
||||
{
|
||||
case IMP:
|
||||
log0(" ");
|
||||
break;
|
||||
case IMPA:
|
||||
log0("A ");
|
||||
break;
|
||||
case BRA:
|
||||
temp = addr + 2 + (signed char)p1;
|
||||
log0("%04X ", temp);
|
||||
addr++;
|
||||
break;
|
||||
case IMM:
|
||||
log0("#%02X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZP:
|
||||
log0("%02X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZPX:
|
||||
log0("%02X,X ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ZPY:
|
||||
log0("%02X,Y ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case IND:
|
||||
log0("(%02X) ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case INDX:
|
||||
log0("(%02X,X) ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case INDY:
|
||||
log0("(%02X),Y ", p1);
|
||||
addr++;
|
||||
break;
|
||||
case ABS:
|
||||
log0("%02X%02X ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case ABSX:
|
||||
log0("%02X%02X,X ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case ABSY:
|
||||
log0("%02X%02X,Y ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case IND16:
|
||||
log0("(%02X%02X) ", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
case IND1X:
|
||||
log0("(%02X%02X,X)", p2, p1);
|
||||
addr += 2;
|
||||
break;
|
||||
}
|
||||
log0("\n");
|
||||
addr++;
|
||||
return addr;
|
||||
}
|
624
firmware/disz80.c
Normal file
624
firmware/disz80.c
Normal file
@ -0,0 +1,624 @@
|
||||
/* Z80 disassembler
|
||||
|
||||
*** Copyright: 1994-1996 Günter Woigk
|
||||
mailto:kio@little-bat.de
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
|
||||
Permission to use, copy, modify, distribute, and sell this software and
|
||||
its documentation for any purpose is hereby granted without fee, provided
|
||||
that the above copyright notice appear in all copies and that both that
|
||||
copyright notice and this permission notice appear in supporting
|
||||
documentation, and that the name of the copyright holder not be used
|
||||
in advertising or publicity pertaining to distribution of the software
|
||||
without specific, written prior permission. The copyright holder makes no
|
||||
representations about the suitability of this software for any purpose.
|
||||
It is provided "as is" without express or implied warranty.
|
||||
|
||||
THE COPYRIGHT HOLDER DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
|
||||
INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
|
||||
EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY SPECIAL, INDIRECT OR
|
||||
CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
|
||||
DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
|
||||
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
30.Jan.95: Started work on disassembler stuff KIO !
|
||||
02.Jun.95: Reworked completely KIO !
|
||||
20.Oct.01 revised for CW7Pro and ANSI C compliance hdusel@bnv-gz.de
|
||||
*/
|
||||
|
||||
#include <string.h>
|
||||
#include "AtomBusMon.h"
|
||||
|
||||
#define legal 0
|
||||
#define illegal 1
|
||||
#define weird 2
|
||||
|
||||
#undef RR
|
||||
#undef IM
|
||||
#undef RH
|
||||
#undef RL
|
||||
#undef BC
|
||||
#undef DE
|
||||
#undef HL
|
||||
#undef IX
|
||||
#undef IY
|
||||
#undef SP
|
||||
#undef PC
|
||||
#undef XH
|
||||
#undef XL
|
||||
#undef YH
|
||||
#undef YL
|
||||
#undef ADC
|
||||
|
||||
// ---- opcode definitions ------------------------------------------------------------------
|
||||
|
||||
enum {
|
||||
NIX, NOP, LD, INC, DEC, RLCA, EX, ADD,
|
||||
RRCA, DJNZ, RLA, JR, RRA, DAA, CPL, HALT,
|
||||
SCF, CCF, RLC, RRC, RL, RR, SLA, SRA,
|
||||
SLL, SRL, IN, OUT, SBC, NEG, RETN, IM,
|
||||
ADC, RETI, RRD, RLD, SUB, AND, XOR,
|
||||
OR, CP, BIT, RES, SET, LDI, CPI, INI,
|
||||
OUTI, LDD, CPD, IND, OUTD, LDIR, CPIR, INIR,
|
||||
OTIR, LDDR, CPDR, INDR, OTDR, RET, POP, JP,
|
||||
CALL, PUSH, RST, PFX, EXX, DI, EI,
|
||||
BC, DE, HL, IX, IY, SP, AF, AF2,
|
||||
B, C, D, E, H, L, XHL, A, // <- KEEP THIS ORDER!
|
||||
XBC, XDE, R, I, XC, XSP, PC, F,
|
||||
N0, N1, N2, N3, N4, N5, N6, N7,
|
||||
Z, NZ, NC, PO, PE, M, P,
|
||||
N, NN, XNN, XN, DIS, CB, ED,
|
||||
XH, XL, YH, YL, XIX, XIY
|
||||
};
|
||||
|
||||
char* word[] =
|
||||
{ "", "NOP", "LD", "INC", "DEC", "RLCA", "EX", "ADD",
|
||||
"RRCA", "DJNZ", "RLA", "JR", "RRA", "DAA", "CPL", "HALT",
|
||||
"SCF", "CCF", "RLC", "RRC", "RL", "RR", "SLA", "SRA",
|
||||
"SLL", "SRL", "IN", "OUT", "SBC", "NEG", "RETN", "IM",
|
||||
"ADC", "RETI", "RRD", "RLD", "SUB", "AND", "XOR",
|
||||
"OR", "CP", "BIT", "RES", "SET", "LDI", "CPI", "INI",
|
||||
"OUTI", "LDD", "CPD", "IND", "OUTD", "LDIR", "CPIR", "INIR",
|
||||
"OTIR", "LDDR", "CPDR", "INDR", "OTDR", "RET", "POP", "JP",
|
||||
"CALL", "PUSH", "RST", "PREFIX", "EXX", "DI", "EI",
|
||||
"BC", "DE", "HL", "IX", "IY", "SP", "AF", "AF'",
|
||||
"B", "C", "D", "E", "H", "L", "(HL)", "A",
|
||||
"(BC)", "(DE)", "R", "I", "(C)", "(SP)", "PC", "F",
|
||||
"0", "1", "2", "3", "4", "5", "6", "7",
|
||||
"Z", "NZ", "NC", "PO", "PE", "M", "P",
|
||||
"N", "NN", "XNN", "XN", "DIS", "CB", "ED",
|
||||
"XH", "XL", "YH", "YL", "DIS(IX)","DIS(IY)"
|
||||
};
|
||||
|
||||
unsigned char cmd_00[64][3] =
|
||||
{
|
||||
{NOP,0,0},
|
||||
{LD,BC,NN},
|
||||
{LD,XBC,A},
|
||||
{INC,BC,0},
|
||||
{INC,B,0},
|
||||
{DEC,B,0},
|
||||
{LD,B,N},
|
||||
{RLCA,0,0},
|
||||
{EX,AF,AF2},
|
||||
{ADD,HL,BC},
|
||||
{LD,A,XBC},
|
||||
{DEC,BC,0},
|
||||
{INC,C,0},
|
||||
{DEC,C,0},
|
||||
{LD,C,N},
|
||||
{RRCA,0,0},
|
||||
{DJNZ,DIS,0},
|
||||
{LD,DE,NN},
|
||||
{LD,XDE,A},
|
||||
{INC,DE,0},
|
||||
{INC,D,0},
|
||||
{DEC,D,0},
|
||||
{LD,D,N},
|
||||
{RLA,0,0},
|
||||
{JR,DIS,0},
|
||||
{ADD,HL,DE},
|
||||
{LD,A,XDE},
|
||||
{DEC,DE,0},
|
||||
{INC,E,0},
|
||||
{DEC,E,0},
|
||||
{LD,E,N},
|
||||
{RRA,0,0},
|
||||
{JR,NZ,DIS},
|
||||
{LD,HL,NN},
|
||||
{LD,XNN,HL},
|
||||
{INC,HL,0},
|
||||
{INC,H,0},
|
||||
{DEC,H,0},
|
||||
{LD,H,N},
|
||||
{DAA,0,0},
|
||||
{JR,Z,DIS},
|
||||
{ADD,HL,HL},
|
||||
{LD,HL,XNN},
|
||||
{DEC,HL,0},
|
||||
{INC,L,0},
|
||||
{DEC,L,0},
|
||||
{LD,L,N},
|
||||
{CPL,0,0},
|
||||
{JR,NC,DIS},
|
||||
{LD,SP,NN},
|
||||
{LD,XNN,A},
|
||||
{INC,SP,0},
|
||||
{INC,XHL,0},
|
||||
{DEC,XHL,0},
|
||||
{LD,XHL,N},
|
||||
{SCF,0,0},
|
||||
{JR,C,N},
|
||||
{ADD,HL,SP},
|
||||
{LD,A,XNN},
|
||||
{DEC,SP,0},
|
||||
{INC,A,0},
|
||||
{DEC,A,0},
|
||||
{LD,A,N},
|
||||
{CCF,0,0}
|
||||
};
|
||||
|
||||
unsigned char cmd_C0[64][3] =
|
||||
{
|
||||
{RET,NZ,0},
|
||||
{POP,BC,0},
|
||||
{JP,NZ,NN},
|
||||
{JP,NN,0},
|
||||
{CALL,NZ,NN},
|
||||
{PUSH,BC,0},
|
||||
{ADD,A,N},
|
||||
{RST,N0,0},
|
||||
{RET,Z,0},
|
||||
{RET,0,0},
|
||||
{JP,Z,NN},
|
||||
{PFX,CB,0},
|
||||
{CALL,Z,NN},
|
||||
{CALL,NN,0},
|
||||
{ADC,A,N},
|
||||
{RST,N1,0},
|
||||
{RET,NC,0},
|
||||
{POP,DE,0},
|
||||
{JP,NC,NN},
|
||||
{OUT,XN,A},
|
||||
{CALL,NC,NN},
|
||||
{PUSH,DE,0},
|
||||
{SUB,A,N},
|
||||
{RST,N2,0},
|
||||
{RET,C,0},
|
||||
{EXX,0,0},
|
||||
{JP,C,NN},
|
||||
{IN,A,XN},
|
||||
{CALL,C,NN},
|
||||
{PFX,IX,0},
|
||||
{SBC,A,N},
|
||||
{RST,N3,0},
|
||||
{RET,PO,0},
|
||||
{POP,HL,0},
|
||||
{JP,PO,NN},
|
||||
{EX,HL,XSP},
|
||||
{CALL,PO,NN},
|
||||
{PUSH,HL,0},
|
||||
{AND,A,N},
|
||||
{RST,N4,0},
|
||||
{RET,PE,0},
|
||||
{LD,PC,HL},
|
||||
{JP,PE,NN},
|
||||
{EX,DE,HL},
|
||||
{CALL,PE,NN},
|
||||
{PFX,ED,0},
|
||||
{XOR,A,N},
|
||||
{RST,N5,0},
|
||||
{RET,P,0},
|
||||
{POP,AF,0},
|
||||
{JP,P,NN},
|
||||
{DI,0,0},
|
||||
{CALL,P,NN},
|
||||
{PUSH,AF,0},
|
||||
{OR,A,N},
|
||||
{RST,N6,0},
|
||||
{RET,M,0},
|
||||
{LD,SP,HL},
|
||||
{JP,M,NN},
|
||||
{EI,0,0},
|
||||
{CALL,M,NN},
|
||||
{PFX,IY,0},
|
||||
{CP,A,N},
|
||||
{RST,N7,0}
|
||||
};
|
||||
|
||||
unsigned char cmd_ED40[64][3] =
|
||||
{
|
||||
{IN,B,XC},
|
||||
{OUT,XC,B},
|
||||
{SBC,HL,BC},
|
||||
{LD,XNN,BC},
|
||||
{NEG,0,0},
|
||||
{RETN,0,0},
|
||||
{IM,N0,0},
|
||||
{LD,I,A},
|
||||
{IN,C,XC},
|
||||
{OUT,XC,C},
|
||||
{ADC,HL,BC},
|
||||
{LD,BC,XNN},
|
||||
{NEG,0,0},
|
||||
{RETI,0,0},
|
||||
{IM,N0,0},
|
||||
{LD,R,A},
|
||||
{IN,D,XC},
|
||||
{OUT,XC,D},
|
||||
{SBC,HL,DE},
|
||||
{LD,XNN,DE},
|
||||
{NEG,0,0},
|
||||
{RETN,0,0},
|
||||
{IM,N1,0},
|
||||
{LD,A,I},
|
||||
{IN,E,XC},
|
||||
{OUT,XC,E},
|
||||
{ADC,HL,DE},
|
||||
{LD,DE,XNN},
|
||||
{NEG,0,0},
|
||||
{RETI,0,0},
|
||||
{IM,N2,0},
|
||||
{LD,A,R},
|
||||
{IN,H,XC},
|
||||
{OUT,XC,H},
|
||||
{SBC,HL,HL},
|
||||
{LD,XNN,HL},
|
||||
{NEG,0,0},
|
||||
{RETN,0,0},
|
||||
{IM,N0,0},
|
||||
{RRD,0,0},
|
||||
{IN,L,XC},
|
||||
{OUT,XC,L},
|
||||
{ADC,HL,HL},
|
||||
{LD,HL,XNN},
|
||||
{NEG,0,0},
|
||||
{RETI,0,0},
|
||||
{IM,N0,0},
|
||||
{RLD,0,0},
|
||||
{IN,F,XC},
|
||||
{OUT,XC,N0},
|
||||
{SBC,HL,SP},
|
||||
{LD,XNN,SP},
|
||||
{NEG,0,0},
|
||||
{RETN,0,0},
|
||||
{IM,N1,0},
|
||||
{NOP,0,0},
|
||||
{IN,A,XC},
|
||||
{OUT,XC,A},
|
||||
{ADC,HL,SP},
|
||||
{LD,SP,XNN},
|
||||
{NEG,0,0},
|
||||
{RETI,0,0},
|
||||
{IM,N2,0},
|
||||
{NOP,0,0}
|
||||
};
|
||||
|
||||
unsigned char cmd_halt[] = { HALT,0,0 };
|
||||
unsigned char cmd_nop[] = { NOP,0,0 };
|
||||
|
||||
unsigned char c_ari[] = { ADD,ADC,SUB,SBC,AND,XOR,OR,CP };
|
||||
|
||||
unsigned char c_blk[] = { LDI,CPI,INI,OUTI,0,0,0,0,LDD,CPD,IND,OUTD,0,0,0,0,
|
||||
LDIR,CPIR,INIR,OTIR,0,0,0,0,LDDR,CPDR,INDR,OTDR };
|
||||
|
||||
unsigned char c_sh[] = { RLC,RRC,RL,RR,SLA,SRA,SLL,SRL };
|
||||
|
||||
|
||||
// ============================================================================================
|
||||
|
||||
|
||||
unsigned char Peek(unsigned int addr) {
|
||||
loadAddr(addr);
|
||||
return readByte();
|
||||
}
|
||||
|
||||
// ---- return mnenonic descriptor for normal instructions
|
||||
// note: for immediate use only, returned result becomes invalid with next call!
|
||||
unsigned char* mnemo(unsigned char op) {
|
||||
static unsigned char cl[3]={LD,A,A};
|
||||
static unsigned char ca[3]={ADD,A,A};
|
||||
|
||||
switch (op>>6)
|
||||
{
|
||||
case 0: return cmd_00[op];
|
||||
case 1: if (op==0x76) return cmd_halt;
|
||||
cl[1] = B + ((op>>3)&0x07);
|
||||
cl[2] = B + (op&0x07);
|
||||
return cl;
|
||||
case 2: ca[0] = c_ari[(op>>3)&0x07];
|
||||
ca[2] = B + (op&0x07);
|
||||
return ca;
|
||||
case 3: return cmd_C0[op&0x3f];
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for CB instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoCB(unsigned char op) {
|
||||
static unsigned char cmd[3];
|
||||
|
||||
switch (op>>6)
|
||||
{
|
||||
case 0: cmd[0] = c_sh[(op>>3)&0x07];
|
||||
cmd[1] = B + (op&0x07);
|
||||
cmd[2] = 0;
|
||||
return cmd;
|
||||
case 1: cmd[0] = BIT; break;
|
||||
case 2: cmd[0] = RES; break;
|
||||
case 3: cmd[0] = SET; break;
|
||||
}
|
||||
cmd[1] = N0 + ((op>>3)&0x07);
|
||||
cmd[2] = B + (op&0x07);
|
||||
return cmd;
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for IXCB instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoIXCB(unsigned char op) {
|
||||
unsigned char *c;
|
||||
|
||||
c = mnemoCB(op);
|
||||
if (c[1]==XHL) c[1]=XIX; // this is only allowed, because mnemo() doesn't
|
||||
if (c[2]==XHL) c[2]=XIX; // retrieve a pointer but creates mnemo descr ad hoc
|
||||
return c;
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for IYCB instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoIYCB(unsigned char op) {
|
||||
unsigned char *c;
|
||||
|
||||
c = mnemoCB(op);
|
||||
if (c[1]==XHL) c[1]=XIY; // this is only allowed, because mnemo() doesn't
|
||||
if (c[2]==XHL) c[2]=XIY; // retrieve a pointer but creates mnemo descr ad hoc
|
||||
return c;
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for ED instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoED(unsigned char op) {
|
||||
static unsigned char cmd[3]={0,0,0};
|
||||
|
||||
if (op<0x40) return cmd_nop;
|
||||
|
||||
if (op>=0x080)
|
||||
{ if ((op&0xE4)!=0xA0) return cmd_nop;
|
||||
cmd[0] = c_blk[op&0x1B];
|
||||
return cmd;
|
||||
};
|
||||
|
||||
return cmd_ED40[op-0x40];
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for IX instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoIX (unsigned char op) {
|
||||
static unsigned char cmd[3];
|
||||
|
||||
memcpy (cmd, mnemo(op), 3);
|
||||
|
||||
if (cmd[1]==XHL) { cmd[1]=XIX; return cmd; }
|
||||
if (cmd[2]==XHL) { cmd[2]=XIX; return cmd; }
|
||||
if (cmd[1]==HL) { cmd[1]=IX; return cmd; }
|
||||
if (cmd[2]==HL) { cmd[2]=IX; return cmd; }
|
||||
if (cmd[1]==H) cmd[1]=XH;
|
||||
if (cmd[1]==L) cmd[1]=XL;
|
||||
if (cmd[2]==H) cmd[2]=XH;
|
||||
if (cmd[2]==L) cmd[2]=XL;
|
||||
return cmd;
|
||||
}
|
||||
|
||||
|
||||
// ---- return mnenonic descriptor for IY instructions
|
||||
// note: for immediate use only!
|
||||
unsigned char* mnemoIY (unsigned char op) {
|
||||
static unsigned char cmd[3];
|
||||
|
||||
memcpy (cmd, mnemo(op), 3);
|
||||
|
||||
if (cmd[1]==XHL) { cmd[1]=XIY; return cmd; }
|
||||
if (cmd[2]==XHL) { cmd[2]=XIY; return cmd; }
|
||||
if (cmd[1]==HL) { cmd[1]=IY; return cmd; }
|
||||
if (cmd[2]==HL) { cmd[2]=IY; return cmd; }
|
||||
if (cmd[1]==H) cmd[1]=YH;
|
||||
if (cmd[1]==L) cmd[1]=YL;
|
||||
if (cmd[2]==H) cmd[2]=YH;
|
||||
if (cmd[2]==L) cmd[2]=YL;
|
||||
return cmd;
|
||||
}
|
||||
|
||||
// ---- get legal state of CB instruction --------------------------------------
|
||||
// all instructions legal except: sll is illegal
|
||||
int IllegalCB (unsigned char op) {
|
||||
return op>=0x30 && op<0x38 ? illegal : legal;
|
||||
}
|
||||
|
||||
|
||||
// ---- get legal state of IXCB/IYCB instruction ----------------------------------
|
||||
// all instructions which do not use IX are weird
|
||||
// instructions using IX are legal except: sll is illegal
|
||||
int IllegalXXCB (unsigned char op) {
|
||||
if ((op&0x07)!=6) return weird;
|
||||
return op>=0x30 && op<0x38 ? illegal : legal;
|
||||
}
|
||||
|
||||
|
||||
// ---- get legal state of ED instruction --------------------------------------
|
||||
// 0x00-0x3F and 0x80-0xFF weird except block instructions
|
||||
// 0x40-0x7F legal or weird
|
||||
// in f,(c) is legal; out (c),0 is weird
|
||||
int IllegalED (unsigned char op) {
|
||||
char *il = "1111111111110101111100111111001111110001111100011011000011110000";
|
||||
|
||||
if ((op>>6)==1) return il[op-0x40]-'0' ? weird : legal;
|
||||
return *mnemoED(op)==NOP ? weird : legal;
|
||||
}
|
||||
|
||||
|
||||
// ---- get legal state of IX/IY instruction --------------------------------------
|
||||
// all illegal instructions, which use XH or XL are illegal
|
||||
// all illegal instructions, which don't use XH or XL are weird
|
||||
// prefixes are legal
|
||||
int IllegalXX (unsigned char op) {
|
||||
unsigned char *c;
|
||||
|
||||
c = mnemo(op);
|
||||
|
||||
if (*c==PFX || c[1]==XHL || c[2]==XHL) return legal;
|
||||
if (c[1]==H||c[1]==L||c[2]==H||c[2]==L) return illegal;
|
||||
return weird;
|
||||
}
|
||||
|
||||
|
||||
// ---- Calculate length of instruction 30.jun.95 KIO !
|
||||
// op2 is only used if op1 is a prefix instruction
|
||||
// IX/IY before IX/IY/ed have no effect and are reported as length 1
|
||||
int OpcodeLength (unsigned char op1, unsigned char op2) {
|
||||
static char* len0 = "1311112111111121231111212111112123311121213111212331112121311121"; // 0x00 - 0x3F
|
||||
static char* len3 = "1133312111303321113231211132302111313121113130211131312111313021"; // 0xC0 - 0xFF; prefixes are 0
|
||||
|
||||
switch (op1>>6)
|
||||
{
|
||||
case 0: return len0[op1]-'0'; // 0x00 - 0x3F: various length
|
||||
case 1: // 0x40 - 0x7F: ld r,r: all 1
|
||||
case 2: return 1; // 0x80 - 0xBF: arithmetics/logics op a,r: all 1
|
||||
}
|
||||
|
||||
switch (op1) // test for prefix
|
||||
{
|
||||
case 0xcb: return 2;
|
||||
case 0xed: if (/* op2<0x40 || op2>=0x80 || ((op2&7)!=3) */ (op2&0xc7)!=0x43) return 2; else return 4;
|
||||
case 0xdd:
|
||||
case 0xfd:
|
||||
switch (op2>>6)
|
||||
{
|
||||
case 0: return len0[op2]-'0'+1 + (op2>=0x34&&op2<=0x36); // inc(hl); dec(hl); ld(hl),N: add displacement
|
||||
case 1:
|
||||
case 2: if (((op2&0x07)==6) == ((op2&0x0F8)==0x70)) return 2; else return 3;
|
||||
}
|
||||
if (op2==0xcb) return 4;
|
||||
return len3[op2&0x3F]-'0'+1; // note: entries for prefixes are 0 giving a total of 1, just to skip the useless prefix
|
||||
}
|
||||
|
||||
return len3[op1&0x3F]-'0'; // 0xC0 - 0xFF: no prefix: various length
|
||||
}
|
||||
|
||||
|
||||
// ===================================================================================
|
||||
|
||||
|
||||
void xword (unsigned char n, unsigned int *ip) {
|
||||
unsigned int nn;
|
||||
|
||||
switch (n)
|
||||
{
|
||||
case DIS:
|
||||
n = Peek((*ip)++);
|
||||
log0("$%04X", *ip+(char)n,4); // branch destination
|
||||
break;
|
||||
case N:
|
||||
n = Peek((*ip)++);
|
||||
log0("$%02X", n);
|
||||
break;
|
||||
case NN:
|
||||
n = Peek((*ip)++);
|
||||
nn = n+256*Peek((*ip)++);
|
||||
log0("$%04X", nn);
|
||||
break;
|
||||
case XNN:
|
||||
n = Peek((*ip)++);
|
||||
nn = n+256*Peek((*ip)++);
|
||||
log0("($%04X)", nn);
|
||||
break;
|
||||
case XN:
|
||||
n = Peek((*ip)++);
|
||||
log0("($%02X)", n);
|
||||
break;
|
||||
case XIX:
|
||||
n = Peek((*ip)++);
|
||||
if (n&0x80) {
|
||||
log0("(IX-$%02X)", 256-n);
|
||||
} else {
|
||||
log0("(IX+$%02X)", n);
|
||||
}
|
||||
break;
|
||||
case XIY:
|
||||
n = Peek((*ip)++);
|
||||
if (n&0x80) {
|
||||
log0("(IY-$%02X)", 256-n);
|
||||
} else {
|
||||
log0("(IY+$%02X)", n);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
log0("%s", word[n]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// ---- expand 3-char descriptor m[3] to mnemonic with arguments via pc
|
||||
void disass (unsigned char *m, unsigned int *ip) {
|
||||
log0("%-5s", word[*m++]);
|
||||
if (*m) {
|
||||
xword(*m++,ip);
|
||||
}
|
||||
if (*m) {
|
||||
log0(",");
|
||||
xword(*m,ip);
|
||||
}
|
||||
}
|
||||
|
||||
void disassem (unsigned int *ip) {
|
||||
unsigned char op;
|
||||
|
||||
op = Peek((*ip)++);
|
||||
switch (op)
|
||||
{
|
||||
case 0xcb:
|
||||
disass (mnemoCB(Peek((*ip)++)), ip);
|
||||
break;
|
||||
case 0xed:
|
||||
disass (mnemoED(Peek((*ip)++)), ip);
|
||||
break;
|
||||
case 0xdd:
|
||||
op = Peek((*ip)++);
|
||||
if (op!=0xCB) {
|
||||
disass (mnemoIX(op), ip);
|
||||
} else {
|
||||
disass (mnemoIXCB(Peek((*ip)+1)), ip);
|
||||
(*ip)++;
|
||||
}
|
||||
break;
|
||||
case 0xfd:
|
||||
op = Peek((*ip)++);
|
||||
if (op!=0xCB) {
|
||||
disass (mnemoIY(op), ip);
|
||||
} else {
|
||||
disass (mnemoIYCB(Peek((*ip)+1)), ip);
|
||||
(*ip)++;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
disass (mnemo(op),ip);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
unsigned int disassemble(unsigned int addr) {
|
||||
log0("%04X : ", addr);
|
||||
disassem(&addr);
|
||||
log0("\n");
|
||||
return addr;
|
||||
}
|
@ -126,12 +126,14 @@ begin
|
||||
tmosi => tmosi,
|
||||
tdin => tdin,
|
||||
tcclk => tcclk,
|
||||
Regs => Regs,
|
||||
Regs(63 downto 0) => Regs,
|
||||
Regs(255 downto 64) => (others <= '0'),
|
||||
RdOut => memory_rd,
|
||||
WrOut => memory_wr,
|
||||
AddrOut => memory_addr,
|
||||
DataOut => memory_dout,
|
||||
DataIn => memory_din,
|
||||
Done => memory_rd,
|
||||
SS_Step => open,
|
||||
SS_Single => open
|
||||
);
|
||||
|
@ -44,7 +44,7 @@ entity BusMonCore is
|
||||
|
||||
-- 6502 Registers
|
||||
-- unused in pure bus monitor mode
|
||||
Regs : in std_logic_vector(63 downto 0);
|
||||
Regs : in std_logic_vector(255 downto 0);
|
||||
|
||||
-- 6502 Memory Read/Write
|
||||
-- unused in pure bus monitor mode
|
||||
@ -53,6 +53,7 @@ entity BusMonCore is
|
||||
AddrOut : out std_logic_vector(15 downto 0);
|
||||
DataOut : out std_logic_vector(7 downto 0);
|
||||
DataIn : in std_logic_vector(7 downto 0);
|
||||
Done : in std_logic;
|
||||
|
||||
-- Single Step interface
|
||||
SS_Single : out std_logic;
|
||||
@ -98,7 +99,7 @@ architecture behavioral of BusMonCore is
|
||||
signal dy_data : y2d_type ;
|
||||
|
||||
signal mux : std_logic_vector(7 downto 0);
|
||||
signal muxsel : std_logic_vector(4 downto 0);
|
||||
signal muxsel : std_logic_vector(5 downto 0);
|
||||
signal cmd_edge : std_logic;
|
||||
signal cmd_edge1 : std_logic;
|
||||
signal cmd_edge2 : std_logic;
|
||||
@ -221,7 +222,7 @@ begin
|
||||
portdout(2) => muxsel(2),
|
||||
portdout(3) => muxsel(3),
|
||||
portdout(4) => muxsel(4),
|
||||
portdout(5) => open,
|
||||
portdout(5) => muxsel(5),
|
||||
portdout(6) => open,
|
||||
portdout(7) => open,
|
||||
|
||||
@ -287,15 +288,42 @@ begin
|
||||
fifo_dout(63 downto 56) when muxsel = 13 else
|
||||
fifo_dout(71 downto 64) when muxsel = 14 else
|
||||
|
||||
Regs(7 downto 0) when muxsel = 16 else
|
||||
Regs(15 downto 8) when muxsel = 17 else
|
||||
Regs(23 downto 16) when muxsel = 18 else
|
||||
Regs(31 downto 24) when muxsel = 19 else
|
||||
Regs(39 downto 32) when muxsel = 20 else
|
||||
Regs(47 downto 40) when muxsel = 21 else
|
||||
Regs(55 downto 48) when muxsel = 22 else
|
||||
Regs(63 downto 56) when muxsel = 23 else
|
||||
"10101010";
|
||||
Regs(8 * to_integer(unsigned(muxsel(4 downto 0))) + 7 downto 8 * to_integer(unsigned(muxsel(4 downto 0))));
|
||||
|
||||
-- Regs( 15 downto 8) when muxsel = 33 else
|
||||
-- Regs( 23 downto 16) when muxsel = 34 else
|
||||
-- Regs( 31 downto 24) when muxsel = 35 else
|
||||
-- Regs( 39 downto 32) when muxsel = 36 else
|
||||
-- Regs( 47 downto 40) when muxsel = 37 else
|
||||
-- Regs( 55 downto 48) when muxsel = 38 else
|
||||
-- Regs( 63 downto 56) when muxsel = 39 else
|
||||
-- Regs( 7 downto 64) when muxsel = 40 else
|
||||
-- Regs( 15 downto 72) when muxsel = 41 else
|
||||
-- Regs( 23 downto 80) when muxsel = 42 else
|
||||
-- Regs( 31 downto 88) when muxsel = 43 else
|
||||
-- Regs( 39 downto 96) when muxsel = 44 else
|
||||
-- Regs( 47 downto 104) when muxsel = 45 else
|
||||
-- Regs( 55 downto 112) when muxsel = 46 else
|
||||
-- Regs( 63 downto 120) when muxsel = 47 else
|
||||
-- Regs( 7 downto 128) when muxsel = 48 else
|
||||
-- Regs( 15 downto 136) when muxsel = 49 else
|
||||
-- Regs( 23 downto 144) when muxsel = 50 else
|
||||
-- Regs( 31 downto 24) when muxsel = 51 else
|
||||
-- Regs( 39 downto 32) when muxsel = 52 else
|
||||
-- Regs( 47 downto 40) when muxsel = 53 else
|
||||
-- Regs( 55 downto 48) when muxsel = 54 else
|
||||
-- Regs( 63 downto 56) when muxsel = 55 else
|
||||
-- Regs( 7 downto 0) when muxsel = 56 else
|
||||
-- Regs( 15 downto 8) when muxsel = 57 else
|
||||
-- Regs( 23 downto 16) when muxsel = 58 else
|
||||
-- Regs( 31 downto 24) when muxsel = 59 else
|
||||
-- Regs( 39 downto 32) when muxsel = 60 else
|
||||
-- Regs( 47 downto 40) when muxsel = 61 else
|
||||
-- Regs( 55 downto 48) when muxsel = 62 else
|
||||
-- Regs( 63 downto 56) when muxsel = 63 else
|
||||
--
|
||||
--
|
||||
-- "10101010";
|
||||
|
||||
-- Combinatorial set of comparators to decode breakpoint/watch addresses
|
||||
brkpt_active_process: process (brkpt_reg, brkpt_enable, Addr, Sync)
|
||||
@ -402,7 +430,6 @@ begin
|
||||
fifo_rst <= '0';
|
||||
memory_rd <= '0';
|
||||
memory_wr <= '0';
|
||||
auto_inc <= '0';
|
||||
SS_Step <= '0';
|
||||
if (cmd_edge2 = '0' and cmd_edge1 = '1') then
|
||||
if (cmd(4 downto 1) = "0000") then
|
||||
@ -446,7 +473,7 @@ begin
|
||||
end if;
|
||||
|
||||
-- Auto increment the memory address reg the cycle after a rd/wr
|
||||
if (auto_inc = '1' and (memory_rd = '1' or memory_wr = '1')) then
|
||||
if (auto_inc = '1' and Done = '1') then
|
||||
addr_dout_reg(23 downto 8) <= addr_dout_reg(23 downto 8) + 1;
|
||||
end if;
|
||||
|
||||
@ -492,7 +519,7 @@ begin
|
||||
-- Latch the data bus for use in watches
|
||||
Data1 <= Data;
|
||||
-- Latch memory read in response to a read command
|
||||
if (memory_rd = '1') then
|
||||
if (Done = '1') then
|
||||
din_reg <= DataIn;
|
||||
end if;
|
||||
end if;
|
||||
|
@ -122,8 +122,7 @@ entity T80 is
|
||||
IntCycle_n : out std_logic;
|
||||
IntE : out std_logic;
|
||||
Stop : out std_logic;
|
||||
Regs : out std_logic_vector(63 downto 0)
|
||||
|
||||
Regs : out std_logic_vector(255 downto 0)
|
||||
);
|
||||
end T80;
|
||||
|
||||
@ -251,10 +250,13 @@ architecture rtl of T80 is
|
||||
|
||||
begin
|
||||
|
||||
Regs(31 downto 0) <= Ap & Fp & ACC & F;
|
||||
-- Regs(31 downto 0) <= RegFileData(31 downto 0);
|
||||
Regs(47 downto 32) <= std_logic_vector(SP);
|
||||
Regs(63 downto 48) <= std_logic_vector(PC);
|
||||
Regs(127 downto 0) <= RegFileData;
|
||||
Regs(159 downto 128) <= Ap & Fp & ACC & F;
|
||||
Regs(175 downto 160) <= std_logic_vector(SP);
|
||||
Regs(191 downto 176) <= std_logic_vector(PC);
|
||||
Regs(199 downto 192) <= I;
|
||||
Regs(207 downto 200) <= std_logic_vector(R);
|
||||
Regs(215 downto 208) <= "000000" & IntE_FF2 & IntE_FF1;
|
||||
|
||||
|
||||
mcode : T80_MCode
|
||||
|
@ -105,7 +105,7 @@ package T80_Pack is
|
||||
IntCycle_n : out std_logic;
|
||||
IntE : out std_logic;
|
||||
Stop : out std_logic;
|
||||
Regs : out std_logic_vector(63 downto 0)
|
||||
Regs : out std_logic_vector(255 downto 0)
|
||||
);
|
||||
end component;
|
||||
|
||||
|
@ -92,21 +92,20 @@ architecture rtl of T80_Reg is
|
||||
begin
|
||||
|
||||
RegFileData( 7 downto 0) <= RegsL(0);
|
||||
RegFileData( 15 downto 8) <= RegsL(1);
|
||||
RegFileData( 23 downto 16) <= RegsL(2);
|
||||
RegFileData( 31 downto 24) <= RegsL(3);
|
||||
RegFileData( 39 downto 32) <= RegsL(4);
|
||||
RegFileData( 47 downto 40) <= RegsL(5);
|
||||
RegFileData( 55 downto 48) <= RegsL(6);
|
||||
RegFileData( 63 downto 56) <= RegsL(7);
|
||||
|
||||
RegFileData( 71 downto 64) <= RegsH(0);
|
||||
RegFileData( 79 downto 72) <= RegsH(1);
|
||||
RegFileData( 87 downto 80) <= RegsH(2);
|
||||
RegFileData( 95 downto 88) <= RegsH(3);
|
||||
RegFileData(103 downto 96) <= RegsH(4);
|
||||
RegFileData(111 downto 104) <= RegsH(5);
|
||||
RegFileData(119 downto 112) <= RegsH(6);
|
||||
RegFileData( 15 downto 8) <= RegsH(0);
|
||||
RegFileData( 23 downto 16) <= RegsL(1);
|
||||
RegFileData( 31 downto 24) <= RegsH(1);
|
||||
RegFileData( 39 downto 32) <= RegsL(2);
|
||||
RegFileData( 47 downto 40) <= RegsH(2);
|
||||
RegFileData( 55 downto 48) <= RegsL(3);
|
||||
RegFileData( 63 downto 56) <= RegsH(3);
|
||||
RegFileData( 71 downto 64) <= RegsL(4);
|
||||
RegFileData( 79 downto 72) <= RegsH(4);
|
||||
RegFileData( 87 downto 80) <= RegsL(5);
|
||||
RegFileData( 95 downto 88) <= RegsH(5);
|
||||
RegFileData(103 downto 96) <= RegsL(6);
|
||||
RegFileData(111 downto 104) <= RegsH(6);
|
||||
RegFileData(119 downto 112) <= RegsL(7);
|
||||
RegFileData(127 downto 120) <= RegsH(7);
|
||||
|
||||
process (Clk)
|
||||
|
562
src/T80/T80a.vhd
562
src/T80/T80a.vhd
@ -1,282 +1,286 @@
|
||||
-- ****
|
||||
-- T80(b) core. In an effort to merge and maintain bug fixes ....
|
||||
--
|
||||
--
|
||||
-- Ver 300 started tidyup
|
||||
-- MikeJ March 2005
|
||||
-- Latest version from www.fpgaarcade.com (original www.opencores.org)
|
||||
--
|
||||
-- ****
|
||||
--
|
||||
-- Z80 compatible microprocessor core, asynchronous top level
|
||||
--
|
||||
-- Version : 0247
|
||||
--
|
||||
-- Copyright (c) 2001-2002 Daniel Wallner (jesus@opencores.org)
|
||||
--
|
||||
-- All rights reserved
|
||||
--
|
||||
-- Redistribution and use in source and synthezised forms, with or without
|
||||
-- modification, are permitted provided that the following conditions are met:
|
||||
--
|
||||
-- Redistributions of source code must retain the above copyright notice,
|
||||
-- this list of conditions and the following disclaimer.
|
||||
--
|
||||
-- Redistributions in synthesized form must reproduce the above copyright
|
||||
-- notice, this list of conditions and the following disclaimer in the
|
||||
-- documentation and/or other materials provided with the distribution.
|
||||
--
|
||||
-- Neither the name of the author nor the names of other contributors may
|
||||
-- be used to endorse or promote products derived from this software without
|
||||
-- specific prior written permission.
|
||||
--
|
||||
-- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
-- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
|
||||
-- THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
-- PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE
|
||||
-- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
-- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
-- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
-- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
-- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
-- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
-- POSSIBILITY OF SUCH DAMAGE.
|
||||
--
|
||||
-- Please report bugs to the author, but before you do so, please
|
||||
-- make sure that this is not a derivative work and that
|
||||
-- you have the latest version of this file.
|
||||
--
|
||||
-- The latest version of this file can be found at:
|
||||
-- http://www.opencores.org/cvsweb.shtml/t80/
|
||||
--
|
||||
-- Limitations :
|
||||
--
|
||||
-- File history :
|
||||
--
|
||||
-- 0208 : First complete release
|
||||
--
|
||||
-- 0211 : Fixed interrupt cycle
|
||||
--
|
||||
-- 0235 : Updated for T80 interface change
|
||||
--
|
||||
-- 0238 : Updated for T80 interface change
|
||||
--
|
||||
-- 0240 : Updated for T80 interface change
|
||||
--
|
||||
-- 0242 : Updated for T80 interface change
|
||||
--
|
||||
-- 0247 : Fixed bus req/ack cycle
|
||||
--
|
||||
|
||||
library IEEE;
|
||||
use IEEE.std_logic_1164.all;
|
||||
use IEEE.numeric_std.all;
|
||||
use work.T80_Pack.all;
|
||||
|
||||
entity T80a is
|
||||
generic(
|
||||
Mode : integer := 0 -- 0 => Z80, 1 => Fast Z80, 2 => 8080, 3 => GB
|
||||
);
|
||||
port(
|
||||
-- Additions
|
||||
TS : out std_logic_vector(2 downto 0);
|
||||
Regs : out std_logic_vector(63 downto 0);
|
||||
-- Original Signals
|
||||
RESET_n : in std_logic;
|
||||
CLK_n : in std_logic;
|
||||
WAIT_n : in std_logic;
|
||||
INT_n : in std_logic;
|
||||
NMI_n : in std_logic;
|
||||
BUSRQ_n : in std_logic;
|
||||
M1_n : out std_logic;
|
||||
MREQ_n : out std_logic;
|
||||
IORQ_n : out std_logic;
|
||||
RD_n : out std_logic;
|
||||
WR_n : out std_logic;
|
||||
RFSH_n : out std_logic;
|
||||
HALT_n : out std_logic;
|
||||
BUSAK_n : out std_logic;
|
||||
A : out std_logic_vector(15 downto 0);
|
||||
D : inout std_logic_vector(7 downto 0)
|
||||
);
|
||||
end T80a;
|
||||
|
||||
architecture rtl of T80a is
|
||||
|
||||
signal CEN : std_logic;
|
||||
signal Reset_s : std_logic;
|
||||
signal IntCycle_n : std_logic;
|
||||
signal IORQ : std_logic;
|
||||
signal NoRead : std_logic;
|
||||
signal Write : std_logic;
|
||||
signal MREQ : std_logic;
|
||||
signal MReq_Inhibit : std_logic;
|
||||
signal Req_Inhibit : std_logic;
|
||||
signal RD : std_logic;
|
||||
signal MREQ_n_i : std_logic;
|
||||
signal IORQ_n_i : std_logic;
|
||||
signal RD_n_i : std_logic;
|
||||
signal WR_n_i : std_logic;
|
||||
signal RFSH_n_i : std_logic;
|
||||
signal BUSAK_n_i : std_logic;
|
||||
signal A_i : std_logic_vector(15 downto 0);
|
||||
signal DO : std_logic_vector(7 downto 0);
|
||||
signal DI_Reg : std_logic_vector (7 downto 0); -- Input synchroniser
|
||||
signal Wait_s : std_logic;
|
||||
signal MCycle : std_logic_vector(2 downto 0);
|
||||
signal TState : std_logic_vector(2 downto 0);
|
||||
|
||||
begin
|
||||
|
||||
CEN <= '1';
|
||||
|
||||
BUSAK_n <= BUSAK_n_i;
|
||||
MREQ_n_i <= not MREQ or (Req_Inhibit and MReq_Inhibit);
|
||||
RD_n_i <= not RD or Req_Inhibit;
|
||||
|
||||
MREQ_n <= MREQ_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
IORQ_n <= IORQ_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
RD_n <= RD_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
WR_n <= WR_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
RFSH_n <= RFSH_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
A <= A_i when BUSAK_n_i = '1' else (others => 'Z');
|
||||
D <= DO when Write = '1' and BUSAK_n_i = '1' else (others => 'Z');
|
||||
|
||||
process (RESET_n, CLK_n)
|
||||
begin
|
||||
if RESET_n = '0' then
|
||||
Reset_s <= '0';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
Reset_s <= '1';
|
||||
end if;
|
||||
end process;
|
||||
|
||||
u0 : T80
|
||||
generic map(
|
||||
Mode => Mode,
|
||||
IOWait => 1)
|
||||
port map(
|
||||
CEN => CEN,
|
||||
M1_n => M1_n,
|
||||
IORQ => IORQ,
|
||||
NoRead => NoRead,
|
||||
Write => Write,
|
||||
RFSH_n => RFSH_n_i,
|
||||
HALT_n => HALT_n,
|
||||
WAIT_n => Wait_s,
|
||||
INT_n => INT_n,
|
||||
NMI_n => NMI_n,
|
||||
RESET_n => Reset_s,
|
||||
BUSRQ_n => BUSRQ_n,
|
||||
BUSAK_n => BUSAK_n_i,
|
||||
CLK_n => CLK_n,
|
||||
A => A_i,
|
||||
DInst => D,
|
||||
DI => DI_Reg,
|
||||
DO => DO,
|
||||
MC => MCycle,
|
||||
TS => TState,
|
||||
IntCycle_n => IntCycle_n,
|
||||
Regs => Regs
|
||||
);
|
||||
|
||||
|
||||
process (CLK_n)
|
||||
begin
|
||||
if CLK_n'event and CLK_n = '0' then
|
||||
Wait_s <= WAIT_n;
|
||||
if TState = "011" and BUSAK_n_i = '1' then
|
||||
DI_Reg <= to_x01(D);
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
WR_n_i <= '1';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
WR_n_i <= '1';
|
||||
if TState = "001" or (TState = "010" and Wait_s = '0') then -- To short for IO writes !!!!!!!!!!!!!!!!!!!
|
||||
WR_n_i <= not Write;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
-- ****
|
||||
-- T80(b) core. In an effort to merge and maintain bug fixes ....
|
||||
--
|
||||
--
|
||||
-- Ver 300 started tidyup
|
||||
-- MikeJ March 2005
|
||||
-- Latest version from www.fpgaarcade.com (original www.opencores.org)
|
||||
--
|
||||
-- ****
|
||||
--
|
||||
-- Z80 compatible microprocessor core, asynchronous top level
|
||||
--
|
||||
-- Version : 0247
|
||||
--
|
||||
-- Copyright (c) 2001-2002 Daniel Wallner (jesus@opencores.org)
|
||||
--
|
||||
-- All rights reserved
|
||||
--
|
||||
-- Redistribution and use in source and synthezised forms, with or without
|
||||
-- modification, are permitted provided that the following conditions are met:
|
||||
--
|
||||
-- Redistributions of source code must retain the above copyright notice,
|
||||
-- this list of conditions and the following disclaimer.
|
||||
--
|
||||
-- Redistributions in synthesized form must reproduce the above copyright
|
||||
-- notice, this list of conditions and the following disclaimer in the
|
||||
-- documentation and/or other materials provided with the distribution.
|
||||
--
|
||||
-- Neither the name of the author nor the names of other contributors may
|
||||
-- be used to endorse or promote products derived from this software without
|
||||
-- specific prior written permission.
|
||||
--
|
||||
-- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
-- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
|
||||
-- THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
-- PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE
|
||||
-- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
-- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
-- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
-- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
-- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
-- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
-- POSSIBILITY OF SUCH DAMAGE.
|
||||
--
|
||||
-- Please report bugs to the author, but before you do so, please
|
||||
-- make sure that this is not a derivative work and that
|
||||
-- you have the latest version of this file.
|
||||
--
|
||||
-- The latest version of this file can be found at:
|
||||
-- http://www.opencores.org/cvsweb.shtml/t80/
|
||||
--
|
||||
-- Limitations :
|
||||
--
|
||||
-- File history :
|
||||
--
|
||||
-- 0208 : First complete release
|
||||
--
|
||||
-- 0211 : Fixed interrupt cycle
|
||||
--
|
||||
-- 0235 : Updated for T80 interface change
|
||||
--
|
||||
-- 0238 : Updated for T80 interface change
|
||||
--
|
||||
-- 0240 : Updated for T80 interface change
|
||||
--
|
||||
-- 0242 : Updated for T80 interface change
|
||||
--
|
||||
-- 0247 : Fixed bus req/ack cycle
|
||||
--
|
||||
|
||||
-- process (Reset_s,CLK_n)
|
||||
-- begin
|
||||
-- if Reset_s = '0' then
|
||||
-- WR_n_i <= '1';
|
||||
-- elsif CLK_n'event and CLK_n = '0' then
|
||||
-- WR_n_i <= '1';
|
||||
-- if TState = "010" then -- To short for IO writes !!!!!!!!!!!!!!!!!!!
|
||||
-- WR_n_i <= not Write;
|
||||
-- end if;
|
||||
-- end if;
|
||||
library IEEE;
|
||||
use IEEE.std_logic_1164.all;
|
||||
use IEEE.numeric_std.all;
|
||||
use work.T80_Pack.all;
|
||||
|
||||
entity T80a is
|
||||
generic(
|
||||
Mode : integer := 0 -- 0 => Z80, 1 => Fast Z80, 2 => 8080, 3 => GB
|
||||
);
|
||||
port(
|
||||
-- Additions
|
||||
TS : out std_logic_vector(2 downto 0);
|
||||
Regs : out std_logic_vector(255 downto 0);
|
||||
-- Original Signals
|
||||
RESET_n : in std_logic;
|
||||
CLK_n : in std_logic;
|
||||
WAIT_n : in std_logic;
|
||||
INT_n : in std_logic;
|
||||
NMI_n : in std_logic;
|
||||
BUSRQ_n : in std_logic;
|
||||
M1_n : out std_logic;
|
||||
MREQ_n : out std_logic;
|
||||
IORQ_n : out std_logic;
|
||||
RD_n : out std_logic;
|
||||
WR_n : out std_logic;
|
||||
RFSH_n : out std_logic;
|
||||
HALT_n : out std_logic;
|
||||
BUSAK_n : out std_logic;
|
||||
A : out std_logic_vector(15 downto 0);
|
||||
Din : in std_logic_vector(7 downto 0);
|
||||
Dout : out std_logic_vector(7 downto 0);
|
||||
Den : out std_logic
|
||||
);
|
||||
end T80a;
|
||||
|
||||
architecture rtl of T80a is
|
||||
|
||||
signal CEN : std_logic;
|
||||
signal Reset_s : std_logic;
|
||||
signal IntCycle_n : std_logic;
|
||||
signal IORQ : std_logic;
|
||||
signal NoRead : std_logic;
|
||||
signal Write : std_logic;
|
||||
signal MREQ : std_logic;
|
||||
signal MReq_Inhibit : std_logic;
|
||||
signal Req_Inhibit : std_logic;
|
||||
signal RD : std_logic;
|
||||
signal MREQ_n_i : std_logic;
|
||||
signal IORQ_n_i : std_logic;
|
||||
signal RD_n_i : std_logic;
|
||||
signal WR_n_i : std_logic;
|
||||
signal RFSH_n_i : std_logic;
|
||||
signal BUSAK_n_i : std_logic;
|
||||
signal A_i : std_logic_vector(15 downto 0);
|
||||
signal DO : std_logic_vector(7 downto 0);
|
||||
signal DI_Reg : std_logic_vector (7 downto 0); -- Input synchroniser
|
||||
signal Wait_s : std_logic;
|
||||
signal MCycle : std_logic_vector(2 downto 0);
|
||||
signal TState : std_logic_vector(2 downto 0);
|
||||
|
||||
begin
|
||||
|
||||
CEN <= '1';
|
||||
|
||||
BUSAK_n <= BUSAK_n_i;
|
||||
MREQ_n_i <= not MREQ or (Req_Inhibit and MReq_Inhibit);
|
||||
RD_n_i <= not RD or Req_Inhibit;
|
||||
|
||||
MREQ_n <= MREQ_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
IORQ_n <= IORQ_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
RD_n <= RD_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
WR_n <= WR_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
RFSH_n <= RFSH_n_i when BUSAK_n_i = '1' else 'Z';
|
||||
A <= A_i when BUSAK_n_i = '1' else (others => 'Z');
|
||||
|
||||
Dout <= DO;
|
||||
Den <= Write and BUSAK_n_i;
|
||||
|
||||
process (RESET_n, CLK_n)
|
||||
begin
|
||||
if RESET_n = '0' then
|
||||
Reset_s <= '0';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
Reset_s <= '1';
|
||||
end if;
|
||||
end process;
|
||||
|
||||
u0 : T80
|
||||
generic map(
|
||||
Mode => Mode,
|
||||
IOWait => 1)
|
||||
port map(
|
||||
CEN => CEN,
|
||||
M1_n => M1_n,
|
||||
IORQ => IORQ,
|
||||
NoRead => NoRead,
|
||||
Write => Write,
|
||||
RFSH_n => RFSH_n_i,
|
||||
HALT_n => HALT_n,
|
||||
WAIT_n => Wait_s,
|
||||
INT_n => INT_n,
|
||||
NMI_n => NMI_n,
|
||||
RESET_n => Reset_s,
|
||||
BUSRQ_n => BUSRQ_n,
|
||||
BUSAK_n => BUSAK_n_i,
|
||||
CLK_n => CLK_n,
|
||||
A => A_i,
|
||||
DInst => Din,
|
||||
DI => DI_Reg,
|
||||
DO => DO,
|
||||
MC => MCycle,
|
||||
TS => TState,
|
||||
IntCycle_n => IntCycle_n,
|
||||
Regs => Regs
|
||||
);
|
||||
|
||||
|
||||
process (CLK_n)
|
||||
begin
|
||||
if CLK_n'event and CLK_n = '0' then
|
||||
Wait_s <= WAIT_n;
|
||||
if TState = "011" and BUSAK_n_i = '1' then
|
||||
DI_Reg <= to_x01(Din);
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
WR_n_i <= '1';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
WR_n_i <= '1';
|
||||
if TState = "001" or (TState = "010" and Wait_s = '0') then -- To short for IO writes !!!!!!!!!!!!!!!!!!!
|
||||
WR_n_i <= not Write;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
-- process (Reset_s,CLK_n)
|
||||
-- begin
|
||||
-- if Reset_s = '0' then
|
||||
-- WR_n_i <= '1';
|
||||
-- elsif CLK_n'event and CLK_n = '0' then
|
||||
-- WR_n_i <= '1';
|
||||
-- if TState = "010" then -- To short for IO writes !!!!!!!!!!!!!!!!!!!
|
||||
-- WR_n_i <= not Write;
|
||||
-- end if;
|
||||
-- end if;
|
||||
-- end process;
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
Req_Inhibit <= '0';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
if MCycle = "001" and TState = "010" and Wait_s = '1' then
|
||||
Req_Inhibit <= '1';
|
||||
else
|
||||
Req_Inhibit <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
MReq_Inhibit <= '0';
|
||||
elsif CLK_n'event and CLK_n = '0' then
|
||||
if MCycle = "001" and TState = "010" then
|
||||
MReq_Inhibit <= '1';
|
||||
else
|
||||
MReq_Inhibit <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process(Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '0';
|
||||
elsif CLK_n'event and CLK_n = '0' then
|
||||
|
||||
if MCycle = "001" then
|
||||
if TState = "001" then
|
||||
RD <= IntCycle_n;
|
||||
MREQ <= IntCycle_n;
|
||||
IORQ_n_i <= IntCycle_n;
|
||||
end if;
|
||||
if TState = "011" then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '1';
|
||||
end if;
|
||||
if TState = "100" then
|
||||
MREQ <= '0';
|
||||
end if;
|
||||
else
|
||||
if TState = "001" and NoRead = '0' then
|
||||
RD <= not Write;
|
||||
IORQ_n_i <= not IORQ;
|
||||
MREQ <= not IORQ;
|
||||
end if;
|
||||
if TState = "011" then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
Req_Inhibit <= '0';
|
||||
elsif CLK_n'event and CLK_n = '1' then
|
||||
if MCycle = "001" and TState = "010" and Wait_s = '1' then
|
||||
Req_Inhibit <= '1';
|
||||
else
|
||||
Req_Inhibit <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process (Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
MReq_Inhibit <= '0';
|
||||
elsif CLK_n'event and CLK_n = '0' then
|
||||
if MCycle = "001" and TState = "010" then
|
||||
MReq_Inhibit <= '1';
|
||||
else
|
||||
MReq_Inhibit <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
process(Reset_s,CLK_n)
|
||||
begin
|
||||
if Reset_s = '0' then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '0';
|
||||
elsif CLK_n'event and CLK_n = '0' then
|
||||
|
||||
if MCycle = "001" then
|
||||
if TState = "001" then
|
||||
RD <= IntCycle_n;
|
||||
MREQ <= IntCycle_n;
|
||||
IORQ_n_i <= IntCycle_n;
|
||||
end if;
|
||||
if TState = "011" then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '1';
|
||||
end if;
|
||||
if TState = "100" then
|
||||
MREQ <= '0';
|
||||
end if;
|
||||
else
|
||||
if TState = "001" and NoRead = '0' then
|
||||
RD <= not Write;
|
||||
IORQ_n_i <= not IORQ;
|
||||
MREQ <= not IORQ;
|
||||
end if;
|
||||
if TState = "011" then
|
||||
RD <= '0';
|
||||
IORQ_n_i <= '1';
|
||||
MREQ <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
TS <= TState;
|
||||
end;
|
||||
end;
|
||||
|
@ -78,6 +78,10 @@ end Z80CpuMon;
|
||||
|
||||
architecture behavioral of Z80CpuMon is
|
||||
|
||||
type state_type is (idle, rd_init, rd_setup, rd, rd_hold, wr_init, wr_setup, wr, wr_hold, release);
|
||||
|
||||
signal state : state_type;
|
||||
|
||||
signal RESET_n_int : std_logic;
|
||||
signal cpu_clk : std_logic;
|
||||
signal busmon_clk : std_logic;
|
||||
@ -94,8 +98,13 @@ signal SS_Single : std_logic;
|
||||
signal SS_Step : std_logic;
|
||||
signal SS_Step_held : std_logic;
|
||||
|
||||
signal Regs : std_logic_vector(63 downto 0);
|
||||
signal Write : std_logic;
|
||||
signal Regs : std_logic_vector(255 downto 0);
|
||||
signal memory_rd : std_logic;
|
||||
signal memory_wr : std_logic;
|
||||
signal memory_addr : std_logic_vector(15 downto 0);
|
||||
signal memory_dout : std_logic_vector(7 downto 0);
|
||||
signal memory_din : std_logic_vector(7 downto 0);
|
||||
signal memory_done : std_logic;
|
||||
|
||||
signal INT_n_sync : std_logic;
|
||||
signal NMI_n_sync : std_logic;
|
||||
@ -110,15 +119,20 @@ signal Sync : std_logic;
|
||||
signal Sync0 : std_logic;
|
||||
signal nRST : std_logic;
|
||||
|
||||
signal ex_data : std_logic_vector(7 downto 0);
|
||||
signal rd_data : std_logic_vector(7 downto 0);
|
||||
signal mon_data : std_logic_vector(7 downto 0);
|
||||
signal MemState : std_logic_vector(2 downto 0);
|
||||
|
||||
signal Din : std_logic_vector(7 downto 0);
|
||||
signal Dout : std_logic_vector(7 downto 0);
|
||||
signal Den : std_logic;
|
||||
signal ex_data : std_logic_vector(7 downto 0);
|
||||
signal rd_data : std_logic_vector(7 downto 0);
|
||||
signal mon_data : std_logic_vector(7 downto 0);
|
||||
|
||||
begin
|
||||
|
||||
mon : entity work.BusMonCore
|
||||
generic map (
|
||||
num_comparators => 8
|
||||
num_comparators => 4
|
||||
)
|
||||
port map (
|
||||
clock49 => clock49,
|
||||
@ -129,10 +143,8 @@ begin
|
||||
Wr_n => Write_n,
|
||||
Sync => Sync,
|
||||
Rdy => Rdy,
|
||||
SS_Single => SS_Single,
|
||||
SS_Step => SS_Step,
|
||||
nRSTin => RESET_n_int,
|
||||
nRSTout => nRST,
|
||||
nRSTin => RESET_n_int,
|
||||
nRSTout => nRST,
|
||||
trig => trig,
|
||||
lcd_rs => open,
|
||||
lcd_rw => open,
|
||||
@ -148,12 +160,15 @@ begin
|
||||
tmosi => tmosi,
|
||||
tdin => tdin,
|
||||
tcclk => tcclk,
|
||||
Regs => Regs(63 downto 0),
|
||||
RdOut => open,
|
||||
WrOut => open,
|
||||
AddrOut => open,
|
||||
DataOut => open,
|
||||
DataIn => (others => '0')
|
||||
Regs => Regs,
|
||||
RdOut => memory_rd,
|
||||
WrOut => memory_wr,
|
||||
AddrOut => memory_addr,
|
||||
DataOut => memory_dout,
|
||||
DataIn => memory_din,
|
||||
Done => memory_done,
|
||||
SS_Single => SS_Single,
|
||||
SS_Step => SS_Step
|
||||
);
|
||||
|
||||
GenT80Core: if UseT80Core generate
|
||||
@ -175,14 +190,15 @@ begin
|
||||
HALT_n => HALT_n,
|
||||
BUSAK_n => BUSAK_n,
|
||||
A => Addr_int,
|
||||
D => Data
|
||||
Din => Din,
|
||||
Dout => Dout,
|
||||
DEn => Den
|
||||
);
|
||||
end generate;
|
||||
|
||||
WAIT_n_int <= WAIT_n when SS_Single = '0'
|
||||
else WAIT_n and SS_Step_held;
|
||||
|
||||
|
||||
WAIT_n_int <= WAIT_n when SS_Single = '0' else
|
||||
WAIT_n and SS_Step_held;
|
||||
|
||||
sync_gen : process(CLK_n, RESET_n_int)
|
||||
begin
|
||||
if RESET_n_int = '0' then
|
||||
@ -218,9 +234,9 @@ begin
|
||||
watch_gen : process(CLK_n)
|
||||
begin
|
||||
if falling_edge(CLK_n) then
|
||||
Sync <= Sync0;
|
||||
Sync <= Sync0;
|
||||
Read_n1 <= Read_n0;
|
||||
Read_n <= Read_n1;
|
||||
Read_n <= Read_n1;
|
||||
Write_n <= Write_n0;
|
||||
end if;
|
||||
end process;
|
||||
@ -242,18 +258,79 @@ begin
|
||||
if (Read_n1 = '0') then
|
||||
rd_data <= Data;
|
||||
end if;
|
||||
memory_din <= Data;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
-- Mux the data seen by the bus monitor appropriately
|
||||
mon_data <= rd_data when Read_n <= '0' else ex_data;
|
||||
|
||||
Addr <= Addr_int;
|
||||
WR_n <= WR_n_int;
|
||||
RD_n <= RD_n_int;
|
||||
MREQ_n <= MREQ_n_int;
|
||||
IORQ_n <= IORQ_n_int;
|
||||
M1_n <= M1_n_int;
|
||||
-- Memory access
|
||||
Addr <= memory_addr when (state /= idle) else Addr_int;
|
||||
|
||||
MREQ_n <= '1' when (state = rd_init or state = wr_init or state = release) else
|
||||
'0' when (state /= idle) else MREQ_n_int;
|
||||
|
||||
IORQ_n <= '1' when (state /= idle) else IORQ_n_int;
|
||||
|
||||
WR_n <= '0' when (state = wr) else
|
||||
'1' when (state /= idle) else WR_n_int;
|
||||
|
||||
RD_n <= '0' when (state = rd_setup or state = rd or state = rd_hold) else
|
||||
'1' when (state /= idle) else RD_n_int;
|
||||
|
||||
M1_n <= '1' when (state /= idle) else M1_n_int;
|
||||
|
||||
memory_done <= '1' when (state = rd_hold or state = wr_hold) else '0';
|
||||
|
||||
-- TODO: Also need to take account of BUSRQ_n/BUSAK_n
|
||||
|
||||
Data <= memory_dout when state = wr_setup or state = wr or state = wr_hold else
|
||||
Dout when state = idle and Den = '1' else
|
||||
(others => 'Z');
|
||||
Din <= Data;
|
||||
|
||||
|
||||
-- TODO: Add refresh generation into idle loop
|
||||
|
||||
men_access_machine : process(CLK_n)
|
||||
begin
|
||||
if (RESET_n = '0') then
|
||||
state <= idle;
|
||||
elsif falling_edge(CLK_n) then
|
||||
case state IS
|
||||
when idle =>
|
||||
if (memory_wr = '1') then
|
||||
state <= wr_init;
|
||||
elsif (memory_rd = '1') then
|
||||
state <= rd_init;
|
||||
end if;
|
||||
when rd_init =>
|
||||
state <= rd_setup;
|
||||
when rd_setup =>
|
||||
if (WAIT_n = '1') then
|
||||
state <= rd;
|
||||
end if;
|
||||
when rd =>
|
||||
state <= rd_hold;
|
||||
when rd_hold =>
|
||||
state <= idle;
|
||||
when wr_init =>
|
||||
state <= wr_setup;
|
||||
when wr_setup =>
|
||||
if (WAIT_n = '1') then
|
||||
state <= wr;
|
||||
end if;
|
||||
when wr =>
|
||||
state <= wr_hold;
|
||||
when wr_hold =>
|
||||
state <= release;
|
||||
when release =>
|
||||
state <= idle;
|
||||
end case;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
RESET_n_int <= RESET_n and (not sw1) and nRST;
|
||||
|
||||
test1 <= TState(0);
|
||||
|
Loading…
x
Reference in New Issue
Block a user