OpenCores
URL https://opencores.org/ocsvn/yifive/yifive/trunk

Subversion Repositories yifive

[/] [yifive/] [trunk/] [caravel_yifive/] [verilog/] [rtl/] [syntacore/] [scr1/] [src/] [top/] [scr1_imem_ahb.sv] - Blame information for rev 11

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 11 dinesha
/// Copyright by Syntacore LLC © 2016-2021. See LICENSE for details
2
/// @file       
3
/// @brief      Instruction memory AHB bridge
4
///
5
 
6
`include "scr1_ahb.svh"
7
`include "scr1_memif.svh"
8
 
9
module scr1_imem_ahb (
10
    // Control Signals
11
    input   logic                           rst_n,
12
    input   logic                           clk,
13
 
14
    // Core Interface
15
    output  logic                           imem_req_ack,
16
    input   logic                           imem_req,
17
    input   logic   [SCR1_AHB_WIDTH-1:0]    imem_addr,
18
    output  logic   [SCR1_AHB_WIDTH-1:0]    imem_rdata,
19
    output  type_scr1_mem_resp_e            imem_resp,
20
 
21
    // AHB Interface
22
    output  logic   [3:0]                   hprot,
23
    output  logic   [2:0]                   hburst,
24
    output  logic   [2:0]                   hsize,
25
    output  logic   [1:0]                   htrans,
26
    output  logic                           hmastlock,
27
    output  logic   [SCR1_AHB_WIDTH-1:0]    haddr,
28
    input   logic                           hready,
29
    input   logic   [SCR1_AHB_WIDTH-1:0]    hrdata,
30
    input   logic                           hresp
31
 
32
);
33
 
34
//-------------------------------------------------------------------------------
35
// Local parameters declaration
36
//-------------------------------------------------------------------------------
37
`ifndef SCR1_IMEM_AHB_OUT_BP
38
localparam  SCR1_FIFO_WIDTH = 2;
39
localparam  SCR1_FIFO_CNT_WIDTH = $clog2(SCR1_FIFO_WIDTH+1);
40
`endif // SCR1_IMEM_AHB_OUT_BP
41
 
42
//-------------------------------------------------------------------------------
43
// Local types declaration
44
//-------------------------------------------------------------------------------
45
typedef enum logic {
46
    SCR1_FSM_ADDR = 1'b0,
47
    SCR1_FSM_DATA = 1'b1,
48
    SCR1_FSM_ERR  = 1'bx
49
} type_scr1_fsm_e;
50
 
51
typedef struct packed {
52
    logic   [SCR1_AHB_WIDTH-1:0]    haddr;
53
} type_scr1_req_fifo_s;
54
 
55
typedef struct packed {
56
    logic                           hresp;
57
    logic   [SCR1_AHB_WIDTH-1:0]    hrdata;
58
} type_scr1_resp_fifo_s;
59
 
60
//-------------------------------------------------------------------------------
61
// Local signal declaration
62
//-------------------------------------------------------------------------------
63
type_scr1_fsm_e                             fsm;
64
logic                                       req_fifo_rd;
65
logic                                       req_fifo_wr;
66
logic                                       req_fifo_up;
67
`ifdef SCR1_IMEM_AHB_OUT_BP
68
type_scr1_req_fifo_s                        req_fifo_r;
69
type_scr1_req_fifo_s [0:0]                  req_fifo;
70
`else // SCR1_IMEM_AHB_OUT_BP
71
type_scr1_req_fifo_s [0:SCR1_FIFO_WIDTH-1]  req_fifo;
72
type_scr1_req_fifo_s [0:SCR1_FIFO_WIDTH-1]  req_fifo_new;
73
logic       [SCR1_FIFO_CNT_WIDTH-1:0]       req_fifo_cnt;
74
logic       [SCR1_FIFO_CNT_WIDTH-1:0]       req_fifo_cnt_new;
75
`endif // SCR1_IMEM_AHB_OUT_BP
76
logic                                       req_fifo_empty;
77
logic                                       req_fifo_full;
78
 
79
type_scr1_resp_fifo_s                       resp_fifo;
80
logic                                       resp_fifo_hready;
81
 
82
//-------------------------------------------------------------------------------
83
// Interface to Core
84
//-------------------------------------------------------------------------------
85
assign imem_req_ack = ~req_fifo_full;
86
assign req_fifo_wr  = ~req_fifo_full & imem_req;
87
 
88
assign imem_rdata = resp_fifo.hrdata;
89
 
90
assign imem_resp = (resp_fifo_hready)
91
                    ? (resp_fifo.hresp == SCR1_HRESP_OKAY)
92
                        ? SCR1_MEM_RESP_RDY_OK
93
                        : SCR1_MEM_RESP_RDY_ER
94
                    : SCR1_MEM_RESP_NOTRDY;
95
 
96
//-------------------------------------------------------------------------------
97
// REQ_FIFO
98
//-------------------------------------------------------------------------------
99
`ifdef SCR1_IMEM_AHB_OUT_BP
100
always_ff @(negedge rst_n, posedge clk) begin
101
    if (~rst_n) begin
