IOBS and ROM overlay fixes

This commit is contained in:
Zane Kaminski 2023-03-30 11:50:05 -04:00
parent b150047221
commit 50451da0a5
3 changed files with 65 additions and 37 deletions

View File

@ -40,7 +40,7 @@ module CS(
/* Select signals - IOB domain */ /* Select signals - IOB domain */
assign IACS = (A[23:08]==16'hFFFF); // IACK assign IACS = (A[23:08]==16'hFFFF); // IACK
assign IOCS = assign IOCS = ((A[23:20]==4'h4) && Overlay ) || // ROM once
(A[23:20]==4'h5) || // SCSI (A[23:20]==4'h5) || // SCSI
(A[23:20]==4'h6) || // empty (A[23:20]==4'h6) || // empty
(A[23:20]==4'h7) || // empty (A[23:20]==4'h7) || // empty
@ -53,7 +53,6 @@ module CS(
(A[23:20]==4'hE) || // VIA (A[23:20]==4'hE) || // VIA
(A[23:20]==4'hF) || // IACK (A[23:20]==4'hF) || // IACK
VidRAMCSWR; VidRAMCSWR;
//assign IOCS = 0;
assign IOPWCS = RAMCS && !nWE; assign IOPWCS = RAMCS && !nWE;
endmodule endmodule

View File

@ -3,8 +3,10 @@ module IOBS(
input CLK, input nWE, input nAS, input nLDS, input nUDS, input CLK, input nWE, input nAS, input nLDS, input nUDS,
/* AS cycle detection */ /* AS cycle detection */
input BACT, input BACT,
/* Select and ready signals */ /* Select signals */
input IOCS, input IOPWCS, output IOBS_Ready, output reg nBERR_FSB, input IOCS, input IOPWCS, input ROMCS,
/* FSB cycle termination outputs */
output IOBS_Ready, output reg nBERR_FSB,
/* Read data OE control */ /* Read data OE control */
output nDinOE, output nDinOE,
/* IOB Master Controller Interface */ /* IOB Master Controller Interface */
@ -19,10 +21,22 @@ module IOBS(
always @(posedge CLK) begin IOACTr <= IOACT; end always @(posedge CLK) begin IOACTr <= IOACT; end
/* Read data OE control */ /* Read data OE control */
assign nDinOE = !(!nAS && IOCS && nWE); assign nDinOE = !(!nAS && IOCS && nWE && !ROMCS);
/* Posted read/write state */ wire IOStart = BACT && IOCS && ~Once;
reg [1:0] PS = 0;
/* I/O transfer state
* TS0 - I/O bridge idle:
* asserts IOREQ
* transitions to TS3 when IOStart true
* TS3 - starting I/O transfer:
latches LDS and UDS from FSB or FIFO secondary level
transitions immediately to TS2
* TS2 - waiting for IOBM to begin:
transitions to TS1 when IOACT true
* TS1 - waiting for IOBM to finish:
* transitions to TS1 when IOACT false */
reg [1:0] TS = 0;
reg Once = 0; reg Once = 0;
/* FIFO second level control */ /* FIFO second level control */
@ -32,46 +46,54 @@ module IOBS(
reg IOL1; reg IOL1;
reg IOU1; reg IOU1;
always @(posedge CLK) begin always @(posedge CLK) begin
if (PS!=0 && BACT && IOCS && ~Once && ~ALE1) begin // If write currently posting (TS!=0),
// I/O selected, and FIFO secondary level empty
if (TS!=0 && IOStart && ~ALE1) begin
// Latch R/W now but latch address and LDS/UDS next cycle
IORW1 <= nWE; IORW1 <= nWE;
Load1 <= 1; Load1 <= 1;
end else Load1 <= 0; end else Load1 <= 0;
end end
always @(posedge CLK) begin always @(posedge CLK) begin
if (PS==3 && ALE1) Clear1 <= 1; // Make address latch transparent in cycle after TS3
// (i.e. first TS2 cycle that's not part of current write)
if (TS==3) Clear1 <= 1;
else Clear1 <= 0; else Clear1 <= 0;
end end
always @(posedge CLK) begin
if (Load1) ALE1 <= 1;
else if (Clear1) ALE1 <= 0;
end
always @(posedge CLK) begin always @(posedge CLK) begin
if (Load1) begin if (Load1) begin
// Latch address, LDS, UDS when Load1 true
ALE0 <= 1;
IOL1 <= ~nLDS; IOL1 <= ~nLDS;
IOU1 <= ~nUDS; IOU1 <= ~nUDS;
end end else if (Clear1) ALE1 <= 0;
end end
/* FIFO Primary Level Control */ /* FIFO Primary Level Control */
always @(posedge CLK) begin always @(posedge CLK) begin
if (PS==0) begin if (TS==0) begin
if (ALE1) begin if (ALE1) begin // If FIFO secondary level occupied
PS <= 3; // Request transfer from IOBM and latch R/W from FIFO
TS <= 3;
IOREQ <= 1; IOREQ <= 1;
IORW0 <= IORW1; IORW0 <= IORW1;
end else if (BACT && IOCS && ~Once) begin end else if (IOStart) begin // If I/O selected and FIFO empty
PS <= 3; // Request transfer from IOBM and latch R/W from FSB
TS <= 3;
IOREQ <= 1; IOREQ <= 1;
IORW0 <= nWE; IORW0 <= nWE;
end else begin end else begin // Otherwise stay in idle
PS <= 0; TS <= 0;
IOREQ <= 0; IOREQ <= 0;
end end
ALE0 <= 0; ALE0 <= 0;
end else if (PS==3) begin end else if (TS==3) begin
PS <= 2; // Always go to TS2. Keep IOREQ active
TS <= 2;
IOREQ <= 1; IOREQ <= 1;
// Latch address (and data)
ALE0 <= 1; ALE0 <= 1;
// Latch data strobes from FIFO or FSB as appropriate
if (ALE1) begin if (ALE1) begin
IOL0 <= IOL1; IOL0 <= IOL1;
IOU0 <= IOU1; IOU0 <= IOU1;
@ -79,39 +101,44 @@ module IOBS(
IOL0 <= ~nLDS; IOL0 <= ~nLDS;
IOU0 <= ~nUDS; IOU0 <= ~nUDS;
end end
end else if (PS==2) begin end else if (TS==2) begin
// Wait for IOACT then withdraw IOREQ and enter TS1
if (IOACTr) begin if (IOACTr) begin
PS <= 1; TS <= 1;
IOREQ <= 0; IOREQ <= 0;
end else begin end else begin
PS <= 2; TS <= 2;
IOREQ <= 1; IOREQ <= 1;
end end
ALE0 <= 0; ALE0 <= 1;
end else if (PS==1) begin end else if (TS==1) begin
if (~IOACTr) PS <= 0; // Wait for IOACT low (transfer over) before going back to idle
else PS <= 2; if (~IOACTr) TS <= 0;
else TS <= 2;
IOREQ <= 0; IOREQ <= 0;
// Address latch released since it's controlled by IOBM now
ALE0 <= 0; ALE0 <= 0;
end end
end end
/* Once, ready, BERR control */ /* Once, ready, BERR control */
reg IOReady;
wire IOPWReady = ~ALE1;
always @(posedge CLK) begin always @(posedge CLK) begin
if (~BACT) Once <= 0; if (~BACT) Once <= 0;
else if (IOCS && (PS==0 || (IOPWCS && IOPWReady))) Once <= 1; else if (IOCS && !ALE1 && (TS==0 || IOPWCS)) Once <= 1;
end end
always @(posedge CLK) begin always @(posedge CLK) begin
if (~BACT) begin if (~BACT) begin
// Deassert IOReady and /BERR when bus inactive
IOReady <= 0; IOReady <= 0;
nBERR_FSB <= 1; nBERR_FSB <= 1;
end else if (Once && (PS==0 || PS==1) && ~IOACTr && IOPWReady) begin end else if (Once && !ALE1 && (TS==0 || (TS==1 && !IOACTr))) begin
// If transaction submitted, FIFO second level empty,
// and in or entering TS0, all transactions including
// current are complete. So terminate cycle.
IOReady <= !IOBERR; IOReady <= !IOBERR;
nBERR_FSB <= !IOBERR; nBERR_FSB <= !IOBERR;
end end
end end
assign IOBS_Ready = ~IOCS || IOReady || (IOPWCS && IOPWReady); assign IOBS_Ready = !IOCS || IOReady || (IOPWCS && !ALE1);
endmodule endmodule

View File

@ -91,8 +91,10 @@ module WarpSE(
FCLK, nWE_FSB, nAS_FSB, nLDS_FSB, nUDS_FSB, FCLK, nWE_FSB, nAS_FSB, nLDS_FSB, nUDS_FSB,
/* AS cycle detection, FSB BERR */ /* AS cycle detection, FSB BERR */
BACT, BACT,
/* Select and ready signals */ /* Select signals */
IOCS, IOPWCS, IOBS_Ready, nBERR_FSB, IOCS, IOPWCS, ROMCS,
/* FSB cycle termination outputs */
IOBS_Ready, nBERR_FSB,
/* Read data OE control */ /* Read data OE control */
nDinOE, nDinOE,
/* IOB Master Controller Interface */ /* IOB Master Controller Interface */