123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440 |
- module vjtag_max80
- #(
- parameter sram_bits,
- parameter [31:0] sdram_base_addr,
- parameter sdram_bits,
- parameter [31:0] VJTAG_WRITE_PREFIX = 32'hABC80FED
- ) (
- input rst_n,
- input sys_clk,
- output reset_cmd,
- input cpu_valid,
- input [6:2] cpu_addr,
- input [31:0] cpu_wdata,
- input [ 3:0] cpu_wstrb,
- output [31:0] cpu_rdata,
- output cpu_irq,
- output cpu_halt,
- dram_bus.dstr sdram,
-
- output [sram_bits-1:2] sram_addr,
- input [31:0] sram_rdata,
- output [31:0] sram_wdata,
- output sram_read,
- output sram_write
- );
- wire v_tdi;
- reg v_tdo;
- wire [4:0] v_ir;
- wire v_tck;
- wire v_st_cdr;
- wire v_st_sdr;
- wire v_st_e1dr;
- wire v_st_pdr;
- wire v_st_e2dr;
- wire v_st_udr;
- wire v_st_cir;
- wire v_st_uir;
- vjtag vjtag (
- .tdi ( v_tdi ),
- .tdo ( v_tdo ),
- .tck ( v_tck ),
- .ir_in ( v_ir ),
- .ir_out ( ),
- .virtual_state_cdr ( v_st_cdr ),
- .virtual_state_e1dr ( v_st_e1dr ),
- .virtual_state_e2dr ( v_st_e2dr ),
- .virtual_state_pdr ( v_st_pdr ),
- .virtual_state_sdr ( v_st_sdr ),
- .virtual_state_udr ( v_st_udr ),
- .virtual_state_uir ( v_st_uir ),
- .virtual_state_cir ( v_st_cir )
- );
- localparam cmd_bypass = 4'b0000;
- localparam cmd_irq = 4'b0001;
- localparam cmd_reset = 4'b0010;
- localparam cmd_halt = 4'b0011;
- localparam cmd_memerr = 4'b0100;
- localparam cmd_mem0 = 4'b1000;
- localparam cmd_memaddr = 4'b1001;
- localparam cmd_memread = 4'b1010;
- localparam cmd_memwrite = 4'b1011;
- localparam cmd_memwr = 3'b101;
- localparam cmd_cpucmd = 4'b1100;
- localparam cmd_cpucmd_irq = 4'b1101;
- localparam cmd_cpuinfo = 4'b1110;
- localparam cmd_cpustatus = 4'b1111;
- reg jtag_bypass;
- wire jtag_out;
- reg tdi_s;
- wire tdo_s;
-
- reg [3:0] ir_cmd;
- reg ir_ro;
- always @(posedge v_tck)
- begin
- jtag_bypass <= v_ir == cmd_bypass;
- tdi_s <= v_tdi;
- ir_cmd <= v_ir[4:1];
- ir_ro <= v_ir[0];
- end
- assign v_tdo = jtag_bypass ? tdi_s : tdo_s;
-
-
-
- wire tck_s;
- synchronizer #(.width(1), .stages(3)) tck_sync
- (
- .rst_n ( rst_n ),
- .clk ( sys_clk ),
- .d ( v_tck ),
- .q ( tck_s )
- );
-
-
-
- localparam [31:0] memaddr_mask = ((1'b1 << sdram_bits) - 3'b100)
- | sdram_base_addr;
- function logic [31:0] maskaddr (input [31:0] addr);
- maskaddr = addr & memaddr_mask;
- endfunction
- wire is_dram = |(mem_addr & sdram_base_addr);
- reg jtag_cpu_irq = 1'b0;
- reg jtag_cpu_halt = 1'b0;
- reg jtag_reset_cmd = 1'b0;
- assign cpu_irq = jtag_cpu_irq;
- assign cpu_halt = jtag_cpu_halt;
- assign reset_cmd = jtag_reset_cmd;
- reg [31:0] jtag_memaddr = maskaddr(32'b0);
- reg [31:0] jtag_cpucmd;
- reg [31:0] jtag_cpuinfo;
- reg [ 7:0] jtag_cpustatus;
- reg mem_valid;
- reg mem_write;
- reg [31:0] mem_addr;
- wire [31:0] mem_addr_next = maskaddr(mem_addr + 3'h4);
- wire [31:0] sdram_rdata;
- reg [31:0] mem_wdata;
- wire sdram_ready;
- reg sram_ready;
- reg mem_done;
- reg mem_error;
- reg advance_mem_addr;
- reg mem_header_done;
- reg mem_do_write;
- reg tck_q;
- reg tck_stb;
- always @(posedge sys_clk)
- begin
- tck_q <= tck_s;
- tck_stb <= tck_s & ~tck_q;
- end
-
-
-
- reg [4:0] sdr_ctr;
-
- reg v_st_sdr_q;
- reg [31:0] jtag_shr;
- wire [31:0] jtag_shr_in = ir_cmd[3]
- ? { tdi_s, jtag_shr[31:1] } :
- { 30'bx, tdi_s, jtag_shr[1] };
- assign tdo_s = jtag_shr[0];
- always @(posedge sys_clk)
- begin
- if ( ~rst_n )
- jtag_reset_cmd <= 1'b0;
- jtag_cpu_irq <= 1'b0;
- if ( tck_stb )
- begin
- v_st_sdr_q <= v_st_sdr;
- if ( v_st_sdr_q )
- jtag_shr <= jtag_shr_in;
- if ( v_st_cdr )
- case ( ir_cmd )
- cmd_halt: begin
- jtag_shr[0] <= jtag_cpu_halt;
- end
- cmd_memerr: begin
- jtag_shr[0] <= mem_error;
- if ( ~ir_ro ) mem_error <= 1'b0;
- end
- cmd_mem0, cmd_memaddr, cmd_memread, cmd_memwrite: begin
- jtag_shr <= jtag_memaddr;
- end
- cmd_cpucmd, cmd_cpucmd_irq: begin
- jtag_shr <= jtag_cpucmd;
- end
- cmd_cpuinfo: begin
- jtag_shr <= jtag_cpuinfo;
- end
- cmd_cpustatus: begin
- jtag_shr <= jtag_cpustatus;
- end
- default: ;
- endcase
-
-
-
-
-
-
-
-
-
-
-
- mem_do_write <= 1'b0;
-
- if ( ir_cmd[3:1] == cmd_memwr )
- begin
- if ( v_st_cdr )
- begin
- mem_done <= 1'b0;
- mem_valid <= 1'b0;
- mem_write <= ir_cmd[0];
- advance_mem_addr <= 1'b0;
- mem_header_done <= 1'b0;
- mem_addr <= jtag_memaddr;
- sdr_ctr <= 5'b0;
- mem_do_write <= 1'b0;
- end
- if ( v_st_sdr )
- begin
- sdr_ctr <= sdr_ctr + 1'b1;
- if ( ~mem_header_done )
- begin
- if ( ~mem_write )
- begin
-
- mem_header_done <= &sdr_ctr;
- end
- else
- begin
-
- if ( jtag_shr_in == VJTAG_WRITE_PREFIX )
- mem_header_done <= 1'b1;
- else
- sdr_ctr <= 5'b0;
- end
- end
-
- if ( sdr_ctr == 5'd31 )
- mem_error <= mem_error | mem_valid;
- if ( ~mem_write )
- begin
-
- case ( sdr_ctr )
- 5'd2: begin
-
-
- if ( ~ir_ro )
- jtag_memaddr <= mem_addr;
-
- advance_mem_addr <= mem_header_done;
- end
- 5'd3:
- begin
-
- mem_valid <= 1'b1;
- mem_done <= 1'b0;
- end
- 5'd31: begin
- jtag_shr <= is_dram ? sdram_rdata : sram_rdata;
- end
- default: ;
- endcase
- end
- else
- begin
-
- mem_do_write <= &sdr_ctr;
- end
- end
- end
-
- if ( mem_do_write )
- begin
- mem_wdata <= jtag_shr_in;
- mem_valid <= 1'b1;
- mem_done <= 1'b0;
- advance_mem_addr <= 1'b1;
- if ( ~ir_ro )
- jtag_memaddr <= mem_addr_next;
- end
- if ( v_st_uir )
- jtag_cpu_irq <= ir_cmd == cmd_irq;
- else if ( v_st_udr )
- jtag_cpu_irq <= ir_cmd == cmd_cpucmd_irq;
- if ( v_st_uir )
- jtag_reset_cmd <= jtag_reset_cmd | (ir_cmd == cmd_reset);
- if ( v_st_udr & ~ir_ro )
- case ( ir_cmd )
- cmd_halt: begin
- jtag_cpu_halt <= jtag_shr[0];
- end
- cmd_memaddr: begin
- jtag_memaddr <= maskaddr(jtag_shr);
- end
- cmd_cpucmd, cmd_cpucmd_irq: begin
- jtag_cpucmd <= jtag_shr;
- end
- default: ;
- endcase
- end
-
-
- if ( mem_valid )
- begin
- if (is_dram ? sdram_ready : sram_ready)
- begin
- mem_valid <= 1'b0;
- mem_done <= 1'b1;
- end
- else
- sram_ready <= ~is_dram;
- end
- if ( advance_mem_addr & ~mem_valid )
- begin
- mem_addr <= mem_addr_next;
- advance_mem_addr <= 1'b0;
- end
- end
- dram_port #(32) mem
- (
- .bus ( sdram ),
- .prio ( 2'd2 ),
- .addr ( mem_addr ),
- .valid ( mem_valid & is_dram ),
- .wd ( mem_wdata ),
- .wstrb ( {4{mem_write}} ),
- .ready ( sdram_ready ),
- .rd ( sdram_rdata )
- );
- assign sram_addr = mem_addr[sram_bits-1:2];
- assign sram_wdata = mem_wdata;
- assign sram_read = mem_valid & ~is_dram & ~mem_write;
- assign sram_write = mem_valid & ~is_dram & mem_write;
- wire [7:0] cpustatus_new =
- ( tck_stb & v_st_cdr & ~ir_ro & (ir_cmd == cmd_cpustatus) )
- ? 'b0 : jtag_cpustatus;
- always @(negedge rst_n or posedge sys_clk)
- if (~rst_n)
- begin
- jtag_cpuinfo <= 'b0;
- jtag_cpustatus <= 'b0;
- end
- else
- begin
- jtag_cpustatus <= cpustatus_new;
- if ( cpu_valid )
- begin
- case ( cpu_addr )
- 5'b00001: begin
- if ( cpu_wstrb[0] ) jtag_cpuinfo[7:0] <= cpu_wdata[7:0];
- if ( cpu_wstrb[1] ) jtag_cpuinfo[15:8] <= cpu_wdata[15:8];
- if ( cpu_wstrb[2] ) jtag_cpuinfo[23:16] <= cpu_wdata[23:16];
- if ( cpu_wstrb[3] ) jtag_cpuinfo[31:24] <= cpu_wdata[31:24];
- end
- 5'b00010: begin
- if ( cpu_wstrb[0] ) jtag_cpustatus <= cpu_wdata[7:0];
-
- end
- 5'b00011: begin
- if ( cpu_wstrb[0] )
- jtag_cpustatus <= cpustatus_new | cpu_wdata[7:0];
- end
- default: ;
- endcase
- end
- end
- always @(*)
- casez ( cpu_addr )
- 5'b00000: cpu_rdata = jtag_cpucmd;
- 5'b00001: cpu_rdata = jtag_cpuinfo;
- 5'b0001?: cpu_rdata = jtag_cpustatus;
- default: cpu_rdata = 32'bx;
- endcase
- endmodule
|