Skip to content

Commit

Permalink
Merge pull request #1 from FREEWING-JP/denghongcai_master
Browse files Browse the repository at this point in the history
Denghongcai master
  • Loading branch information
FREEWING-JP authored Jun 28, 2022
2 parents 26085d6 + 329196f commit d0669fe
Show file tree
Hide file tree
Showing 21 changed files with 469 additions and 241 deletions.
98 changes: 51 additions & 47 deletions hw/ise/nes.xise

Large diffs are not rendered by default.

43 changes: 23 additions & 20 deletions hw/src/cpu/jp.v
Original file line number Diff line number Diff line change
Expand Up @@ -32,36 +32,35 @@ module jp
input wire wr, // write enable signal
input wire [15:0] addr, // 16-bit memory address
input wire din, // data input bus
input wire jp_data1, // joypad 1 input signal
input wire jp_data2, // joypad 2 input signal
output wire jp_clk, // joypad output clk signal
output wire jp_latch, // joypad output latch signal
input wire [ 7:0] joypad_cfg_in, // joypad input signal
input wire joypad_cfg_upd_in, // joypad cfg input signal
output reg [ 7:0] dout // data output bus
);
reg [ 7:0] joypad_cfg_latch;

wire jp_latch;

//
// FFs for tracking/reading current controller state.
//
reg [7:0] q_jp1_state, d_jp1_state;
reg [7:0] q_jp2_state, d_jp2_state;
reg q_jp_clk, d_jp_clk;
reg q_jp_latch, d_jp_latch;
reg [8:0] q_cnt, d_cnt;


always @(posedge clk)
begin
if (rst)
begin
q_jp1_state <= 8'h00;
q_jp2_state <= 8'h00;
q_jp2_state <= 8'h00;
q_jp_clk <= 1'b0;
q_jp_latch <= 1'b0;
q_cnt <= 9'h00;
end
else
begin
q_jp1_state <= d_jp1_state;
q_jp2_state <= d_jp2_state;
q_jp2_state <= d_jp2_state;
q_jp_clk <= d_jp_clk;
q_jp_latch <= d_jp_latch;
q_cnt <= d_cnt;
Expand All @@ -74,7 +73,7 @@ always @*
begin
// Default most FFs to current state.
d_jp1_state = q_jp1_state;
d_jp2_state = q_jp2_state;
d_jp2_state = q_jp2_state;
d_jp_clk = q_jp_clk;
d_jp_latch = q_jp_latch;

