Line 192... |
Line 192... |
// set the following address in question. Hence all accesses require
|
// set the following address in question. Hence all accesses require
|
// two accesses: write the address to the control register (and halt
|
// two accesses: write the address to the control register (and halt
|
// the CPU if not halted), then read/write the data from the data
|
// the CPU if not halted), then read/write the data from the data
|
// register.
|
// register.
|
//
|
//
|
wire cpu_break;
|
wire cpu_break, dbg_cmd_write;
|
reg cmd_reset, cmd_halt, cmd_step;
|
reg cmd_reset, cmd_halt, cmd_step;
|
reg [5:0] cmd_addr;
|
reg [5:0] cmd_addr;
|
|
assign dbg_cmd_write = (dbg_cyc)&&(dbg_stb)&&(dbg_we)&&(~dbg_addr);
|
|
//
|
initial cmd_reset = 1'b1;
|
initial cmd_reset = 1'b1;
|
|
always @(posedge i_clk)
|
|
cmd_reset <= ((dbg_cmd_write)&&(dbg_idata[6]));
|
|
//
|
initial cmd_halt = 1'b1;
|
initial cmd_halt = 1'b1;
|
initial cmd_step = 1'b0;
|
|
always @(posedge i_clk)
|
always @(posedge i_clk)
|
if (i_rst)
|
if (i_rst)
|
begin
|
|
cmd_halt <= 1'b0;
|
cmd_halt <= 1'b0;
|
cmd_step <= 1'b0;
|
else if (dbg_cmd_write)
|
cmd_reset<= 1'b0;
|
|
cmd_addr <= 6'h00;
|
|
end else if ((dbg_cyc)&&(dbg_stb)
|
|
&&(dbg_we)&&(~dbg_addr))
|
|
begin
|
|
cmd_halt <= dbg_idata[10];
|
cmd_halt <= dbg_idata[10];
|
cmd_step <= dbg_idata[ 8];
|
else if ((cmd_step)||(cpu_break))
|
cmd_reset<= dbg_idata[ 6];
|
|
cmd_addr <= dbg_idata[5:0];
|
|
end else if (cmd_step)
|
|
begin
|
|
cmd_halt <= 1'b1;
|
|
cmd_step <= 1'b0;
|
|
end else if (cpu_break)
|
|
cmd_halt <= 1'b1;
|
cmd_halt <= 1'b1;
|
|
//
|
|
initial cmd_step = 1'b0;
|
|
always @(posedge i_clk)
|
|
cmd_step <= (dbg_cmd_write)&&(dbg_idata[8]);
|
|
//
|
|
always @(posedge i_clk)
|
|
if (dbg_cmd_write)
|
|
cmd_addr <= dbg_idata[5:0];
|
|
|
wire cpu_reset;
|
wire cpu_reset;
|
assign cpu_reset = (i_rst)||(cmd_reset)||(wdt_reset);
|
assign cpu_reset = (i_rst)||(cmd_reset)||(wdt_reset);
|
|
|
wire cpu_halt, cpu_dbg_stall;
|
wire cpu_halt, cpu_dbg_stall;
|
assign cpu_halt = (cmd_halt)&&(~cmd_step);
|
assign cpu_halt = (cmd_halt)&&(~cmd_step);
|
Line 275... |
Line 275... |
|
|
// Counters -- for performance measurement and accounting
|
// Counters -- for performance measurement and accounting
|
//
|
//
|
// Here's the stuff we'll be counting ....
|
// Here's the stuff we'll be counting ....
|
//
|
//
|
wire cpu_mem_stall, cpu_pf_stall, cpu_alu_stall;
|
wire cpu_op_stall, cpu_pf_stall, cpu_i_count;
|
|
|
//
|
//
|
// The master counters will, in general, not be reset. They'll be used
|
// The master counters will, in general, not be reset. They'll be used
|
// for an overall counter.
|
// for an overall counter.
|
//
|
//
|
Line 289... |
Line 289... |
zipcounter mtask_ctr(i_clk, (~cmd_halt), sys_cyc,
|
zipcounter mtask_ctr(i_clk, (~cmd_halt), sys_cyc,
|
(sys_stb)&&(sys_addr == `MSTR_TASK_CTR),
|
(sys_stb)&&(sys_addr == `MSTR_TASK_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
mtc_ack, mtc_stall, mtc_data, mtc_int);
|
mtc_ack, mtc_stall, mtc_data, mtc_int);
|
|
|
// Master Memory-Stall counter
|
// Master Operand Stall counter
|
wire mmc_ack, mmc_stall, mmc_int;
|
wire moc_ack, moc_stall, moc_int;
|
wire [31:0] mmc_data;
|
wire [31:0] moc_data;
|
zipcounter mmstall_ctr(i_clk,(~cmd_halt)&&(cpu_mem_stall), sys_cyc,
|
zipcounter mmstall_ctr(i_clk,(cpu_op_stall), sys_cyc,
|
(sys_stb)&&(sys_addr == `MSTR_MSTL_CTR),
|
(sys_stb)&&(sys_addr == `MSTR_MSTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
mmc_ack, mmc_stall, mmc_data, mmc_int);
|
moc_ack, moc_stall, moc_data, moc_int);
|
|
|
// Master PreFetch-Stall counter
|
// Master PreFetch-Stall counter
|
wire mpc_ack, mpc_stall, mpc_int;
|
wire mpc_ack, mpc_stall, mpc_int;
|
wire [31:0] mpc_data;
|
wire [31:0] mpc_data;
|
zipcounter mpstall_ctr(i_clk,(~cmd_halt)&&(cpu_pf_stall), sys_cyc,
|
zipcounter mpstall_ctr(i_clk,(cpu_pf_stall), sys_cyc,
|
(sys_stb)&&(sys_addr == `MSTR_PSTL_CTR),
|
(sys_stb)&&(sys_addr == `MSTR_PSTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
mpc_ack, mpc_stall, mpc_data, mpc_int);
|
mpc_ack, mpc_stall, mpc_data, mpc_int);
|
|
|
// Master ALU-Stall counter
|
// Master Instruction counter
|
wire mac_ack, mac_stall, mac_int;
|
wire mic_ack, mic_stall, mic_int;
|
wire [31:0] mac_data;
|
wire [31:0] mic_data;
|
zipcounter mastall_ctr(i_clk,(~cmd_halt)&&(cpu_alu_stall), sys_cyc,
|
zipcounter mins_ctr(i_clk,(cpu_i_count), sys_cyc,
|
(sys_stb)&&(sys_addr == `MSTR_ASTL_CTR),
|
(sys_stb)&&(sys_addr == `MSTR_ASTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
mac_ack, mac_stall, mac_data, mac_int);
|
mic_ack, mic_stall, mic_data, mic_int);
|
|
|
//
|
//
|
// The user counters are different from those of the master. They will
|
// The user counters are different from those of the master. They will
|
// be reset any time a task is given control of the CPU.
|
// be reset any time a task is given control of the CPU.
|
//
|
//
|
Line 325... |
Line 325... |
zipcounter utask_ctr(i_clk,(~cmd_halt), sys_cyc,
|
zipcounter utask_ctr(i_clk,(~cmd_halt), sys_cyc,
|
(sys_stb)&&(sys_addr == `USER_TASK_CTR),
|
(sys_stb)&&(sys_addr == `USER_TASK_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
utc_ack, utc_stall, utc_data, utc_int);
|
utc_ack, utc_stall, utc_data, utc_int);
|
|
|
// User Memory-Stall counter
|
// User Op-Stall counter
|
wire umc_ack, umc_stall, umc_int;
|
wire uoc_ack, uoc_stall, uoc_int;
|
wire [31:0] umc_data;
|
wire [31:0] uoc_data;
|
zipcounter umstall_ctr(i_clk,(~cmd_halt)&&(cpu_mem_stall), sys_cyc,
|
zipcounter umstall_ctr(i_clk,(cpu_op_stall), sys_cyc,
|
(sys_stb)&&(sys_addr == `USER_MSTL_CTR),
|
(sys_stb)&&(sys_addr == `USER_MSTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
umc_ack, umc_stall, umc_data, umc_int);
|
uoc_ack, uoc_stall, uoc_data, uoc_int);
|
|
|
// User PreFetch-Stall counter
|
// User PreFetch-Stall counter
|
wire upc_ack, upc_stall, upc_int;
|
wire upc_ack, upc_stall, upc_int;
|
wire [31:0] upc_data;
|
wire [31:0] upc_data;
|
zipcounter upstall_ctr(i_clk,(~cmd_halt)&&(cpu_pf_stall), sys_cyc,
|
zipcounter upstall_ctr(i_clk,(cpu_pf_stall), sys_cyc,
|
(sys_stb)&&(sys_addr == `USER_PSTL_CTR),
|
(sys_stb)&&(sys_addr == `USER_PSTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
upc_ack, upc_stall, upc_data, upc_int);
|
upc_ack, upc_stall, upc_data, upc_int);
|
|
|
// User ALU-Stall counter
|
// User instruction counter
|
wire uac_ack, uac_stall, uac_int;
|
wire uic_ack, uic_stall, uic_int;
|
wire [31:0] uac_data;
|
wire [31:0] uic_data;
|
zipcounter uastall_ctr(i_clk,(~cmd_halt)&&(cpu_alu_stall), sys_cyc,
|
zipcounter uins_ctr(i_clk,(cpu_i_count), sys_cyc,
|
(sys_stb)&&(sys_addr == `USER_ASTL_CTR),
|
(sys_stb)&&(sys_addr == `USER_ASTL_CTR),
|
sys_we, sys_data,
|
sys_we, sys_data,
|
uac_ack, uac_stall, uac_data, uac_int);
|
uic_ack, uic_stall, uic_data, uic_int);
|
|
|
// A little bit of pre-cleanup (actr = accounting counters)
|
// A little bit of pre-cleanup (actr = accounting counters)
|
wire actr_ack, actr_stall;
|
wire actr_ack, actr_stall;
|
wire [31:0] actr_data;
|
wire [31:0] actr_data;
|
assign actr_ack = ((mtc_ack | mmc_ack | mpc_ack | mac_ack)
|
assign actr_ack = ((mtc_ack | moc_ack | mpc_ack | mic_ack)
|
|(utc_ack | umc_ack | upc_ack | uac_ack));
|
|(utc_ack | uoc_ack | upc_ack | uic_ack));
|
assign actr_stall = ((mtc_stall | mmc_stall | mpc_stall | mac_stall)
|
assign actr_stall = ((mtc_stall | moc_stall | mpc_stall | mic_stall)
|
|(utc_stall | umc_stall | upc_stall|uac_stall));
|
|(utc_stall | uoc_stall | upc_stall|uic_stall));
|
assign actr_data = ((mtc_ack) ? mtc_data
|
assign actr_data = ((mtc_ack) ? mtc_data
|
: ((mmc_ack) ? mmc_data
|
: ((moc_ack) ? moc_data
|
: ((mpc_ack) ? mpc_data
|
: ((mpc_ack) ? mpc_data
|
: ((mac_ack) ? mac_data
|
: ((mic_ack) ? mic_data
|
: ((utc_ack) ? utc_data
|
: ((utc_ack) ? utc_data
|
: ((umc_ack) ? umc_data
|
: ((uoc_ack) ? uoc_data
|
: ((upc_ack) ? upc_data
|
: ((upc_ack) ? upc_data
|
: uac_data)))))));
|
: uic_data)))))));
|
|
|
|
|
|
|
//
|
//
|
// Counter Interrupt controller
|
// Counter Interrupt controller
|
Line 375... |
Line 375... |
reg ctri_ack;
|
reg ctri_ack;
|
wire ctri_stall, ctri_int, ctri_sel;
|
wire ctri_stall, ctri_int, ctri_sel;
|
wire [7:0] ctri_vector;
|
wire [7:0] ctri_vector;
|
wire [31:0] ctri_data;
|
wire [31:0] ctri_data;
|
assign ctri_sel = (sys_cyc)&&(sys_stb)&&(sys_addr == `CTRINT);
|
assign ctri_sel = (sys_cyc)&&(sys_stb)&&(sys_addr == `CTRINT);
|
assign ctri_vector = { mtc_int, mmc_int, mpc_int, mac_int,
|
assign ctri_vector = { mtc_int, moc_int, mpc_int, mic_int,
|
utc_int, umc_int, upc_int, uac_int };
|
utc_int, uoc_int, upc_int, uic_int };
|
icontrol #(8) ctri(i_clk, cpu_reset, (ctri_sel)&&(sys_addr==`CTRINT),
|
icontrol #(8) ctri(i_clk, cpu_reset, (ctri_sel)&&(sys_addr==`CTRINT),
|
sys_data, ctri_data, ctri_vector, ctri_int);
|
sys_data, ctri_data, ctri_vector, ctri_int);
|
always @(posedge i_clk)
|
always @(posedge i_clk)
|
ctri_ack <= ctri_sel;
|
ctri_ack <= ctri_sel;
|
|
|
Line 454... |
Line 454... |
cpu_halt, cmd_addr[4:0], cpu_dbg_we,
|
cpu_halt, cmd_addr[4:0], cpu_dbg_we,
|
dbg_idata, cpu_dbg_stall, cpu_dbg_data,
|
dbg_idata, cpu_dbg_stall, cpu_dbg_data,
|
cpu_break,
|
cpu_break,
|
cpu_cyc, cpu_stb, cpu_we, cpu_addr, cpu_data,
|
cpu_cyc, cpu_stb, cpu_we, cpu_addr, cpu_data,
|
cpu_ack, cpu_stall, wb_data,
|
cpu_ack, cpu_stall, wb_data,
|
cpu_mem_stall, cpu_pf_stall, cpu_alu_stall);
|
cpu_op_stall, cpu_pf_stall, cpu_i_count);
|
|
|
// Now, arbitrate the bus ... first for the local peripherals
|
// Now, arbitrate the bus ... first for the local peripherals
|
assign sys_cyc = (cpu_cyc)||((cpu_halt)&&(~cpu_dbg_stall)&&(dbg_cyc));
|
assign sys_cyc = (cpu_cyc)||((cpu_halt)&&(~cpu_dbg_stall)&&(dbg_cyc));
|
assign sys_stb = (cpu_cyc)
|
assign sys_stb = (cpu_cyc)
|
? ((cpu_stb)&&(cpu_addr[31:4] == 28'hc000000))
|
? ((cpu_stb)&&(cpu_addr[31:4] == 28'hc000000))
|