URL
https://opencores.org/ocsvn/wb_z80/wb_z80/trunk
Subversion Repositories wb_z80
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 22 to Rev 23
- ↔ Reverse comparison
Rev 22 → Rev 23
/trunk/rtl/z80_core_top.v
37,10 → 37,10
/////////////////////////////////////////////////////////////////////////////////////////////// |
// CVS Log |
// |
// $Id: z80_core_top.v,v 1.2 2004-04-27 21:38:22 bporcella Exp $ |
// $Id: z80_core_top.v,v 1.3 2004-05-13 14:58:53 bporcella Exp $ |
// |
// $Date: 2004-04-27 21:38:22 $ |
// $Revision: 1.2 $ |
// $Date: 2004-05-13 14:58:53 $ |
// $Revision: 1.3 $ |
// $Author: bporcella $ |
// $Locker: $ |
// $State: Exp $ |
47,6 → 47,9
// |
// Change History: |
// $Log: not supported by cvs2svn $ |
// Revision 1.2 2004/04/27 21:38:22 bporcella |
// test lint on core |
// |
// Revision 1.1 2004/04/27 21:27:13 bporcella |
// first core build |
// |
62,21 → 65,24
// z80_sdram_config.v // fundamentally wishbone glue logic - not on top per design guidelines |
// add a comment test lint |
//-------1---------2---------3--------Module Name and Port List------7---------8---------9--------0 |
module z80_core_top( wb_dat_o, |
module z80_core_top( |
wb_dat_o, |
wb_stb_o, |
wb_cyc_o, |
wb_we_o, |
wb_adr_o, |
wb_tga_o, |
bist_ack_o, |
bist_err_o, |
wb_ack_i, |
wb_clk_i, |
wb_dat_i, |
wb_rst_i, |
`ifdef COMPILE_BIST |
bist_ack_o, |
bist_err_o, |
bist_req_i, |
`endif |
int_req_i |
|
|
); |
|
//-------1---------2---------3--------Output Ports---------6---------7---------8---------9--------0 |
87,8 → 93,6
output wb_we_o; |
output [15:0] wb_adr_o; |
output [1:0] wb_tga_o; |
output bist_ack_o; |
output bist_err_o; |
|
|
//-------1---------2---------3--------Input Ports----------6---------7---------8---------9--------0 |
96,18 → 100,24
input wb_ack_i; |
input wb_clk_i; |
input [7:0] wb_dat_i; |
input bist_req_i; |
input wb_rst_i; |
input int_req_i; |
|
|
`ifdef COMPILE_BIST |
output bist_err_o; |
output bist_ack_o; |
input bist_req_i; |
`endif |
|
|
//-------1---------2---------3--------Parameters-----------6---------7---------8---------9--------0 |
//-------1---------2---------3--------Wires------5---------6---------7---------8---------9--------0 |
wire [15:0] wb_adr_o; |
wire [15:0] add_out; // output of adder (may not wb_adr_o) |
wire [9:0] ir1, ir2; |
wire [15:0] nn; |
wire [15:0] sp; |
wire [7:0] ar, fr, br, cr, dr, er, hr, lr; |
wire [7:0] ar, fr, br, cr, dr, er, hr, lr, intr; |
wire [15:0] ixr, iyr; |
wire [7:0] wb_dat_i, wb_dat_o, sdram_do, cfg_do; |
wire [15:0] add16; // ir2 execution engine output for sp updates |
122,19 → 132,30
//-------1---------2---------3--------Assignments----------6---------7---------8---------9--------0 |
//-------1---------2---------3--------State Machines-------6---------7---------8---------9--------0 |
|
|
`ifdef COMPILE_BIST |
z80_bist_logic i_z80_bist_logic( |
.bist_err_o(bist_err_o), .bist_ack_o(bist_ack_o), |
.wb_adr_i(wb_adr_o), .wb_dat_i(wb_dat_o), .wb_we_i(wb_we_o), .wb_cyc_i(wb_cyc_o), |
.wb_stb_i(wb_stb_o), .wb_tga_i(wb_tga_o), .wb_clk_i(wb_clk_i), .wb_rst_i(wb_rst_i) |
); |
`endif |
|
|
|
z80_memstate2 i_z80_memstate2( |
.wb_adr_o(wb_adr_o), .wb_we_o(wb_we_o), .wb_cyc_o(wb_cyc_o), .wb_stb_o(wb_stb_o), .wb_tga_o(wb_tga_o), .wb_dat_o(wb_dat_o), |
.exec_ir2(exec_ir2), .ir1(ir1), .ir2(ir2), .ir1dd(ir1dd), .ir1fd(ir1fd), .ir2dd(ir2dd), .ir2fd(ir2fd), .nn(nn), .sp(sp), |
.upd_ar(upd_ar), .upd_br(upd_br), .upd_cr(upd_cr), .upd_dr(upd_dr), .upd_er(upd_er), .upd_hr(upd_hr), .upd_lr(upd_lr),.upd_fr(upd_fr), |
.beq0(beq0), .ceq0(ceq0), |
.beq0(br_eq0), .ceq0(cr_eq0), |
.ar(ar), .fr(fr), .br(br), .cr(cr), .dr(dr), .er(er), .hr(hr), .lr(lr), |
.ixr(ixr), .iyr(iyr), |
.wb_dat_i(cfg_do), .wb_ack_i(wb_ack_i), |
.wb_dat_i(cfg_do), .wb_ack_i(cfg_ack_o), |
.int_req_i(int_req_i), |
.add16(add16), |
.wb_clk_i(wb_clk_i), |
.rst_i(rst_i) // keep this generic - may turn out to be different from wb_rst |
); |
.rst_i(wb_rst_i) // keep this generic - may turn out to be different from wb_rst |
); |
|
|
z80_inst_exec i_z80_inst_exec( |
141,16 → 162,16
.br_eq0(br_eq0), |
.cr_eq0(cr_eq0), |
.upd_ar(upd_ar), .upd_br(upd_br), .upd_cr(upd_cr), .upd_dr(upd_dr), .upd_er(upd_er), .upd_hr(upd_hr), .upd_lr(upd_lr),.upd_fr(upd_fr), |
.ar(ar), .fr(fr), .br(br), .cr(cr), .dr(dr), .er(er), .hr(hr), .lr(lr), |
.ar(ar), .fr(fr), .br(br), .cr(cr), .dr(dr), .er(er), .hr(hr), .lr(lr), .intr(intr), |
.ixr(ixr), .iyr(iyr), .add16(add16), |
.exec_ir2(exec_ir2), |
.exec_decbc(exec_decbc), .exec_decb(exec_decb), |
.ir2(ir2), |
.clk(wb_clk_i), |
.rst(rst_i), |
.rst(wb_rst_i), |
.nn(nn), .sp(sp), |
.dd_grp(dd_grp), |
.fd_grp(fd_grp) |
.ir2dd(ir2dd), |
.ir2fd(ir2fd) |
); |
|
// The parameter passed to i_generic_sprem specifies the number of address bits used by the |
162,21 → 183,22
// happy with this...... Depending on which target technology is specified, read behavior changes. |
// It is easy to insure all possible behavior will in fact operate properly -- see the data reduction |
// logic in sdram_cfg.v -- but still... I guess the important thing to be aware of is that |
// big memories like this typically require special back-end handleing. This is likely to prove |
// big memories like this typically require special back-end handeling. This is likely to prove |
// no exception - despite the work that has been done to make this file as generally useful as |
// possible. |
|
generic_spram #(12) i_generic_spram( |
generic_spram #(15) i_generic_spram( |
// Generic synchronous single-port RAM interface |
.clk(wb_clk_i), .rst(rst_i), .ce(cfg_ce_spram_o), .we(wb_we_o), .oe(1'b1), .addr(wb_adr_o[11:0]), .di(wb_dat_o), .do(sdram_do) |
); |
.clk(wb_clk_i), .rst(wb_rst_i), .ce(cfg_ce_spram_o), .we(wb_we_o), .oe(1'b1), .addr(wb_adr_o[14:0]), .di(wb_dat_o), .do(sdram_do) |
); |
|
|
|
z80_sdram_cfg i_z80_sdram_cfg( |
.cfg_ce_spram_o(cfg_ce_spram_o), .cfg_do(cfg_do), .cfg_ack_o(cfg_ack_o), .sdram_di(sdram_do), |
.wb_adr_i(wb_adr_o), .wb_dat_i(wb_dat_i), .wb_ack_i(wb_ack_i), .wb_stb_i(wd_stb_o), |
.wb_cyc_i(wb_cyc_o), .wb_tga_i(wb_tga_o) ); |
.wb_adr_i(wb_adr_o), .wb_dat_i(wb_dat_i), .wb_ack_i(wb_ack_i), .wb_stb_i(wb_stb_o), |
.wb_cyc_i(wb_cyc_o), .wb_tga_i(wb_tga_o) |
); |
|
|
endmodule |
/trunk/rtl/files.txt
1,8 → 1,10
+incdir+. |
z80_core_top.v |
z80_inst_exec.v |
z80_memstate2.v |
z80_sdram_cfg.v |
generic_spram.v |
+incdir+rtl |
rtl\z80_testbed.v |
rtl\z80_bist_logic.v |
rtl\z80_core_top.v |
rtl\z80_inst_exec.v |
rtl\z80_memstate2.v |
rtl\z80_sdram_cfg.v |
rtl\generic_spram.v |
|
|
/trunk/rtl/generic_spram.v
67,6 → 67,9
// CVS Revision History |
// |
// $Log: not supported by cvs2svn $ |
// Revision 1.1 2004/04/27 21:27:13 bporcella |
// first core build |
// |
// Revision 1.3 2001/11/09 00:34:19 samg |
// minor changes: unified with all common rams |
// |
90,7 → 93,21
//`define VENDOR_XILINX |
//`define VENDOR_ALTERA |
//`define VENDOR_FPGA |
|
// |
//--------------------- WARNING ------------------------------------ |
// |
// The way this "generic" ram works is not compatable with ANY SRAM that |
// I have used in 30 years in this industry....... |
// |
// WHY register the address on read - but not on write? makes absolutly |
// no sense to me. I suppose that there might be no real register file |
// compatable SRAMS in some of the FPGA libraries. In which case, I probably |
// need to make modifications to the basic core. |
// |
// Well for now just patch this to work like I expected, |
// |
// AS OF 4/29/2004 this is a seriously modified file. bjp |
// see changes under bjp below |
module generic_spram( |
// Generic synchronous single-port RAM interface |
clk, rst, ce, we, oe, addr, di, do |
118,155 → 135,7
// Module body |
// |
|
`ifdef VENDOR_FPGA |
// |
// Instantiation synthesizeable FPGA memory |
// |
// This code has been tested using LeonardoSpectrum and Synplicity. |
// The code correctly instantiates Altera EABs and Xilinx BlockRAMs. |
// |
reg [dw-1 :0] mem [(1<<aw) -1:0]; |
reg [aw-1:0] raddr; |
|
always@(posedge clk) |
begin |
// read operation |
raddr <= #1 addr; // read address needs to be registered to read clock |
|
// write operation |
if (we && ce) |
mem[addr] <= #1 di; |
end |
|
assign #1 do = mem[raddr]; |
|
`else |
|
`ifdef VENDOR_XILINX |
|
wire [dw-1:0] q; // output from xilinx ram |
// |
// Instantiation of FPGA memory: |
// |
// Virtex/Spartan2 BlockRAMs |
// |
xilinx_ram_sp xilinx_ram( |
.clk(clk), |
.rst(rst), |
.addr(addr), |
.di(di), |
.en(ce), |
.we(we), |
.do(do) |
); |
|
defparam |
xilinx_ram.dwidth = dw, |
xilinx_ram.awidth = aw; |
|
`else |
|
`ifdef VENDOR_ALTERA |
|
// |
// Instantiation of FPGA memory: |
// |
// Altera FLEX EABs |
// |
|
altera_ram_sp altera_ram( |
.inclock(clk), |
.address(addr), |
.data(di), |
.we(we && ce), |
.q(do) |
); |
|
defparam |
altera_ram.dwidth = dw, |
altera_ram.awidth = aw; |
|
`else |
|
`ifdef VENDOR_ARTISAN |
|
// |
// Instantiation of ASIC memory: |
// |
// Artisan Synchronous Single-Port RAM (ra1sh) |
// |
artisan_ssp #(dw, 1<<aw, aw) artisan_ssp( |
.CLK(clk), |
.CEN(~ce), |
.WEN(~we), |
.A(addr), |
.D(di), |
.OEN(~oe), |
.Q(do) |
); |
|
`else |
|
`ifdef VENDOR_AVANT |
|
// |
// Instantiation of ASIC memory: |
// |
// Avant! Asynchronous Two-Port RAM |
// |
avant_atp avant_atp( |
.web(~we), |
.reb(), |
.oeb(~oe), |
.rcsb(), |
.wcsb(), |
.ra(addr), |
.wa(addr), |
.di(di), |
.do(do) |
); |
|
`else |
|
`ifdef VENDOR_VIRAGE |
|
// |
// Instantiation of ASIC memory: |
// |
// Virage Synchronous 1-port R/W RAM |
// |
virage_ssp virage_ssp( |
.clk(clk), |
.adr(addr), |
.d(di), |
.we(we), |
.oe(oe), |
.me(ce), |
.q(do) |
); |
|
`else |
|
`ifdef VENDOR_VIRTUALSILICON |
|
// |
// Instantiation of ASIC memory: |
// |
// Virtual Silicon Single-Port Synchronous SRAM |
// |
virtualsilicon_spram #(1<<aw, aw-1, dw-1) virtualsilicon_ssp( |
.CK(clk), |
.ADR(addr), |
.DI(di), |
.WEN(~we), |
.CEN(~ce), |
.OEN(~oe), |
.DOUT(do) |
); |
|
`else |
|
// |
// Generic single-port synchronous RAM model |
// |
|
274,156 → 143,33
// Generic RAM's registers and wires |
// |
reg [dw-1:0] mem [(1<<aw)-1:0]; // RAM content |
wire [dw-1:0] q; // RAM output |
reg [aw-1:0] raddr; // RAM read address |
|
// bjp change was |
//reg [aw-1:0] raddr; // RAM read address |
//wire raddr = addr; |
// |
// Data output drivers |
// |
assign do = (oe & ce) ? q : {dw{1'bz}}; |
assign do = (oe & ce) ? mem[addr] : {dw{1'bz}}; |
|
// |
// RAM read and write |
// |
|
// read operation |
always@(posedge clk) |
if (ce) // && !we) |
raddr <= #1 addr; // read address needs to be registered to read clock |
// bjp read operation made asynchronous (only write is on clock) |
//always@(posedge clk) |
//if (ce) // && !we) |
// raddr <= #1 addr; // read address needs to be registered to read clock |
|
|
assign #1 q = rst ? {dw{1'b0}} : mem[raddr]; |
|
// write operation |
always@(posedge clk) |
if (ce && we) |
mem[addr] <= #1 di; |
mem[addr] <= di; |
|
// Task prints range of memory |
// *** Remember that tasks are non reentrant, don't call this task in parallel for multiple instantiations. |
task print_ram; |
input [aw-1:0] start; |
input [aw-1:0] finish; |
integer rnum; |
begin |
for (rnum=start;rnum<=finish;rnum=rnum+1) |
$display("Addr %h = %h",rnum,mem[rnum]); |
end |
endtask |
|
`endif // !VIRTUALSILICON_SSP |
`endif // !VIRAGE_SSP |
`endif // !AVANT_ATP |
`endif // !ARTISAN_SSP |
`endif // !VENDOR_ALTERA |
`endif // !VENDOR_XILINX |
`endif // !VENDOR_FPGA |
|
endmodule |
|
|
// |
// Black-box modules |
// |
|
`ifdef VENDOR_ALTERA |
module altera_ram_sp ( |
address, |
inclock, |
we, |
data, |
q) /* synthesis black_box */; |
|
parameter awidth = 7; |
parameter dwidth = 8; |
|
input [awidth -1:0] address; |
input inclock; |
input we; |
input [dwidth -1:0] data; |
output [dwidth -1:0] q; |
|
// synopsis translate_off |
// exemplar translate_off |
|
syn_ram_irou #( |
"UNUSED", |
dwidth, |
awidth, |
1 << awidth |
) |
altera_spram_model ( |
.Inclock(inclock), |
.Address(address), |
.Data(data), |
.WE(we), |
.Q(q) |
); |
|
// exemplar translate_on |
// synopsis translate_on |
|
endmodule |
`endif // VENDOR_ALTERA |
|
`ifdef VENDOR_XILINX |
module xilinx_ram_sp ( |
clk, |
rst, |
addr, |
di, |
en, |
we, |
do) /* synthesis black_box */ ; |
|
parameter awidth = 7; |
parameter dwidth = 8; |
|
input clk; |
input rst; |
input [awidth -1:0] addr; |
input [dwidth -1:0] di; |
input en; |
input we; |
output [dwidth -1:0] do; |
|
// insert simulation model |
|
|
// synopsys translate_off |
// exemplar translate_off |
|
C_MEM_SP_BLOCK_V1_0 #( |
awidth, |
1, |
"0", |
1 << awidth, |
1, |
1, |
1, |
1, |
1, |
1, |
1, |
"", |
16, |
0, |
0, |
1, |
1, |
dwidth |
) |
xilinx_spram_model ( |
.CLK(clk), |
.RST(rst), |
.ADDR(addr), |
.DI(di), |
.EN(en), |
.WE(we), |
.DO(do) |
); |
|
// exemplar translate_on |
// synopsys translate_on |
|
endmodule |
`endif // VENDOR_XILINX |
|
/trunk/rtl/z80_inst_exec.v
71,10 → 71,10
// |
//-------1---------2---------3--------CVS Log -----------------------7---------8---------9--------0 |
// |
// $Id: z80_inst_exec.v,v 1.1 2004-04-27 21:27:13 bporcella Exp $ |
// $Id: z80_inst_exec.v,v 1.2 2004-05-13 14:58:53 bporcella Exp $ |
// |
// $Date: 2004-04-27 21:27:13 $ |
// $Revision: 1.1 $ |
// $Date: 2004-05-13 14:58:53 $ |
// $Revision: 1.2 $ |
// $Author: bporcella $ |
// $Locker: $ |
// $State: Exp $ |
81,6 → 81,9
// |
// Change History: |
// $Log: not supported by cvs2svn $ |
// Revision 1.1 2004/04/27 21:27:13 bporcella |
// first core build |
// |
// Revision 1.4 2004/04/19 19:13:27 bporcella |
// real lint problems pretty much fixed -- need another look - but need to get on to other things first |
// |
99,7 → 102,7
module z80_inst_exec( br_eq0, |
cr_eq0, |
upd_ar, upd_br, upd_cr, upd_dr, upd_er, upd_hr, upd_lr,upd_fr, |
ar, fr, br, cr, dr, er, hr, lr, |
ar, fr, br, cr, dr, er, hr, lr, intr, |
ixr, iyr, add16, |
exec_ir2, |
exec_decbc, exec_decb, |
107,8 → 110,8
clk, |
rst, |
nn, sp, |
dd_grp, |
fd_grp |
ir2dd, |
ir2fd |
); |
|
//-------1---------2---------3--------Output Ports---------6---------7---------8---------9--------0 |
115,7 → 118,7
output br_eq0; |
output cr_eq0; |
output upd_ar, upd_br, upd_cr, upd_dr, upd_er, upd_hr, upd_lr,upd_fr; |
output [7:0] ar, fr, br, cr, dr, er, hr, lr; |
output [7:0] ar, fr, br, cr, dr, er, hr, lr, intr; |
output [15:0] ixr, iyr; |
output [15:0] add16; |
//-------1---------2---------3--------Input Ports----------6---------7---------8---------9--------0 |
126,8 → 129,8
input clk; |
input rst; |
input [15:0] nn, sp; |
input dd_grp; // this must be ir2 |
input fd_grp; |
input ir2dd; // this must be ir2 |
input ir2fd; |
|
//-------1---------2---------3--------Parameters-----------6---------7---------8---------9--------0 |
`include "opcodes.v" |
203,7 → 206,7
wire upd_fr_edadd16 ; |
wire upd_fr_sh ; |
wire upd_fr_cbsh ; |
wire eb_blk_mv ; |
//wire eb_blk_mv ; |
wire ed_blk_cp ; |
wire c_8in0 ; |
|
220,16 → 223,16
// pipeline is such that we can make a fetch for free - so we will do that..... the |
// prefix flags should not be set here -- all we will know on execution is that it is a |
// cb instruction. ---- src is always nn |
assign src_hr = dd_grp ? ixr[15:8] : |
fd_grp ? iyr[15:8] : |
assign src_hr = ir2dd ? ixr[15:8] : |
ir2fd ? iyr[15:8] : |
hr ; |
|
assign src_lr = dd_grp ? ixr[7:0] : |
fd_grp ? iyr[7:0] : |
assign src_lr = ir2dd ? ixr[7:0] : |
ir2fd ? iyr[7:0] : |
lr ; |
|
assign src_dblhr = dd_grp ? ixr : // ed grp instructions (ADC HL ; SBC HL are not affected - |
fd_grp ? iyr : // instruction assembler assures this - ed_grp has no prefix |
assign src_dblhr = ir2dd ? ixr : // ed grp instructions (ADC HL ; SBC HL are not affected - |
ir2fd ? iyr : // instruction assembler assures this - ed_grp has no prefix |
{hr, lr} ; |
// ddcb_grp not defined - src_cb_r20 not used. Why these lines? 4/17/2004 |
//assign src_cb_r20 = (ddcb_grp | fdcb_grp) ? nn[7:0] : |
261,9 → 264,9
{16{ir2[5:4]==2'b10}} & src_dblhr | // HL, ixr, iyr |
{16{ir2[5:4]==2'b11}} & sp ; |
|
assign sh_src = ir2[8] & dd_grp ? nn[15:8] : |
ir2[8] & fd_grp ? nn[15:8] : |
ir2 ? src_pqr20 : |
assign sh_src = ir2[8] & ir2dd ? nn[15:8] : |
ir2[8] & ir2fd ? nn[15:8] : |
ir2[8] ? src_pqr20 : |
ar ; |
// I wonder how well the synthesizer can reduce this??? - It is probably worth spending |
// some time during physical design to see if a more low level description would help -- |
311,7 → 314,7
// f3f fpv fn fc |
alu8_out[3], alu8_out[7], alu8_nf, c_8out7 }; |
|
//assign alu8_pvf = (ir2[7:3]==5'b10100 | ir2[7:3]==5'b10101 | ir2[7:3]==5'b10110) ? |
//assign alu8_pvf = (ir2[9:3]==5'b10100 | ir2[9:3]==5'b10101 | ir2[7:3]==5'b10110) ? |
// ~^alu8_out : // even parity |
// (src_aor_cnst[7]==src_pqri[7]) & (src_aor_cnst[7]!=alu8_out[7]) ; // ofl |
|
335,16 → 338,16
|
ed_blk_cp ? {c_8out7,c_8out3, add_8bit, ~src_pqr20, 1'h1} : //CPI CPIR CPD CPDR |
|
{19{ir2[7:3]==5'b10000}} & ({c_8out7,c_8out3, add_8bit, src_pqr20, 1'b0} ) |// a+src |
{19{ir2[7:3]==5'b10001}} & ({c_8out7,c_8out3, add_8bit, src_pqr20, cf} ) |// a+src+cf |
{19{ir2[7:3]==5'b10010}} & ({c_8out7,c_8out3, add_8bit, ~src_pqr20, 1'h1} ) |// a-src |
{19{ir2[7:3]==5'b10011}} & ({c_8out7,c_8out3, add_8bit, ~src_pqr20, ~cf } ) |// a-src-cf |
{19{ir2[7:3]==5'b10100}} & ({1'b0 ,1'b1 , ar & src_pqr20, src_pqr20, 1'b0} ) |// a&src |
{19{ir2[7:3]==5'b10101}} & ({1'b0 ,1'b0 , ar ^ src_pqr20, src_pqr20, 1'b0} ) |// a^src |
{19{ir2[7:3]==5'b10110}} & ({1'b0 ,1'b0 , ar | src_pqr20, src_pqr20, 1'b0} ) |// a|src |
{19{ir2[7:3]==5'b10111}} & ({c_8out7,c_8out3, add_8bit, src_pqr20, 1'h1}) |// a-src |
{19{(ir2[7:6]==2'b00)& ~ir2[0] }}& ({ cf,c_8out3, add_8bit, src_pqr53, 1'h1}) |// inc_r main |
{19{(ir2[7:6]==2'b00)& ir2[0] }}& ({ cf,c_8out3, add_8bit, src_pqr53, 1'h0}) |// dec_r |
{19{ir2[7] & ir2[5:3]==3'b000}} & ({c_8out7,c_8out3, add_8bit, src_pqr20, 1'b0} ) |// a+src |
{19{ir2[7] & ir2[5:3]==5'b001}} & ({c_8out7,c_8out3, add_8bit, src_pqr20, cf} ) |// a+src+cf |
{19{ir2[7] & ir2[5:3]==5'b010}} & ({c_8out7,c_8out3, add_8bit, ~src_pqr20, 1'h1} ) |// a-src |
{19{ir2[7] & ir2[5:3]==5'b011}} & ({c_8out7,c_8out3, add_8bit, ~src_pqr20, ~cf } ) |// a-src-cf |
{19{ir2[7] & ir2[5:3]==5'b100}} & ({1'b0 ,1'b1 , ar & src_pqr20, src_pqr20, 1'b0} )|// a&src |
{19{ir2[7] & ir2[5:3]==5'b101}} & ({1'b0 ,1'b0 , ar ^ src_pqr20, src_pqr20, 1'b0} )|// a^src |
{19{ir2[7] & ir2[5:3]==5'b110}} & ({1'b0 ,1'b0 , ar | src_pqr20, src_pqr20, 1'b0} )|// a|src |
{19{ir2[7] & ir2[5:3]==5'b111}} & ({c_8out7,c_8out3, add_8bit, ~src_pqr20, 1'h1}) |// a-src |
{19{(ir2[7:6]==2'b00)& ~ir2[0] }}& ({ cf,c_8out3, add_8bit, src_pqr53, 1'h1}) |// inc_r main |
{19{(ir2[7:6]==2'b00)& ir2[0] }}& ({ cf,c_8out3, add_8bit, src_pqr53, 1'h0}) |// dec_r |
{19{(ir2[7:6]==2'b01) }}& ({c_8out7,c_8out3, add_8bit, ~ar, 1'h1}) ;// ed44 -a |
|
|
379,7 → 382,7
// in assembly code as they appear to have some utility - and by all accounts operate reliably. |
// The first four are implemented in a single byte inaruction . (A <= sh_op A ) |
// All 8 are implemented in the CB group with all registers as potential sources (and dests). |
// if dd_grp or fd_grp is prefix..... source is always the memory. This is undocumented - but |
// if ir2dd or ir2fd is prefix..... source is always the memory. This is undocumented - but |
// may be a useful hint for simplyfing the total machine. Destination registers |
// (if any) get a copy of the updated memory location (This is also true of the bit set and |
// clear instructions in the cb_grp. |
537,7 → 540,7
if (upd_a_alu8 & exec_ir2) ar <= alu8_out; |
if (up_a_sh_alu & exec_ir2) ar <= sh_alu; |
if (up_a_src_pqr & exec_ir2) ar <= src_pqr20; |
if (up_a_n & exec_ir2) ar <= nn[7:0]; |
if (up_a_n & exec_ir2) ar <= nn[15:8]; // changed for LD A N |
if (ir2 == EXsAF_AFp & exec_ir2) ar <= ap; |
if (ir2 == EXX & exec_ir2) ar <= ap; |
if (ir2 == DAA & exec_ir2) ar <= daa_alu; |
620,7 → 623,7
if ( LDsBC_NN == ir2 & exec_ir2) br <= nn[15:8]; |
if ( POPsBC == ir2 & exec_ir2) br <= nn[15:8]; |
if ( EXX == ir2 & exec_ir2) br <= bp; |
if ( LDsB_N == ir2 & exec_ir2) br <= nn[7:0]; |
if ( LDsB_N == ir2 & exec_ir2) br <= nn[15:8]; |
if (ir2[2:0] == REG8_B & |
bit_alu_act & exec_ir2) br <= bit_alu; |
if (ir2[2:0] == REG8_B & |
630,7 → 633,7
// use |br. If we need more speed add |
// a ff. |
if (exec_decb | exec_decbc) br <= decb_alu; |
if ( (ED_INsREG_6C7 == {ir2[7:6],ir2[2:0]}) & (ir2[5:3] == REG8_B) & exec_ir2 ) |
if ( (ED_INsREG_6C7 == {ir2[9:6],ir2[2:0]}) & (ir2[5:3] == REG8_B) & exec_ir2 ) |
br <= nn[7:0]; |
end |
|
675,7 → 678,7
if ( LDsBC_NN == ir2 & exec_ir2) cr <= nn[7:0]; |
if ( POPsBC == ir2 & exec_ir2) cr <= nn[7:0]; |
if ( EXX == ir2 & exec_ir2) cr <= cp; |
if ( LDsC_N == ir2 & exec_ir2) cr <= nn[7:0]; |
if ( LDsC_N == ir2 & exec_ir2) cr <= nn[15:8]; |
if (ir2[2:0] == REG8_C & |
bit_alu_act & exec_ir2) cr <= bit_alu; |
if (ir2[2:0] == REG8_C & |
734,7 → 737,7
if ( POPsDE == ir2 & exec_ir2) dr <= nn[15:8]; |
if ( EXX == ir2 & exec_ir2) dr <= dp; |
if ( EXsDE_HL == ir2 & exec_ir2) dr <= hr; |
if ( LDsD_N == ir2 & exec_ir2) dr <= nn[7:0]; |
if ( LDsD_N == ir2 & exec_ir2) dr <= nn[15:8]; |
if (ir2[2:0] == REG8_D & |
bit_alu_act & exec_ir2) dr <= bit_alu; |
if (ir2[2:0] == REG8_D & |
794,7 → 797,7
if ( POPsDE == ir2 & exec_ir2) er <= nn[7:0]; |
if ( EXX == ir2 & exec_ir2) er <= ep; |
if ( EXsDE_HL == ir2 & exec_ir2) er <= hr; |
if ( LDsE_N == ir2 & exec_ir2) er <= nn[7:0]; |
if ( LDsE_N == ir2 & exec_ir2) er <= nn[15:8]; |
if (ir2[2:0] == REG8_E & |
bit_alu_act & exec_ir2) er <= bit_alu; |
if (ir2[2:0] == REG8_E & |
850,7 → 853,7
|
|
|
wire exec_hlir2 = exec_ir2 & !(dd_grp | fd_grp); |
wire exec_hlir2 = exec_ir2 & !(ir2dd | ir2fd); |
|
always @(posedge clk) |
begin |
863,7 → 866,7
if ( EXs6SP7_HL== ir2 & exec_hlir2) hr <= nn[15:8]; |
if ( EXX == ir2 & exec_ir2) hr <= hp; |
if ( EXsDE_HL == ir2 & exec_ir2) hr <= dr; |
if ( LDsH_N == ir2 & exec_hlir2) hr <= nn[7:0]; |
if ( LDsH_N == ir2 & exec_hlir2) hr <= nn[15:8]; |
if (ir2[2:0] == REG8_H & |
bit_alu_act & exec_hlir2) hr <= bit_alu; |
if (ir2[2:0] == REG8_H & |
923,7 → 926,7
if ( EXs6SP7_HL== ir2 & exec_hlir2) lr <= nn[7:0]; |
if ( EXX == ir2 & exec_ir2) lr <= lp; |
if ( EXsDE_HL == ir2 & exec_ir2) lr <= er; |
if ( LDsL_N == ir2 & exec_hlir2) lr <= nn[7:0]; |
if ( LDsL_N == ir2 & exec_hlir2) lr <= nn[15:8]; |
if (ir2[2:0] == REG8_L & |
bit_alu_act & exec_hlir2) lr <= bit_alu; |
if (ir2[2:0] == REG8_L & |
933,7 → 936,7
|
end |
//------------------------ ixr --------------------------------------------- |
wire exec_ixir2 = exec_ir2 & dd_grp; |
wire exec_ixir2 = exec_ir2 & ir2dd; |
always @(posedge clk) |
begin |
if ( upd_l_alu8 & exec_ixir2) ixr[7:0] <= alu8_out; |
944,7 → 947,7
if ( POPsHL == ir2 & exec_ixir2) ixr[7:0] <= nn[7:0]; |
if ( EXs6SP7_HL== ir2 & exec_ixir2) ixr[7:0] <= nn[7:0]; |
|
if ( LDsL_N == ir2 & exec_ixir2) ixr[7:0] <= nn[7:0]; |
if ( LDsL_N == ir2 & exec_ixir2) ixr[7:0] <= nn[15:8]; |
if (ir2[2:0] == REG8_L & |
bit_alu_act & exec_ixir2) ixr[7:0] <= bit_alu; |
if (ir2[2:0] == REG8_L & |
962,7 → 965,7
if ( POPsHL == ir2 & exec_ixir2) ixr[15:8] <= nn[15:8]; |
if ( EXs6SP7_HL== ir2 & exec_ixir2) ixr[15:8] <= nn[15:8]; |
|
if ( LDsH_N == ir2 & exec_ixir2) ixr[15:8] <= nn[7:0]; |
if ( LDsH_N == ir2 & exec_ixir2) ixr[15:8] <= nn[15:8]; |
if (ir2[2:0] == REG8_H & |
bit_alu_act & exec_ixir2) ixr[15:8] <= bit_alu; |
if (ir2[2:0] == REG8_H & |
971,7 → 974,7
end |
|
//------------------------ iyr --------------------------------------------- |
wire exec_iyir2 = exec_ir2 & fd_grp; |
wire exec_iyir2 = exec_ir2 & ir2fd; |
always @(posedge clk) |
begin |
if ( upd_l_alu8 & exec_iyir2) iyr[7:0] <= alu8_out; |
982,7 → 985,7
if ( POPsHL == ir2 & exec_iyir2) iyr[7:0] <= nn[7:0]; |
if ( EXs6SP7_HL== ir2 & exec_iyir2) iyr[7:0] <= nn[7:0]; |
|
if ( LDsL_N == ir2 & exec_iyir2) iyr[7:0] <= nn[7:0]; |
if ( LDsL_N == ir2 & exec_iyir2) iyr[7:0] <= nn[15:8]; |
if (ir2[2:0] == REG8_L & |
bit_alu_act & exec_iyir2) iyr[7:0] <= bit_alu; |
if (ir2[2:0] == REG8_L & |
1000,7 → 1003,7
if ( POPsHL == ir2 & exec_iyir2) iyr[15:8] <= nn[15:8]; |
if ( EXs6SP7_HL== ir2 & exec_iyir2) iyr[15:8] <= nn[15:8]; |
|
if ( LDsH_N == ir2 & exec_iyir2) iyr[15:8] <= nn[7:0]; |
if ( LDsH_N == ir2 & exec_iyir2) iyr[15:8] <= nn[15:8]; |
if (ir2[2:0] == REG8_H & |
bit_alu_act & exec_iyir2) iyr[15:8] <= bit_alu; |
if (ir2[2:0] == REG8_H & |
1071,6 → 1074,7
ADDsA_H == ir2 | CPsH == ir2 | SBCsE == ir2 | XORsH == ir2 | INCsL == ir2 | |
ADDsA_L == ir2 | CPsL == ir2 | SBCsH == ir2 | XORsL == ir2 | INCs6HL7 == ir2 | |
ADDsA_6HL7== ir2| CPs6HL7 ==ir2 | SBCsL == ir2 | XORs6HL7 == ir2 | DECs6HL7 == ir2 | |
CPsN == ir2 | |
ED_NEG == {ir2[9:6],ir2[2:0]} ; //7'b1001___100, A<= -A |
|
|
1114,7 → 1118,7
// pretty nomal stuff here |
//CB_BIT = 4'b01_01, // these must be compaired with ir2[9:6] |
// which alu? -- done from alu8 |
//ED_NEG = 5'b01___100, // compair with {ir2[7:6],ir2[2:0]} all A<= -A |
//ED_NEG = 5'b01___100, // compair with {ir2[9:6],ir2[2:0]} all A<= -A |
|
// rmw 8 types these handled by standard INC and DEC logic done. |
//INCs6HL7 = 'h34,// INC (HL) ; 34 |
1146,7 → 1150,7
//ED_OTIR = 'hB3// OTIR ; ED B3 (Cio) <-(HL++) , B-- rpt if(|B) |
//ED_OTDR = 'hBB// OTDR ; ED BB (Cio) <-(HL--) , B-- rpt if(|B) |
|
//ED_INsREG_6C7 = 5'b01___000,// compair with {ir2[7:6],ir2[2:0]} really (BCio) |
//ED_INsREG_6C7 = 5'b01___000,// compair with {ir2[9:6],ir2[2:0]} really (BCio) |
|
|
|
1173,7 → 1177,7
( upd_fr_cbsh ) | |
(CB_BIT == ir2[9:6]) | |
( ed_blk_cp ) | |
(ED_INsREG_6C7 == {ir2[7:6],ir2[2:0]}) | |
(ED_INsREG_6C7 == {ir2[9:6],ir2[2:0]}) | |
(CCF == ir2 ) | |
(CPL == ir2 ) | |
(DAA == ir2 ) | |
1202,7 → 1206,7
bit_alu[3], ~|bit_alu, 1'b0 , cf };// pvf == zf ??? |
if ( ed_blk_cp ) fr <= {alu8_out[7], ~|alu8_out, alu8_out[5], alu8_hcry,//std a-n stuff |
alu8_out[3], alu8_out[7], 1'b1, cf }; //cept nf and cf |
if (ED_INsREG_6C7 == {ir2[7:6],ir2[2:0]}) |
if (ED_INsREG_6C7 == {ir2[9:6],ir2[2:0]}) |
fr <= {nn[7], ~|nn[7:0], nn[5], 1'b0, nn[3], ~^nn[7:0], 1'b0, cf}; |
if (CCF == ir2 ) fr <= {sf, zf, f5f, cf, f3f, pvf, nf, ~cf}; |
if (CPL == ir2 ) fr <= {sf, zf, ar[5], 1'b1, ar[3], pvf, 1'b1, cf}; |
/trunk/rtl/z80_memstate2.v
1,6 → 1,6
/////////////////////////////////////////////////////////////////////////////////////////////////// |
// // |
// file name: memstate2.v // |
// file name: memstate2.v // |
// description: memory opertions for z80 // |
// project: wb_z80 // |
// // |
109,10 → 109,10
// complete before starting the ir1 operation |
//-------1---------2---------3--------CVS Log -----------------------7---------8---------9--------0 |
// |
// $Id: z80_memstate2.v,v 1.1 2004-04-27 21:27:13 bporcella Exp $ |
// $Id: z80_memstate2.v,v 1.2 2004-05-13 14:58:53 bporcella Exp $ |
// |
// $Date: 2004-04-27 21:27:13 $ |
// $Revision: 1.1 $ |
// $Date: 2004-05-13 14:58:53 $ |
// $Revision: 1.2 $ |
// $Author: bporcella $ |
// $Locker: $ |
// $State: Exp $ |
119,6 → 119,9
// |
// Change History: |
// $Log: not supported by cvs2svn $ |
// Revision 1.1 2004/04/27 21:27:13 bporcella |
// first core build |
// |
// Revision 1.8 2004/04/19 19:13:28 bporcella |
// real lint problems pretty much fixed -- need another look - but need to get on to other things first |
// |
301,7 → 304,9
I1_RET = 4'ha, |
I1_RMW = 4'hb, |
I1_RST = 4'hc, |
I1_R2R = 4'hd ; |
I1_R2R = 4'hd, |
I1_JMPR = 4'he, |
I1_HALT = 4'hf; |
|
|
// A note here on the choices of mnemonics..... in general, the target registers of |
326,7 → 331,7
MEM_OSADRP1 = 5'h0d, // "" "" "" |
|
MEM_IFRST = 5'h0e, // special address transfer |
MEM_IFREL_N = 5'h0f, // special address transfer for jmp rel |
MEM_REL2PC = 5'h0f, // special address transfer for jmp rel |
MEM_JMPHL = 5'h10, // another special jump transfer |
MEM_IFNN = 5'h11, // used by call and return |
|
454,11 → 459,11
{I1DCNT {ANDsN == ir1}} & I1_N |// AND N ; E6 XX |
{I1DCNT {CPsN == ir1}} & I1_N |// CP N ; FE XX |
{I1DCNT {INsA_6N7 == ir1}} & I1_N |// IN A,(N) ; DB XX |
{I1DCNT {JRs$t2 == ir1}} & I1_N |// JR $+2 ; 18 XX |
{I1DCNT {JRsC_$t2 == ir1}} & I1_N |// JR C,$+2 ; 38 XX |
{I1DCNT {JRsNC_$t2 == ir1}} & I1_N |// JR NC,$+2 ; 30 XX |
{I1DCNT {JRsZ_$t2 == ir1}} & I1_N |// JR Z,$+2 ; 28 XX |
{I1DCNT {JRsNZ_$t2 == ir1}} & I1_N |// JR NZ,$+2 ; 20 XX |
{I1DCNT {JRs$t2 == ir1}} & I1_JMPR|// JR $+2 ; 18 XX |
{I1DCNT {JRsC_$t2 == ir1}} & I1_JMPR|// JR C,$+2 ; 38 XX |
{I1DCNT {JRsNC_$t2 == ir1}} & I1_JMPR|// JR NC,$+2 ; 30 XX |
{I1DCNT {JRsZ_$t2 == ir1}} & I1_JMPR|// JR Z,$+2 ; 28 XX |
{I1DCNT {JRsNZ_$t2 == ir1}} & I1_JMPR|// JR NZ,$+2 ; 20 XX |
{I1DCNT {LDs6HL7_N == ir1}} & I1_N |// LD (HL),N ; 36 XX |
{I1DCNT {LDsA_N == ir1}} & I1_N |// LD A,N ; 3E XX |
{I1DCNT {LDsB_N == ir1}} & I1_N |// LD B,N ; 06 XX |
584,7 → 589,7
{I1DCNT {EXX == ir1}} & I1_R2R |// EXX ; D9 |
{I1DCNT {EXsAF_AFp == ir1}} & I1_R2R |// EX AF,AF' ; 08 |
{I1DCNT {EXsDE_HL == ir1}} & I1_R2R |// EX DE,HL ; EB |
{I1DCNT {HALT == ir1}} & I1_R2R |// HALT ; 76 |
{I1DCNT {HALT == ir1}} & I1_HALT |// HALT ; 76 |
{I1DCNT {INCsA == ir1}} & I1_R2R |// INC A ; 3C |
{I1DCNT {INCsB == ir1}} & I1_R2R |// INC B ; 04 |
{I1DCNT {INCsBC == ir1}} & I1_R2R |// INC BC ; 03 |
812,7 → 817,14
JRsC_$t2 == ir1 & fr[0] | |
JRsNC_$t2 == ir1 & ~fr[0] | |
JRsZ_$t2 == ir1 & fr[6] | |
JRsNZ_$t2 == ir1 & ~fr[6] ; |
JRsNZ_$t2 == ir1 & ~fr[6] ; |
wire jmpr = |
JRs$t2 == ir1 | |
JRsC_$t2 == ir1 | |
JRsNC_$t2 == ir1 | |
JRsZ_$t2 == ir1 | |
JRsNZ_$t2 == ir1 ; |
|
|
//assign { sf, zf. f5f, hf, f3f, pvf, nf, cf} = fr; |
wire callnn_true = CALLsC_NN == ir1 & cf | |
916,16 → 928,32
// 2) flag tests when fr is being updated |
// 3) sp issues see below LDsSP_HL DECsSP INCsSP |
// ANY OTHERS ??? |
// 4) Indirect addressing -(HL) (BC) (DE) when address registers are updated |
// |
// upd_ar, upd_br, upd_cr, upd_dr, upd_er, upd_hr, upd_lr,upd_fr, |
wire use_hl_exec = LDsSP_HL == ir1; |
wire use_hl_exec = LDsSP_HL == ir1 | INCs6HL7 == ir1 | |
ADCsA_6HL7 == ir1 | SBCs6HL7 == ir1 | |
ADDsA_6HL7 == ir1 | SUBs6HL7 == ir1 | |
ANDs6HL7 == ir1 | XORs6HL7 == ir1 | |
CPs6HL7 == ir1 | LDs6HL7_A == ir1 | |
LDsA_6HL7 == ir1 | LDs6HL7_B == ir1 | |
LDsB_6HL7 == ir1 | LDs6HL7_C == ir1 | |
LDsC_6HL7 == ir1 | LDs6HL7_D == ir1 | |
LDsD_6HL7 == ir1 | LDs6HL7_E == ir1 | |
LDsE_6HL7 == ir1 | LDs6HL7_H == ir1 | |
LDsH_6HL7 == ir1 | LDs6HL7_L == ir1 | |
LDsL_6HL7 == ir1 | JPsHL == ir1 | |
ORs6HL7 == ir1 | DECs6HL7 == ir1 ; |
wire use_bc_exec = LDsA_6BC7 == ir1 | |
LDs6BC7_A == ir1 ; |
wire use_de_exec = LDs6DE7_A == ir1 | |
LDsA_6DE7 == ir1 ; |
|
wire use_sp_exec = MEM_OFSP == next_mem_state | |
MEM_OSSP == next_mem_state ; |
wire upd_sp_exec = DECsSP == ir2 | |
INCsSP == ir2 ; |
|
|
|
wire use_fr_exec = ( RETsC == ir1 | |
RETsM == ir1 | |
RETsNC == ir1 | |
937,10 → 965,14
|
assign hazard = (dec_state == DEC_EXEC & exec_ir2 ) & ( upd_fr & use_fr_exec | |
upd_ar & os_a | |
upd_br & os_b | |
upd_cr & os_c | |
upd_dr & os_d | |
upd_er & os_e | |
upd_br & os_b | |
upd_br & use_bc_exec | |
upd_cr & os_c | |
upd_cr & use_bc_exec | |
upd_dr & os_d | |
upd_dr & use_de_exec | |
upd_er & os_e | |
upd_er & use_de_exec | |
upd_hr & os_h | |
upd_lr & os_l | |
upd_hr & use_hl_exec | |
1009,7 → 1041,7
// |_____| |_____| |
// MEM_NOP |
// MEM_IFPP1 MEM_OFIXpD MEM_CALL MEM_IFRST MEM_OFHL_PM MEM_IOF_C |
// MEM_OS1, MEM_OSIXpD MEM_OSNN, MEM_IFREL_N MEM_OSHL_PM MEM_IOS_C |
// MEM_OS1, MEM_OSIXpD MEM_OSNN, MEM_REL2PC MEM_OSHL_PM MEM_IOS_C |
// MEM_OF1, MEM_OSADR MEM_OFNN MEM_JMPHL MEM_OSDE_PM MEM_IOF_N |
// MEM_OFSP MEM_OSSP_PCM2 MEM_OFADRP1 MEM_IFNN MEM_INTA MEM_IOS_N |
// MEM_OSSP MEM_OSSP_P MEM_OSADRP1 MEM_IFINT MEM_OS_HL_N |
1020,7 → 1052,7
next_mem_state == MEM_OSSP | |
next_mem_state == MEM_CALL ; |
wire src_pc = next_mem_state == MEM_IFPP1 | |
next_mem_state == MEM_IFREL_N ; |
next_mem_state == MEM_REL2PC ; |
|
wire src_nn = next_mem_state == MEM_IFNN | |
next_mem_state == MEM_OSNN | |
1090,15 → 1122,17
next_mem_state ==MEM_OFSP | |
next_mem_state ==MEM_IFPP1 | |
next_mem_state ==MEM_OSSP_PCM2 | |
next_mem_state ==MEM_IFNN | |
next_mem_state ==MEM_OSSP_P ; |
|
wire dec = next_mem_state ==MEM_OFHL_PM & ~block_mv_inc | |
next_mem_state ==MEM_OSHL_PM & ~block_mv_inc | |
next_mem_state ==MEM_OSDE_PM & ~block_mv_inc | |
next_mem_state == MEM_OFSP ; |
next_mem_state ==MEM_CALL | |
next_mem_state == MEM_OSSP ; |
|
|
wire reln = next_mem_state == MEM_IFREL_N | |
wire reln = next_mem_state == MEM_REL2PC | |
next_mem_state == MEM_OFIXpD | |
next_mem_state == MEM_OSIXpD ; |
|
1114,6 → 1148,9
|
wire pre_inc_dec = next_mem_state == MEM_CALL | |
next_mem_state == MEM_OSSP_P | |
next_mem_state == MEM_REL2PC | |
next_mem_state == MEM_OFIXpD | |
next_mem_state == MEM_OSIXpD | |
next_mem_state == MEM_OSSP ; |
|
|
1166,10 → 1203,10
I1_DDFD : next_state = {DEC_DDFD, MEM_IFPP1, IPIPE_EN1};// gets real inst |
I1_ED : next_state = {DEC_ED, MEM_IFPP1, IPIPE_EN1}; |
I1_JMP : next_state = {DEC_IF2, MEM_JMPHL, IPIPE_NOP}; |
I1_N : next_state = {DEC_N, MEM_IFPP1, IPIPE_ENN}; |
I1_N : next_state = {DEC_N, MEM_IFPP1, IPIPE_ENNEN2}; |
I1_NN : next_state = {DEC_NN, MEM_IFPP1, IPIPE_ENN}; |
I1_OF : next_state = {DEC_OF, MEM_OF1, IPIPE_EN12};//transfer, don't activate |
I1_OS : next_state = {DEC_IF2, MEM_OS1, IPIPE_EN1}; // -> ir2_NOP |
I1_OS : next_state = {DEC_IF2A, MEM_OS1, IPIPE_EN1}; // -> ir2_NOP |
I1_POP : next_state = {DEC_POP, MEM_OFSP, IPIPE_EN12}; |
I1_PUSH : next_state = {DEC_PUSH, MEM_OSSP, IPIPE_EN12}; |
I1_RET : next_state = {DEC_RET, MEM_OFSP, IPIPE_EN12}; |
1176,6 → 1213,8
I1_RMW : next_state = {DEC_RMW, MEM_OF1, IPIPE_EN12};//can't activate till data rdy |
I1_RST : next_state = {DEC_IF2, MEM_IFRST, IPIPE_ENN}; |
I1_R2R : next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2}; |
I1_JMPR : next_state = {DEC_N, MEM_NOP, IPIPE_ENN}; |
I1_HALT : next_state = {DEC_HALT, MEM_NOP , IPIPE_EN2}; |
default : next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2}; //I1_R2R |
endcase |
DEC_CB: if (cb_mem) next_state = {DEC_CBM, MEM_OF1, IPIPE_EN12}; |
1199,6 → 1238,8
I1_RMW : next_state = {DEC_RMW, MEM_OF1, IPIPE_EN12}; |
I1_RST : next_state = {DEC_IF2, MEM_IFRST, IPIPE_NOP}; // just dump next inst |
I1_R2R : next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2}; //I1_R2R |
I1_JMPR : next_state = {DEC_N, MEM_NOP, IPIPE_ENN}; |
I1_HALT : next_state = {DEC_HALT, MEM_NOP , IPIPE_EN2}; |
default : next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2}; //I1_R2R |
endcase |
DEC_ED: |
1251,10 → 1292,11
|
DEC_N: |
if (INsA_6N7== ir1) next_state = {DEC_NIN, MEM_IOF_N, IPIPE_EN12}; |
else if (OUTs6N7_A==ir1) next_state = {DEC_IF1, MEM_IOS_N, IPIPE_EN12}; |
else if (OUTs6N7_A==ir1) next_state = {DEC_IF2A, MEM_IOS_N, IPIPE_EN1}; |
else if (LDs6HL7_N==ir1) next_state = {DEC_IF1, MEM_OS_HL_N, IPIPE_EN12}; |
else if (jmpr_true) next_state = {DEC_IF2, MEM_IFREL_N, IPIPE_NOP}; |
else next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2};//r2r or false jumps |
else if (jmpr_true) next_state = {DEC_IF1, MEM_REL2PC, IPIPE_NOP}; |
else if (jmpr) next_state = {DEC_IF2, MEM_IFPP1, IPIPE_NOP}; |
else next_state = {DEC_EXEC, MEM_IFPP1, IPIPE_EN12A2};//r2r |
DEC_NIN: next_state = {DEC_IF2, MEM_IFPP1, IPIPE_ENNA2}; |
|
|
1302,7 → 1344,7
|
|
DEC_RET: next_state = { DEC_RET2, MEM_OFSP, IPIPE_ENN }; |
DEC_RET2: next_state = { DEC_NNCALL2, MEM_NOP, IPIPE_ENN }; |
DEC_RET2: next_state = { DEC_NNJMP, MEM_NOP, IPIPE_ENN }; |
// blow off a tick so we don't gronk adr |
DEC_RMW: next_state = {DEC_RMW2, MEM_NOP, IPIPE_ENNA2}; //activate |
DEC_RMW2: next_state = {DEC_IF1 , MEM_OSADR, IPIPE_NOP }; // from nn |
1353,7 → 1395,7
always @(posedge wb_clk_i or posedge rst_i) |
if (rst_i) ir1 <= NOP; |
else if (wb_rdy_nhz & next_pipe_state[3]) ir1 <= {2'b0, wb_dat_i} ; |
else if ( wb_rdy_nhz &update_prefix ) ir1 <= {ir1[7:0]==8'hed, ir1[7:0]==8'hcd, ir1[7:0]}; |
else if ( wb_rdy_nhz &update_prefix ) ir1 <= {ir1[7:0]==8'hed, ir1[7:0]==8'hcb, ir1[7:0]}; |
|
//----------- prefix states ----------------------------------------- |
// strings of prefix insts are ignored up to last one. Also dded and fded are ignored |
1360,10 → 1402,10
// but ddcd and fdcd are defined prefix sets. |
// |
always @(posedge wb_clk_i) |
if (wb_rdy_nhz & next_pipe_state[3]) {ir1dd, ir1fd } <= 2'b0; |
if (wb_rdy_nhz & next_dec_state == DEC_EXEC) {ir1dd, ir1fd } <= 2'b0; |
else if ( wb_rdy_nhz & update_prefix ) |
{ir1dd, ir1fd } <= {ir1dd | (ir1[7:0]==8'hdd ) & (ir1[7:0]!=8'hed) & (ir1[7:0]!=8'hfd), |
ir1fd | (ir1[7:0]==8'hfd ) & (ir1[7:0]!=8'hed) & (ir1[7:0]!=8'hdd) }; |
{ir1dd, ir1fd } <= { (ir1[7:0]==8'hdd ) | ir1dd & (ir1[7:0]!=8'hed) & (ir1[7:0]!=8'hfd), |
(ir1[7:0]==8'hfd ) | ir1fd & (ir1[7:0]!=8'hed) & (ir1[7:0]!=8'hdd) }; |
|
//------------------- inst reg #2 ----------------------------------- |
// This stuff is key to the data hazard logic. Hazards arise only AFTER activation of |
1413,8 → 1455,8
//-------------------------- memory interface stuff ---------------------------- |
|
|
// -- wb_adr_o |
always @(posedge wb_clk_i) if (wb_rdy) wb_adr_o <= mux21; |
// -- wb_adr_o 4/30/04 to wb_rdy_nhz -- hazard gronks this otherwise |
always @(posedge wb_clk_i) if (wb_rdy_nhz) wb_adr_o <= mux21; |
|
// -- wb_we_o; |
|
1427,15 → 1469,16
// -- wb_cyc_o |
// below is old logic -- appears not needed |
//wire no_wb_start = mem_idle | mem_halt | mem_op3 & blk_cmp_reg | mem_op1 & rmw_reg; |
wire no_mem_start = (next_mem_state == MEM_NOP) | (next_mem_state == MEM_REL2PC); |
always @(posedge wb_clk_i or posedge rst_i) |
if (rst_i) wb_cyc_o <= 1'b0; |
else if (wb_rdy_nhz) wb_cyc_o <= next_mem_state != MEM_NOP ; |
else if (wb_rdy_nhz) wb_cyc_o <= ~no_mem_start; |
|
// -- wb_stb_o; |
|
always @(posedge wb_clk_i or posedge rst_i) |
if (rst_i) wb_stb_o <= 1'b0; |
else if (wb_rdy_nhz) wb_stb_o <= next_mem_state != MEM_NOP ; |
else if (wb_rdy_nhz) wb_stb_o <= ~no_mem_start ; |
|
|
// -- wb_lock lets not worry about lock unless somebody thinks it matters. |
1479,18 → 1522,22
//issue: how is EXs6SP7_HL implemented -- it is known as a rmw - and only trick for this file is |
// that nn must be properly updates with ir2 |
|
|
// 4/30/04 changed else if (we_next) we had a hazard and this term |
// seemed to be gronking nn. see if it works now. Pretty tricky stuff. |
always @(posedge wb_clk_i or posedge rst_i) |
if (rst_i) flag_os1 <= 1'b0; |
if (rst_i) flag_os1 <= 1'b0; |
else if ((DEC_EXEC == next_dec_state) & wb_rdy) flag_os1 <= 1'b0; |
else if ( we_next ) flag_os1 <= 1'b1; |
else if ( we_next & wb_rdy_nhz ) flag_os1 <= 1'b1; |
|
|
wire [15:0] pc_2 = pc - 16'h2; |
always @(posedge wb_clk_i) |
if (wb_rdy_nhz) |
always @(posedge wb_clk_i or posedge rst_i) |
if (rst_i) nn <= 6'h00; |
else if (wb_rdy_nhz) |
begin |
if ( we_next & flag_os1) nn <= { nn[7:0], nn[15:8] } ; |
else if(we_next & ( next_mem_state == MEM_CALL)) nn <= {pc[7:0], pc[15:8]}; |
else if(we_next & ( next_mem_state == MEM_CALL)) nn <= {pc}; |
else if(we_next & ( next_mem_state == MEM_OSSP_PCM2)) nn <= {pc_2[7:0], pc_2[15:8]}; |
else if(EXs6SP7_HL== ir2 & ir2dd & exec_ir2) nn <= ixr; |
else if(EXs6SP7_HL== ir2 & ir2fd & exec_ir2) nn <= iyr; |
1499,16 → 1546,17
else if(we_next & ( next_mem_state == MEM_OS1 | |
next_mem_state == MEM_OSIXpD | |
next_mem_state == MEM_OSSP | |
next_mem_state == MEM_IOS_N | |
next_mem_state == MEM_OSNN ) ) |
begin |
if (os_a) nn[15:8] <= ar; |
if (os_b) nn[15:8] <= br; |
if (os_c) nn <= {cr, br }; // use for PUSHsBC |
if (os_c) nn <= {br, cr }; // use for PUSHsBC |
if (os_d) nn[15:8] <= dr; |
if (os_e) nn <= {er, dr }; // use for PUSHsDE |
if (os_e) nn <= {dr, er }; // use for PUSHsDE |
if (os_h) nn[15:8] <= hr; |
if (os_l) nn <= {lr, hr }; // use for PUSHsHL |
if (os_f) nn <= {fr, ar }; // use for PUSHsAF |
if (os_l) nn <= {hr, lr }; // use for PUSHsHL |
if (os_f) nn <= {ar, fr }; // use for PUSHsAF |
end |
// 4/19/2004 previously no if here - if not needed we don't need next_pipe_state[1] eithor |
else if (next_pipe_state[1]) nn <= { wb_dat_i, nn[15:8] }; |
1526,7 → 1574,8
if (next_mem_state == MEM_CALL ) pc <= nn; //Use MEM_CALL to exchange pc<=>nn |
if (next_mem_state == MEM_IFRST) pc <= src_mux; |
if (next_mem_state == MEM_JMPHL) pc <= src_mux; |
if (next_mem_state == MEM_IFNN ) pc <= src_mux; |
if (next_mem_state == MEM_IFNN ) pc <= adr_alu; //on jumps get adr+1 in pc immediately. |
if (next_mem_state == MEM_REL2PC) pc <= adr_alu; |
if (next_mem_state == MEM_IFINT) pc <= src_mux; |
end |
|
1551,6 → 1600,7
// ED_LDsREG_6NN7 REG== SP // do from ir2 - no hazard as executed on IF2 - refill pipe |
|
always @(posedge wb_clk_i ) |
begin |
if (exec_ir2 ) // this has priority of course |
begin |
if (LDsSP_NN == ir2) sp <= nn; |
1558,7 → 1608,7
if ( DECsSP == ir2 ) sp <= add16; |
if ( INCsSP == ir2 ) sp <= add16; |
end |
else if (wb_rdy_nhz) |
if (wb_rdy_nhz) //the no hazard term should kill these if any abvove is happening in parallel |
begin |
if ( DECsSP == ir1 & dec_state == DEC_EXEC) sp <= adr_alu; |
if ( INCsSP == ir1 & dec_state == DEC_EXEC) sp <= adr_alu; |
1567,7 → 1617,9
if (next_mem_state == MEM_OSSP ) sp <= adr_alu; |
if (next_mem_state == MEM_OSSP_PCM2 ) sp <= adr_alu; |
if (next_mem_state == MEM_OSSP_P ) sp <= adr_alu; |
if (next_mem_state == MEM_CALL ) sp <= adr_alu; |
end |
end |
//----------------- inst hazard logic ------------------------------------------ |
|
|