Tang Nano 9K で Apple II を再現する(1)クロック生成
FPGA での Apple II の実装はいくつかありますが、自分でもやってみます。
Apple II の回路を、SystemVerilog で愚直に書き下すことにします。
参考文献として、The Apple II Circuit Description を使います。
第三章 Clock Generator and Horizontal Timing
14.31818 MHz のマスタークロックから、以下のクロックを生成します。
COLOR REF (3.58MHz)
7M (7.2MHz)
14M (14.3MHz)
/RAS (2MHz)
AX (2MHz)
/CAS (2MHz)
Q3 (2MHz)
φ0 (1MHz)
φ1 (1MHz)
LD194 (1MHz)
/LDPS (1MHz)
回路図 C-2 を clocks.sv として実装します。
`default_nettype none
module a2_clocks (
input wire mclk,
input wire hpe_n,
output wire color_ref,
output wire color_ref_n,
output wire clk_7m,
output wire clk_7m_n,
output wire clk_14m,
output wire ras_n,
output wire ax,
output wire cas_n,
output wire q3,
output wire ph0,
output wire ph1,
output reg ld194,
output reg ldps_n
);
// B1:74S175
logic b1_d0;
logic b1_q0;
logic b1_q0n;
logic b1_d1;
logic b1_q1;
logic b1_q1n;
logic b1_d2;
logic b1_q2;
logic b1_d3;
logic b1_q3;
logic b1_q3n;
always_ff@(posedge mclk) begin
b1_q0 <= b1_d0;
b1_q0n <= ~b1_d0;
b1_q1 <= b1_d1;
b1_q1n <= !b1_d1;
b1_q2 <= b1_d2;
b1_q3 <= b1_d3;
b1_q3n <= ~b1_d3;
end
assign b1_d0 = b1_q0n;
assign b1_d1 = b1_q0 ^ b1_q1; // B2:74S86
assign b1_d2 = c1_zb;
assign b1_d3 = b1_q2;
// C2:74S195
logic c2_p0;
logic c2_p1;
logic c2_p2;
logic c2_p3;
logic c2_q0;
logic c2_q1;
logic c2_q2;
logic c2_q3;
logic c2_q3n;
logic c2_pen;
always_ff@(posedge mclk) begin
if (!c2_pen) begin
c2_q0 <= c2_p0;
c2_q1 <= c2_p1;
c2_q2 <= c2_p2;
c2_q3 <= c2_p3;
c2_q3n <= ~c2_p3;
end else begin
c2_q0 <= 0;
c2_q1 <= c2_q0;
c2_q2 <= c2_q1;
c2_q3 <= c2_q2;
c2_q3n <= ~c2_q2;
end
end
logic b13_10;
logic b2_6;
assign c2_p0 = c2_q1;
assign b13_10 = ~(c2_q1 | c2_q2); // B13:74LS02
assign b2_6 = (hpe_n ^ 1'b1); // B2:74S86
assign c2_p1 = ~(b13_10 & b1_q3 & b1_q1 & b2_6); // D2:74LS20
assign c2_p2 = c2_q1;
assign c2_p3 = c2_q0;
assign c2_pen = c2_q3;
// C1:74LS153
logic c1_s0;
logic c1_s1;
logic c1_0b;
logic c1_1b;
logic c1_2b;
logic c1_3b;
logic c1_zb;
always_comb begin
if (!c1_s1) begin
if (!c1_s0) begin
c1_zb = c1_0b;
end else begin
c1_zb = c1_1b;
end
end else begin
if (!c1_s0) begin
c1_zb = c1_2b;
end else begin
c1_zb = c1_3b;
end
end
end
assign c1_s0 = c2_q1;
assign c1_s1 = b1_q3;
assign c1_0b = b1_q2;
assign c1_1b = c2_q3n;
assign c1_2b = b1_q2;
assign c1_3b = c2_q3;
// Apple II Clocks
assign color_ref = b1_q1n;
assign color_ref_n = b1_q1;
assign clk_7m = b1_q0;
assign clk_7m_n = b1_q0n;
assign clk_14m = mclk;
assign ras_n = c2_q0;
assign ax = c2_q1;
assign cas_n = c2_q2;
assign q3 = c2_q3;
assign ph0 = b1_q3;
assign ph1 = b1_q3n;
assign ld194 = b1_q0n & b1_q3 & b13_10; // B12:74LS11
assign ldps_n = ~(b13_10 & b1_q3); // A1:74LS00
endmodule
`default_nettype wire
クロックの生成ができました。
この記事が気に入ったらサポートをしてみませんか?