URL
https://opencores.org/ocsvn/t6507lp/t6507lp/trunk
Subversion Repositories t6507lp
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 94 to Rev 95
- ↔ Reverse comparison
Rev 94 → Rev 95
/t6507lp/trunk/rtl/verilog/t6507lp_fsm_tb.v
62,6 → 62,8
wire [7:0] alu_a; |
wire alu_enable; |
|
integer i; |
|
`include "../T6507LP_Package.v" |
|
t6507lp_fsm #(8,13) my_dut(clk, reset_n, alu_result, alu_status, data_in, address, control, data_out, alu_opcode, alu_a, alu_enable, alu_x, alu_y); |
68,7 → 70,7
|
always #10 clk = ~clk; |
|
reg[7:0] fake_mem[2000:0]; |
reg[7:0] fake_mem[2**13-1:0]; |
|
initial begin |
clk = 0; |
77,7 → 79,13
alu_status = 8'h00; |
alu_x = 8'h07; |
alu_y = 8'h03; |
|
for (i=0; i < 2**13; i= i+1) begin |
$write("\n%d",i); |
fake_mem[i]=8'h00; |
end |
|
|
fake_mem[0] = ASL_ACC; // testing ACC mode |
fake_mem[1] = ADC_IMM; // testing IMM mode |
fake_mem[2] = 8'h27; |
134,15 → 142,25
fake_mem[315] = BEQ_REL; // testing REL mode, not taking a branch, page would have crossed. |
fake_mem[316] = 8'hff; |
fake_mem[317] = BEQ_REL; // testing REL mode, not taking a branch, page would not have crossed. |
fake_mem[318] = 8'h0; |
|
|
fake_mem[318] = 8'h00; |
fake_mem[319] = LDA_IDX; // testing IDX mode READ TYPE, no page crossed; |
fake_mem[320] = 8'h0a; |
fake_mem[321] = LDA_IDX; // testing IDX mode READ TYPE, page crossed; this will actually do A = MEM[6] because there is no carry |
fake_mem[322] = 8'hff; |
//fake_mem[319] = SLO_IDX; // testing IDX mode READ_MODIFY_WRITE TYPE |
//fake_mem[320] = 8'h0a; // all of read modify write instructions are not documented therefore will not be simulated |
fake_mem[323] = STA_IDX; // testing IDX mode WRITE TYPE, page crossed being ignored |
fake_mem[324] = 8'hff; |
fake_mem[325] = STA_IDX; // testing IDX mode WRITE TYPE, page not crossed; |
fake_mem[326] = 8'hff; |
//fake_mem[321] = LDA_IDX; // testing IDX mode READ TYPE, page crossed; |
//fake_mem[322] = 8'hff; |
|
@(negedge clk) // will wait for next negative edge of the clock (t=20) |
reset_n=1'b1; |
|
|
#2000; |
#3000; |
$finish; // to shut down the simulation |
end //initial |
|
/t6507lp/trunk/rtl/verilog/t6507lp_fsm.v
9,8 → 9,6
//// 6507 FSM //// |
//// //// |
//// TODO: //// |
//// - Fix absolute indexed mode //// |
//// - Code the relative mode //// |
//// - Code the indexed indirect mode //// |
//// - Code the indirect indexed mode //// |
//// - Code the absolute indirect mode //// |
71,21 → 69,25
input [DATA_SIZE_:0] alu_y; |
|
// FSM states |
localparam FETCH_OP = 4'b0000; |
localparam FETCH_OP_CALC = 4'b0001; |
localparam FETCH_LOW = 4'b0010; |
localparam FETCH_HIGH = 4'b0011; |
localparam READ_MEM = 4'b0100; |
localparam DUMMY_WRT_CALC = 4'b0101; |
localparam WRITE_MEM = 4'b0110; |
localparam FETCH_OP_CALC_PARAM = 4'b0111; |
localparam READ_MEM_CALC_INDEX = 4'b1000; |
localparam FETCH_HIGH_CALC_INDEX = 4'b1001; |
localparam READ_MEM_FIX_ADDR = 4'b1010; |
localparam FETCH_OP_EVAL_BRANCH = 4'b1011; |
localparam FETCH_OP_FIX_PC = 4'b1100; |
localparam RESET = 4'b1111; |
localparam FETCH_OP = 5'b00000; |
localparam FETCH_OP_CALC = 5'b00001; |
localparam FETCH_LOW = 5'b00010; |
localparam FETCH_HIGH = 5'b00011; |
localparam READ_MEM = 5'b00100; |
localparam DUMMY_WRT_CALC = 5'b00101; |
localparam WRITE_MEM = 5'b00110; |
localparam FETCH_OP_CALC_PARAM = 5'b00111; |
localparam READ_MEM_CALC_INDEX = 5'b01000; |
localparam FETCH_HIGH_CALC_INDEX = 5'b01001; |
localparam READ_MEM_FIX_ADDR = 5'b01010; |
localparam FETCH_OP_EVAL_BRANCH = 5'b01011; |
localparam FETCH_OP_FIX_PC = 5'b01100; |
localparam READ_FROM_POINTER = 5'b01101; |
localparam READ_FROM_POINTER_X = 5'b01110; |
localparam READ_FROM_POINTER_X1 = 5'b01111; |
|
localparam RESET = 5'b11111; |
|
// OPCODES TODO: verify how this get synthesised |
`include "../T6507LP_Package.v" |
|
108,7 → 110,8
reg accumulator; |
reg immediate; |
reg implied; |
reg indirect; |
reg indirectx; |
reg indirecty; |
reg relative; |
reg zero_page; |
reg zero_page_indexed; |
142,6 → 145,14
address_plus_index[12:8] = pc[12:8] + page_crossed;// warning: pc might feed these lines twice and cause branch failure |
end // solution: add a temp reg i guess |
end |
else if (state == READ_FROM_POINTER) begin |
{page_crossed, address_plus_index[7:0]} = temp_data + index; |
address_plus_index[12:8] = 5'b00000; |
end |
else if (state == READ_FROM_POINTER_X) begin |
{page_crossed, address_plus_index[7:0]} = temp_data + index + 8'h01; |
address_plus_index[12:8] = 5'b00000; |
end |
end |
|
always @ (posedge clk or negedge reset_n) begin // sequencial always block |
217,6 → 228,12
temp_addr <= {{5{1'b0}}, data_in}; |
control <= MEM_READ; |
end |
else if (indirectx) begin |
pc <= next_pc; |
address <= data_in; |
temp_data <= data_in; |
control <= MEM_READ; |
end |
end |
FETCH_HIGH_CALC_INDEX: begin |
pc <= next_pc; |
237,6 → 254,7
address <= next_pc; |
control <= MEM_READ; |
data_out <= 8'h00; |
ir <= data_in; |
end |
end |
FETCH_OP_FIX_PC: begin |
350,8 → 368,30
control <= MEM_READ; |
data_out <= 8'h00; |
end |
READ_FROM_POINTER: begin |
pc <= pc; |
address <= address_plus_index; |
//temp_addr[7:0] <= data_in; |
control <= MEM_READ; |
end |
READ_FROM_POINTER_X: begin |
pc <= pc; |
address <= address_plus_index; |
temp_addr[7:0] <= data_in; |
control <= MEM_READ; |
end |
READ_FROM_POINTER_X1: begin |
pc <= pc; |
address <= {data_in[5:0], temp_addr[7:0]}; |
if (write) begin |
control <= MEM_WRITE; |
end |
else begin |
control <= MEM_READ; |
end |
end |
default: begin |
$write("unknown state"); // TODO: check if synth really ignores this 2 lines. Otherwise wrap it with a `ifdef |
$write("unknown state"); // TODO: check if synth really ignores this 2 lines. Otherwise wrap it with a `ifdef |
$finish(0); |
end |
|
425,7 → 465,26
else if (relative) begin |
next_state = FETCH_OP_EVAL_BRANCH; |
end |
else if (indirectx) begin |
next_state = READ_FROM_POINTER; |
end |
end |
READ_FROM_POINTER: begin |
next_state = READ_FROM_POINTER_X; |
end |
READ_FROM_POINTER_X: begin |
next_state = READ_FROM_POINTER_X1; |
end |
READ_FROM_POINTER_X1: begin |
if (read || read_modify_write) begin |
next_state = READ_MEM; |
end |
else if (write) begin |
alu_opcode = ir; |
alu_enable = 1'b1; |
next_state = WRITE_MEM; |
end |
end |
FETCH_OP_EVAL_BRANCH: begin |
if (branch) begin |
next_state = FETCH_OP_FIX_PC; |
524,7 → 583,8
accumulator = 1'b0; |
immediate = 1'b0; |
implied = 1'b0; |
indirect = 1'b0; |
indirectx = 1'b0; |
indirecty = 1'b0; |
relative = 1'b0; |
zero_page = 1'b0; |
zero_page_indexed = 1'b0; |
664,10 → 724,14
absolute_indexed = 1'b1; |
index = alu_y; |
end |
ADC_IDX, AND_IDX, CMP_IDX, EOR_IDX, LDA_IDX, ORA_IDX, SBC_IDX, STA_IDX, ADC_IDY, AND_IDY, CMP_IDY, EOR_IDY, LDA_IDY, |
ORA_IDY, SBC_IDY, STA_IDY: begin // all these opcodes are 8'hX1; TODO: optimize this |
indirect = 1'b1; |
ADC_IDX, AND_IDX, CMP_IDX, EOR_IDX, LDA_IDX, ORA_IDX, SBC_IDX, STA_IDX: begin |
indirectx = 1'b1; |
index = alu_x; |
end |
ADC_IDY, AND_IDY, CMP_IDY, EOR_IDY, LDA_IDY, ORA_IDY, SBC_IDY, STA_IDY: begin |
indirecty = 1'b1; |
index = alu_y; |
end |
default: begin |
$write("state : %b", state); |
if (reset_n == 1 && state != FETCH_OP_FIX_PC) begin // the processor is NOT being reset neither it is fixing the pc |