Expand All @@ -84,8 +83,8 @@ always @*
// clock 7 more times to read other 7 buttons. Controller states are active low.
if (q_cnt[5:1] == 5'h00)
begin
d_jp1_state[state_idx] = ~jp_data1;
d_jp2_state[state_idx] = ~jp_data2;
d_jp1_state[state_idx] = ~joypad_cfg_latch[state_idx];
d_jp2_state[state_idx] = 1;

if (q_cnt[8:1] == 8'h00)
d_jp_latch = 1'b1;
Expand All @@ -101,10 +100,8 @@ always @*

assign state_idx = q_cnt[8:6] - 3'h1;
assign jp_latch = q_jp_latch;
assign jp_clk = q_jp_clk;

localparam [15:0] JOYPAD1_MMR_ADDR = 16'h4016;
localparam [15:0] JOYPAD2_MMR_ADDR = 16'h4017;

localparam S_STROBE_WROTE_0 = 1'b0,
S_STROBE_WROTE_1 = 1'b1;
Expand All @@ -123,14 +120,12 @@ always @(posedge clk)
begin
q_addr <= 16'h0000;
q_jp1_read_state <= 9'h000;
q_jp2_read_state <= 9'h000;
q_strobe_state <= S_STROBE_WROTE_0;
end
else
begin
q_addr <= addr;
q_jp1_read_state <= d_jp1_read_state;
q_jp2_read_state <= d_jp2_read_state;
q_strobe_state <= d_strobe_state;
end
end
Expand All @@ -141,7 +136,7 @@ always @*

// Default FFs to current state.
d_jp1_read_state = q_jp1_read_state;
d_jp2_read_state = q_jp2_read_state;
d_jp2_read_state = q_jp2_read_state;
d_strobe_state = q_strobe_state;

if (addr[15:1] == JOYPAD1_MMR_ADDR[15:1])
Expand All @@ -163,19 +158,27 @@ always @*
begin
d_strobe_state = S_STROBE_WROTE_0;
d_jp1_read_state = { q_jp1_state, 1'b0 };
d_jp2_read_state = { q_jp2_state, 1'b0 };
d_jp2_read_state = { q_jp2_state, 1'b1 };
end
end

// Shift appropriate jp read state on every read. After 8 reads, all subsequent reads
// should be 1.
else if (!wr && !addr[0])
d_jp1_read_state = { 1'b1, q_jp1_read_state[8:1] };
else if (!wr && addr[0])
else if (!wr && addr[0])
d_jp2_read_state = { 1'b1, q_jp2_read_state[8:1] };
end
end
end

endmodule

always @(posedge joypad_cfg_upd_in)
begin
if( !jp_latch )
begin
joypad_cfg_latch = joypad_cfg_in;
end
end

endmodule
14 changes: 8 additions & 6 deletions hw/src/cpu/rp2a03.v
Original file line number Diff line number Diff line change
Expand Up @@ -40,13 +40,17 @@ module rp2a03
output wire [15:0] a_out, // address bus
output wire r_nw_out, // read/write select (write low)
output wire brk_out, // debug break signal


/*
// Joypad signals.
input wire jp_data1_in, // joypad 1 input signal
input wire jp_data2_in, // joypad 2 input signal
output wire jp_clk, // joypad output clk signal
output wire jp_latch, // joypad output latch signal

*/
// Joypad signals.
input wire [ 7:0] joypad_cfg_in,
input wire joypad_cfg_upd_in,
// Audio signals.
input wire [ 3:0] mute_in, // disable autio channels
output wire audio_out, // pwm audio output
Expand Down Expand Up @@ -113,10 +117,8 @@ jp jp_blk(
.wr(~cpu_r_nw),
.addr(cpu_a),
.din(cpu_dout[0]),
.jp_data1(jp_data1_in),
.jp_data2(jp_data2_in),
.jp_clk(jp_clk),
.jp_latch(jp_latch),
.joypad_cfg_in(joypad_cfg_in),
.joypad_cfg_upd_in(joypad_cfg_upd_in),
.dout(jp_dout)
);

Expand Down
44 changes: 38 additions & 6 deletions hw/src/hci/hci.v
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,9 @@ module hci
output wire [15:0] ppu_vram_a, // ppu memory address
output wire [ 7:0] ppu_vram_dout, // ppu data bus [output]
output wire [39:0] cart_cfg, // cartridge config data (from iNES header)
output wire cart_cfg_upd // pulse on cart_cfg update so cart can reset
output wire cart_cfg_upd, // pulse on cart_cfg update so cart can reset
output wire [ 7:0] joypad_cfg,
output wire joypad_cfg_upd
);

// Debug packet opcodes.
Expand All @@ -63,7 +65,8 @@ localparam [7:0] OP_ECHO = 8'h00,
OP_PPU_MEM_RD = 8'h09,
OP_PPU_MEM_WR = 8'h0A,
OP_PPU_DISABLE = 8'h0B,
OP_CART_SET_CFG = 8'h0C;
OP_CART_SET_CFG = 8'h0C,
OP_JOYPAD_SET_CFG = 8'h0D;

// Error code bit positions.
localparam DBG_UART_PARITY_ERR = 0,
Expand All @@ -88,7 +91,8 @@ localparam [4:0] S_DISABLED = 5'h00,
S_PPU_MEM_WR_STG_1 = 5'h0F,
S_PPU_DISABLE = 5'h10,
S_CART_SET_CFG_STG_0 = 5'h11,
S_CART_SET_CFG_STG_1 = 5'h12;
S_CART_SET_CFG_STG_1 = 5'h12,
S_JOYPAD_CFG_STG_0 = 5'h13;

reg [ 4:0] q_state, d_state;
reg [ 2:0] q_decode_cnt, d_decode_cnt;
Expand All @@ -97,6 +101,8 @@ reg [15:0] q_addr, d_addr;
reg [ 1:0] q_err_code, d_err_code;
reg [39:0] q_cart_cfg, d_cart_cfg;
reg q_cart_cfg_upd, d_cart_cfg_upd;
reg [ 7:0] q_joypad_cfg, d_joypad_cfg;
reg q_joypad_cfg_upd, d_joypad_cfg_upd;

// UART output buffer FFs.
reg [7:0] q_tx_data, d_tx_data;
Expand All @@ -121,6 +127,8 @@ always @(posedge clk)
q_err_code <= 0;
q_cart_cfg <= 40'h0000000000;
q_cart_cfg_upd <= 1'b0;
q_joypad_cfg <= 8'h00;
q_joypad_cfg_upd <= 1'b0;
q_tx_data <= 8'h00;
q_wr_en <= 1'b0;
end
Expand All @@ -133,14 +141,16 @@ always @(posedge clk)
q_err_code <= d_err_code;
q_cart_cfg <= d_cart_cfg;
q_cart_cfg_upd <= d_cart_cfg_upd;
q_joypad_cfg <= d_joypad_cfg;
q_joypad_cfg_upd <= d_joypad_cfg_upd;
q_tx_data <= d_tx_data;
q_wr_en <= d_wr_en;
end
end

// Instantiate the serial controller block.
uart #(.SYS_CLK_FREQ(100000000),
.BAUD_RATE(38400),
.BAUD_RATE(256000),
.DATA_BITS(8),
.STOP_BITS(1),
.PARITY_MODE(1)) uart_blk
Expand Down Expand Up @@ -168,6 +178,8 @@ always @*
d_err_code = q_err_code;
d_cart_cfg = q_cart_cfg;
d_cart_cfg_upd = 1'b0;
d_joypad_cfg = q_joypad_cfg;
d_joypad_cfg_upd = 1'b0;

rd_en = 1'b0;
d_tx_data = 8'h00;
Expand Down Expand Up @@ -205,6 +217,10 @@ always @*
d_tx_data = 8'h00; // Write "0" over UART to indicate we are not in a debug break
d_wr_en = 1'b1;
end
else if (rd_data == OP_JOYPAD_SET_CFG)
begin
d_state = S_JOYPAD_CFG_STG_0;
end
end
end
S_DECODE:
Expand All @@ -227,6 +243,7 @@ always @*
OP_PPU_MEM_WR: d_state = S_PPU_MEM_WR_STG_0;
OP_PPU_DISABLE: d_state = S_PPU_DISABLE;
OP_CART_SET_CFG: d_state = S_CART_SET_CFG_STG_0;
OP_JOYPAD_SET_CFG: d_state = S_JOYPAD_CFG_STG_0;
OP_DBG_RUN:
begin
d_state = S_DISABLED;
Expand Down Expand Up @@ -642,16 +659,31 @@ always @*
d_cart_cfg_upd = 1'b1;
end
end
end
end
// --- JOYPAD_READ_FLAG ---
S_JOYPAD_CFG_STG_0:
begin
if (!rx_empty)
begin
rd_en = 1'b1; // pop packet byte off uart fifo
d_joypad_cfg = rd_data;

// After last byte of packet, return to decode stage.
d_state = S_DISABLED;
d_joypad_cfg_upd = 1'b1;
end
end
endcase
end

assign cpu_a = q_addr;
assign active = (q_state != S_DISABLED);
assign active = (q_state != S_DISABLED && q_state != S_JOYPAD_CFG_STG_0);
assign ppu_vram_a = q_addr;
assign ppu_vram_dout = rd_data;
assign cart_cfg = q_cart_cfg;
assign cart_cfg_upd = q_cart_cfg_upd;
assign joypad_cfg = q_joypad_cfg;
assign joypad_cfg_upd = q_joypad_cfg_upd;

endmodule

62 changes: 38 additions & 24 deletions hw/src/nes.ucf
Original file line number Diff line number Diff line change
@@ -1,41 +1,55 @@
# ==== Clock inputs (CLK) ====
NET "CLK_100MHZ" LOC=V10 | IOSTANDARD=LVCMOS33;
NET "CLK_100MHZ" LOC=E3 | IOSTANDARD=LVCMOS33;

NET "CLK_100MHZ" TNM_NET = sys_clk_pin;
TIMESPEC TS_sys_clk_pin = PERIOD sys_clk_pin 100000 kHz;

# ==== Pushbuttons (BTN) ====
NET "BTN_SOUTH" LOC = C9 | IOSTANDARD = LVCMOS33;
NET "BTN_EAST" LOC = D9 | IOSTANDARD = LVCMOS33;
NET "BTN_SOUTH" LOC = T16 | IOSTANDARD = LVCMOS33;
NET "BTN_EAST" LOC = R10 | IOSTANDARD = LVCMOS33;

# ==== Slide Switch (SW0) ====
NET "SW<0>" LOC = T10 | IOSTANDARD = LVCMOS33;
NET "SW<1>" LOC = T9 | IOSTANDARD = LVCMOS33;
NET "SW<2>" LOC = V9 | IOSTANDARD = LVCMOS33;
NET "SW<3>" LOC = M8 | IOSTANDARD = LVCMOS33;
NET "SW<0>" LOC = U9 | IOSTANDARD = LVCMOS33;
NET "SW<1>" LOC = U8 | IOSTANDARD = LVCMOS33;
NET "SW<2>" LOC = R7 | IOSTANDARD = LVCMOS33;
NET "SW<3>" LOC = R6 | IOSTANDARD = LVCMOS33;

# ==== RS-232 Serial Ports (RS232) ====
NET "RXD" LOC = N17 | IOSTANDARD=LVCMOS33;
NET "TXD" LOC = N18 | IOSTANDARD=LVCMOS33;
NET "RXD" LOC = C4 | IOSTANDARD=LVCMOS33;
NET "TXD" LOC = D4 | IOSTANDARD=LVCMOS33;

# ==== Joypads ====
NET "NES_JOYPAD_CLK" LOC = E12 | IOSTANDARD = LVCMOS33;
NET "NES_JOYPAD_LATCH" LOC = F12 | IOSTANDARD = LVCMOS33;
NET "NES_JOYPAD_DATA1" LOC = C12 | IOSTANDARD = LVCMOS33;
NET "NES_JOYPAD_DATA2" LOC = D12 | IOSTANDARD = LVCMOS33;
#NET "NES_JOYPAD_CLK" LOC = B13 | IOSTANDARD = LVCMOS33;#JA1
#NET "NES_JOYPAD_LATCH" LOC = F14 | IOSTANDARD = LVCMOS33;
#NET "NES_JOYPAD_DATA1" LOC = D17 | IOSTANDARD = LVCMOS33;
#NET "NES_JOYPAD_DATA2" LOC = E17 | IOSTANDARD = LVCMOS33;
NET "led<0>" LOC = "T8" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L24N_T3_34, Sch name = LED0
NET "led<1>" LOC = "V9" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L21N_T3_DQS_34, Sch name = LED1
NET "led<2>" LOC = "R8" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L24P_T3_34, Sch name = LED2
NET "led<3>" LOC = "T6" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L23N_T3_34, Sch name = LED3
NET "led<4>" LOC = "T5" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L12P_T1_MRCC_34, Sch name = LED4
NET "led<5>" LOC = "T4" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L12N_T1_MRCC_34, Sch name = LED5
NET "led<6>" LOC = "U7" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L22P_T3_34, Sch name = LED6
NET "led<7>" LOC = "U6" | IOSTANDARD = "LVCMOS33"; #Bank = 34, Pin name = IO_L22N_T3_34, Sch name = LED7


# ==== VGA Port (VGA) ====
NET "VGA_HSYNC" LOC = N6 | IOSTANDARD = LVCMOS33;
NET "VGA_VSYNC" LOC = P7 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<0>" LOC = U7 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<1>" LOC = V7 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<2>" LOC = N7 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<0>" LOC = P8 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<1>" LOC = T6 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<2>" LOC = V6 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<0>" LOC = R7 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<1>" LOC = T7 | IOSTANDARD = LVCMOS33;
NET "VGA_HSYNC" LOC = B11 | IOSTANDARD = LVCMOS33;
NET "VGA_VSYNC" LOC = B12 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<0>" LOC = A3 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<1>" LOC = B4 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<2>" LOC = C5 | IOSTANDARD = LVCMOS33;
NET "VGA_RED<3>" LOC = A4 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<0>" LOC = C6 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<1>" LOC = A5 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<2>" LOC = B6 | IOSTANDARD = LVCMOS33;
NET "VGA_GREEN<3>" LOC = A6 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<0>" LOC = B7 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<1>" LOC = C7 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<2>" LOC = D7 | IOSTANDARD = LVCMOS33;
NET "VGA_BLUE<3>" LOC = D8 | IOSTANDARD = LVCMOS33;

# ==== Audio ====
NET "AUDIO" LOC = "K2" | IOSTANDARD = LVTTL | SLEW = SLOW | DRIVE = 6;
NET "AUDIO" LOC = A11 | IOSTANDARD = LVCMOS33 | SLEW = SLOW | DRIVE = 6;#MONO AUDIO OUT
NET "AUDIO_SD" LOC = D12 | IOSTANDARD = LVCMOS33;

Loading

0 comments on commit d0669fe

Please sign in to comment.