102
        req_fifo_full <= 1'b0;
103
    end else begin
104
        if (~req_fifo_full) begin
105
            req_fifo_full <= imem_req & ~req_fifo_rd;
106
        end else begin
107
            req_fifo_full <= ~req_fifo_rd;
108
        end
109
    end
110
end
111
assign req_fifo_empty = ~(req_fifo_full | imem_req);
112
 
113
assign req_fifo_up    = ~req_fifo_rd & req_fifo_wr;
114
always_ff @(posedge clk) begin
115
    if (req_fifo_up) begin
116
        req_fifo_r.haddr <= imem_addr;
117
    end
118
end
119
 
120
assign req_fifo[0] = (req_fifo_full) ? req_fifo_r : imem_addr;
121
 
122
`else // SCR1_IMEM_AHB_OUT_BP
123
always_comb begin
124
    req_fifo_up      = 1'b0;
125
    req_fifo_cnt_new = req_fifo_cnt;
126
    req_fifo_new     = req_fifo;
127
    case ({req_fifo_rd, req_fifo_wr})
128
        2'b00 : begin
129
            // nothing todo
130
        end
131
        2'b01: begin
132
            // FIFO write
133
            req_fifo_up = 1'b1;
134
            req_fifo_new[req_fifo_cnt].haddr  = imem_addr;
135
            req_fifo_cnt_new = req_fifo_cnt + 1'b1;
136
        end
137
        2'b10 : begin
138
            // FIFO read
139
            req_fifo_up     = 1'b1;
140
            req_fifo_new[0] = req_fifo_new[1];
141
            req_fifo_new[1].haddr  = 'x;
142
            req_fifo_cnt_new = req_fifo_cnt - 1'b1;
143
        end
144
        2'b11 : begin
145
            // Read and Write FIFO. It is possible only when fifo_cnt = 1
146
            req_fifo_up           = 1'b1;
147
            req_fifo_new[0].haddr = imem_addr;
148
        end
149
        default : begin
150
            req_fifo_up      = 'x;
151
            req_fifo_cnt_new = 'x;
152
            req_fifo_new     = 'x;
153
        end
154
    endcase
155
end
156
 
157
always_ff @(negedge rst_n, posedge clk) begin
158
    if (~rst_n) begin
159
        req_fifo_cnt <= '0;
160
    end else begin
161
        if (req_fifo_up) begin
162
            req_fifo_cnt <= req_fifo_cnt_new;
163
        end
164
    end
165
end
166
assign req_fifo_full  = (req_fifo_cnt == SCR1_FIFO_WIDTH);
167
assign req_fifo_empty = ~(|req_fifo_cnt);
168
 
169
always_ff @(posedge clk) begin
170
    if (req_fifo_up) begin
171
        req_fifo <= req_fifo_new;
172
    end
173
end
174
`endif // SCR1_IMEM_AHB_OUT_BP
175
 
176
//-------------------------------------------------------------------------------
177
// FSM
178
//-------------------------------------------------------------------------------
179
always_ff @(negedge rst_n, posedge clk) begin
180
    if (~rst_n) begin
181
        fsm <= SCR1_FSM_ADDR;
182
    end else begin
183
        case (fsm)
184
            SCR1_FSM_ADDR : begin
185
                if (hready) begin
186
                    fsm <= (req_fifo_empty) ? SCR1_FSM_ADDR : SCR1_FSM_DATA;
187
                end
188
            end
189
            SCR1_FSM_DATA : begin
190
                if (hready) begin
191
                    if (hresp == SCR1_HRESP_OKAY) begin
192
                        fsm <= (req_fifo_empty) ? SCR1_FSM_ADDR : SCR1_FSM_DATA;
193
                    end else begin
194
                        fsm <= SCR1_FSM_ADDR;
195
                    end
196
                end
197
            end
198
            default : begin
199
                fsm <= SCR1_FSM_ERR;
200
            end
201
        endcase
202
    end
203
end
204
 
205
always_comb begin
206
    req_fifo_rd = 1'b0;
207
    case (fsm)
208
        SCR1_FSM_ADDR : begin
209
            if (hready) begin
210
                req_fifo_rd = ~req_fifo_empty;
211
            end
212
        end
213
        SCR1_FSM_DATA : begin
214
            if (hready) begin
215
                req_fifo_rd = ~req_fifo_empty & (hresp == SCR1_HRESP_OKAY);
216
            end
217
        end
218
        default : begin
219
            req_fifo_rd = 1'bx;
220
        end
221
    endcase
222
end
223
 
224
//-------------------------------------------------------------------------------
225
// FIFO response
226
//-------------------------------------------------------------------------------
227
`ifdef SCR1_IMEM_AHB_IN_BP
228
assign resp_fifo_hready = (fsm == SCR1_FSM_DATA) ? hready : 1'b0;
229
assign resp_fifo.hresp  = hresp;
230
assign resp_fifo.hrdata = hrdata;
231
`else // SCR1_IMEM_AHB_IN_BP
232
always_ff @(negedge rst_n, posedge clk) begin
233
    if (~rst_n) begin
234
        resp_fifo_hready <= 1'b0;
235
    end else begin
236
        resp_fifo_hready <= (fsm == SCR1_FSM_DATA) ? hready : 1'b0;
237
    end
238
end
239
 
240
always_ff @(posedge clk) begin
241
    if (hready & (fsm == SCR1_FSM_DATA)) begin
242
        resp_fifo.hresp  <= hresp;
243
        resp_fifo.hrdata <= hrdata;
244
    end
245
end
246
`endif // SCR1_IMEM_AHB_IN_BP
247
 
248
//-------------------------------------------------------------------------------
249
// Interface to AHB
250
//-------------------------------------------------------------------------------
251
assign hprot[SCR1_HPROT_DATA]  = 1'b0;
252
assign hprot[SCR1_HPROT_PRV]   = 1'b0;
253
assign hprot[SCR1_HPROT_BUF]   = 1'b0;
254
assign hprot[SCR1_HPROT_CACHE] = 1'b0;
255
 
256
assign hburst       = SCR1_HBURST_SINGLE;
257
assign hsize        = SCR1_HSIZE_32B;
258
assign hmastlock    = 1'b0;
259
 
260
always_comb begin
261
    htrans = SCR1_HTRANS_IDLE;
262
    case (fsm)
263
        SCR1_FSM_ADDR : begin
264
            if (~req_fifo_empty) begin
265
                htrans = SCR1_HTRANS_NONSEQ;
266
            end
267
        end
268
        SCR1_FSM_DATA : begin
269
            if (hready) begin
270
                if (hresp == SCR1_HRESP_OKAY) begin
271
                    if (~req_fifo_empty) begin
272
                        htrans = SCR1_HTRANS_NONSEQ;
273
                    end
274
                end
275
            end
276
        end
277
        default : begin
278
            htrans = SCR1_HTRANS_ERR;
279
        end
280
    endcase
281
end
282
 
283
assign haddr  = req_fifo[0].haddr;
284
 
285
`ifdef SCR1_TRGT_SIMULATION
286
//-------------------------------------------------------------------------------
287
// Assertion
288
//-------------------------------------------------------------------------------
289
 
290
// Check Core interface
291
SCR1_SVA_IMEM_AHB_BRIDGE_REQ_XCHECK : assert property (
292
    @(negedge clk) disable iff (~rst_n)
293
    !$isunknown(imem_req)
294
    ) else $error("IMEM AHB bridge Error: imem_req has unknown values");
295
 
296
SCR1_IMEM_AHB_BRIDGE_ADDR_XCHECK : assert property (
297
    @(negedge clk) disable iff (~rst_n)
298
    imem_req |-> !$isunknown(imem_addr)
299
    ) else $error("IMEM AHB bridge Error: imem_addr has unknown values");
300
 
301
SCR1_IMEM_AHB_BRIDGE_ADDR_ALLIGN : assert property (
302
    @(negedge clk) disable iff (~rst_n)
303
    imem_req |-> (imem_addr[1:0] == '0)
304
    ) else $error("IMEM AHB bridge Error: imem_addr has unalign values");
305
 
306
// Check AHB interface
307
SCR1_IMEM_AHB_BRIDGE_HREADY_XCHECK : assert property (
308
    @(negedge clk) disable iff (~rst_n)
309
    !$isunknown(hready)
310
    ) else $error("IMEM AHB bridge Error: hready has unknown values");
311
 
312
SCR1_IMEM_AHB_BRIDGE_HRESP_XCHECK : assert property (
313
    @(negedge clk) disable iff (~rst_n)
314
    !$isunknown(hresp)
315
    ) else $error("IMEM AHB bridge Error: hresp has unknown values");
316
 
317
`endif // SCR1_TRGT_SIMULATION
318
 
319
endmodule : scr1_imem_ahb

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.