Skip to content
Snippets Groups Projects
Commit 00451296 authored by Alban Gruin's avatar Alban Gruin
Browse files

frontend: add memory access instructions detection


Signed-off-by: default avatarAlban Gruin <alban.gruin@irit.fr>
parent 8b6f6f93
Branches
No related tags found
No related merge requests found
...@@ -76,6 +76,11 @@ module ariane import ariane_pkg::*; #( ...@@ -76,6 +76,11 @@ module ariane import ariane_pkg::*; #(
logic fetch_valid_if_id; logic fetch_valid_if_id;
logic fetch_ready_id_if; logic fetch_ready_id_if;
// --------------
// IF -> verifier
// --------------
logic has_mem_access_if_verif;
// -------------- // --------------
// ID <-> ISSUE // ID <-> ISSUE
// -------------- // --------------
...@@ -261,6 +266,7 @@ module ariane import ariane_pkg::*; #( ...@@ -261,6 +266,7 @@ module ariane import ariane_pkg::*; #(
.fetch_entry_o ( fetch_entry_if_id ), .fetch_entry_o ( fetch_entry_if_id ),
.fetch_entry_valid_o ( fetch_valid_if_id ), .fetch_entry_valid_o ( fetch_valid_if_id ),
.fetch_entry_ready_i ( fetch_ready_id_if ), .fetch_entry_ready_i ( fetch_ready_id_if ),
.has_mem_access_o ( has_mem_access_if_verif ),
.* .*
); );
...@@ -617,6 +623,9 @@ module ariane import ariane_pkg::*; #( ...@@ -617,6 +623,9 @@ module ariane import ariane_pkg::*; #(
.rst_ni, .rst_ni,
.flush_i (flush_ctrl_id), .flush_i (flush_ctrl_id),
// IF
.if_has_mem_access_i (has_mem_access_if_verif),
// CO // CO
.commit_instr_i (commit_instr_id_commit), .commit_instr_i (commit_instr_id_commit),
.commit_ack_i (commit_ack) .commit_ack_i (commit_ack)
......
...@@ -43,7 +43,9 @@ module frontend import ariane_pkg::*; #( ...@@ -43,7 +43,9 @@ module frontend import ariane_pkg::*; #(
// instruction output port -> to processor back-end // instruction output port -> to processor back-end
output fetch_entry_t fetch_entry_o, // fetch entry containing all relevant data for the ID stage output fetch_entry_t fetch_entry_o, // fetch entry containing all relevant data for the ID stage
output logic fetch_entry_valid_o, // instruction in IF is valid output logic fetch_entry_valid_o, // instruction in IF is valid
input logic fetch_entry_ready_i // ID acknowledged this instruction input logic fetch_entry_ready_i, // ID acknowledged this instruction
output logic has_mem_access_o
); );
// Instruction Cache Registers, from I$ // Instruction Cache Registers, from I$
logic [FETCH_WIDTH-1:0] icache_data_q; logic [FETCH_WIDTH-1:0] icache_data_q;
...@@ -428,7 +430,8 @@ module frontend import ariane_pkg::*; #( ...@@ -428,7 +430,8 @@ module frontend import ariane_pkg::*; #(
.replay_addr_o ( replay_addr ), .replay_addr_o ( replay_addr ),
.fetch_entry_o ( fetch_entry_o ), // to back-end .fetch_entry_o ( fetch_entry_o ), // to back-end
.fetch_entry_valid_o ( fetch_entry_valid_o ), // to back-end .fetch_entry_valid_o ( fetch_entry_valid_o ), // to back-end
.fetch_entry_ready_i ( fetch_entry_ready_i ) // to back-end .fetch_entry_ready_i ( fetch_entry_ready_i ), // to back-end
.has_mem_access_o ( has_mem_access_o ) // to verifier
); );
// pragma translate_off // pragma translate_off
......
...@@ -64,7 +64,9 @@ module instr_queue ( ...@@ -64,7 +64,9 @@ module instr_queue (
// to processor backend // to processor backend
output ariane_pkg::fetch_entry_t fetch_entry_o, output ariane_pkg::fetch_entry_t fetch_entry_o,
output logic fetch_entry_valid_o, output logic fetch_entry_valid_o,
input logic fetch_entry_ready_i input logic fetch_entry_ready_i,
output logic has_mem_access_o
); );
typedef struct packed { typedef struct packed {
...@@ -117,6 +119,12 @@ module instr_queue ( ...@@ -117,6 +119,12 @@ module instr_queue (
// replay interface // replay interface
logic [ariane_pkg::INSTR_PER_FETCH-1:0] instr_overflow_fifo; logic [ariane_pkg::INSTR_PER_FETCH-1:0] instr_overflow_fifo;
// memory access count
logic [ariane_pkg::INSTR_PER_FETCH-1:0] input_is_mem;
logic output_is_mem;
logic [$clog2(ariane_pkg::FETCH_FIFO_DEPTH)*2-1:0] nr_mem_n, nr_mem_q;
assign ready_o = ~(|instr_queue_full) & ~full_address; assign ready_o = ~(|instr_queue_full) & ~full_address;
for (genvar i = 0; i < ariane_pkg::INSTR_PER_FETCH; i++) begin : gen_unpack_taken for (genvar i = 0; i < ariane_pkg::INSTR_PER_FETCH; i++) begin : gen_unpack_taken
...@@ -211,6 +219,41 @@ module instr_queue ( ...@@ -211,6 +219,41 @@ module instr_queue (
// as long as there is at least one queue which can take the value we have a valid instruction // as long as there is at least one queue which can take the value we have a valid instruction
assign fetch_entry_valid_o = ~(&instr_queue_empty); assign fetch_entry_valid_o = ~(&instr_queue_empty);
// ----------------------
// Memory access detector
// ----------------------
for (genvar i = 0; i < ariane_pkg::INSTR_PER_FETCH; i++) begin
assign input_is_mem[i] = valid_i[i] &
((instr_i[i][6:0] == riscv::OpcodeLoad) |
(instr_i[i][6:0] == riscv::OpcodeLoadFp) |
(instr_i[i][6:0] == riscv::OpcodeStore) |
(instr_i[i][6:0] == riscv::OpcodeStoreFp) |
(instr_i[i][6:0] == riscv::OpcodeAmo));
end
assign output_is_mem = fetch_entry_valid_o &
((fetch_entry_o.instruction[6:0] == riscv::OpcodeLoad) |
(fetch_entry_o.instruction[6:0] == riscv::OpcodeLoadFp) |
(fetch_entry_o.instruction[6:0] == riscv::OpcodeStore) |
(fetch_entry_o.instruction[6:0] == riscv::OpcodeStoreFp) |
(fetch_entry_o.instruction[6:0] == riscv::OpcodeAmo));
assign has_mem_access_o = (|nr_mem_n) | (|input_is_mem) | output_is_mem;
always_comb begin
nr_mem_n = nr_mem_q;
for (int unsigned i = 0; i < ariane_pkg::INSTR_PER_FETCH; i++) begin
if (push_instr_fifo[i]) begin
nr_mem_n = nr_mem_n + 1'b1;
end
end
if (fetch_entry_ready_i) begin
nr_mem_n = nr_mem_n - 1'b1;
end
end
always_comb begin always_comb begin
idx_ds_d = idx_ds_q; idx_ds_d = idx_ds_q;
...@@ -331,6 +374,7 @@ module instr_queue ( ...@@ -331,6 +374,7 @@ module instr_queue (
idx_is_q <= '0; idx_is_q <= '0;
pc_q <= '0; pc_q <= '0;
reset_address_q <= 1'b1; reset_address_q <= 1'b1;
nr_mem_q <= '0;
end else begin end else begin
pc_q <= pc_d; pc_q <= pc_d;
reset_address_q <= reset_address_d; reset_address_q <= reset_address_d;
...@@ -340,9 +384,11 @@ module instr_queue ( ...@@ -340,9 +384,11 @@ module instr_queue (
// binary encoded // binary encoded
idx_is_q <= '0; idx_is_q <= '0;
reset_address_q <= 1'b1; reset_address_q <= 1'b1;
nr_mem_q <= '0;
end else begin end else begin
idx_ds_q <= idx_ds_d; idx_ds_q <= idx_ds_d;
idx_is_q <= idx_is_d; idx_is_q <= idx_is_d;
nr_mem_q <= nr_mem_n;
end end
end end
end end
......
...@@ -2,12 +2,15 @@ module verifier #( ...@@ -2,12 +2,15 @@ module verifier #(
parameter int unsigned NR_ENTRIES = 8, parameter int unsigned NR_ENTRIES = 8,
parameter int unsigned NR_COMMIT_PORTS = 2 parameter int unsigned NR_COMMIT_PORTS = 2
) ( ) (
input logic clk_i, input logic clk_i,
input logic rst_ni, input logic rst_ni,
input logic flush_i, input logic flush_i,
// Frontend
input logic if_has_mem_access_i,
// CO // CO
input ariane_pkg::scoreboard_entry_t [NR_COMMIT_PORTS-1:0] commit_instr_i, input ariane_pkg::scoreboard_entry_t [NR_COMMIT_PORTS-1:0] commit_instr_i,
input logic [NR_COMMIT_PORTS-1:0] commit_ack_i input logic [NR_COMMIT_PORTS-1:0] commit_ack_i
); );
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment