add first peripheral set
[shakti-peripherals.git] / src / uncore / axi4 / AXI4_Types.bsv
1 /*
2 Copyright (c) 2013, IIT Madras
3 All rights reserved.
4
5 Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
6
7 * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
9 * Neither the name of IIT Madras nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
10
11 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
12 ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
13 */
14 // Copyright (c) 2017 Bluespec, Inc. All Rights Reserved
15
16 package AXI4_Types;
17
18 // ================================================================
19 // Facilities for ARM AXI4-Lite, consisting of 5 independent channels:
20 // Write Address, Write Data, Write Response, Read Address and Read Data
21
22 // Ref: ARM document:
23 // AMBA AXI and ACE Protocol Specification
24 // AXI3, AXI4, and AXI4-Lite
25 // ACE and ACE-Lite
26 // ARM IHI 0022E (ID022613)
27 // Issue E, 22 Feb 2013
28
29 // See export list below
30
31 // ================================================================
32 // Exports
33
34 export
35
36 // RTL-level interfaces (signals/buses)
37 AXI4_Master_IFC (..),
38 AXI4_Slave_IFC (..),
39
40 // Dummy slave that accepts no requests and generates no response
41 // Used for tying-off unused slave interfaces on fabrics.
42 dummy_AXI4_Slave_ifc,
43
44 // Higher-level enums and structs for the 5 AXI4 channel payloads
45 AXI4_Resp (..),
46
47 AXI4_Wr_Addr (..),
48 AXI4_Wr_Data (..),
49 AXI4_Wr_Resp (..),
50 AXI4_Rd_Addr (..),
51 AXI4_Rd_Data (..),
52
53 // Higher-level FIFO-like interfaces for the 5 AXI4 channels,
54 AXI4_Master_Xactor_IFC (..),
55 AXI4_Slave_Xactor_IFC (..),
56
57 // Transactors from RTL-level interfacecs to FIFO-like interfaces.
58 mkAXI4_Master_Xactor,
59 mkAXI4_Slave_Xactor;
60
61 // ================================================================
62 // BSV library imports
63
64 import FIFOF :: *;
65 import Connectable :: *;
66
67 // ----------------
68 // BSV additional libs
69
70 import Semi_FIFOF :: *;
71
72 // ****************************************************************
73 // ****************************************************************
74 // Section: RTL-level interfaces
75 // ****************************************************************
76 // ****************************************************************
77
78 // ================================================================
79 // These are the signal-level interfaces for an AXI4-Lite master.
80 // The (*..*) attributes ensure that when bsc compiles this to Verilog,
81 // we get exactly the signals specified in the ARM spec.
82
83 interface AXI4_Master_IFC #(numeric type wd_addr,
84 numeric type wd_data,
85 numeric type wd_user);
86 // Wr Addr channel
87 (* always_ready, result="awvalid" *) method Bool m_awvalid; // out
88 (* always_ready, result="awaddr" *) method Bit #(wd_addr) m_awaddr; // out
89 (* always_ready, result="awuser" *) method Bit #(wd_user) m_awuser; // out
90 (* always_ready, result="awlen" *) method Bit #(8) m_awlen; // out
91 (* always_ready, result="awsize" *) method Bit #(3) m_awsize; // out
92 (* always_ready, result="awburst" *) method Bit #(2) m_awburst; // out
93 (* always_ready, result="awid" *) method Bit #(4) m_awid; // out
94 (* always_ready, always_enabled *) method Action m_awready ((* port="awready" *) Bool awready); // in
95
96 // Wr Data channel
97 (* always_ready, result="wvalid" *) method Bool m_wvalid; // out
98 (* always_ready, result="wdata" *) method Bit #(wd_data) m_wdata; // out
99 (* always_ready, result="wstrb" *) method Bit #(TDiv #(wd_data, 8)) m_wstrb; // out
100 (* always_ready, result="wlast" *) method Bool m_wlast; // out
101 (* always_ready, result="wid" *) method Bit #(4) m_wid; // out
102 (* always_ready, always_enabled *) method Action m_wready ((* port="wready" *) Bool wready); // in
103
104 // Wr Response channel
105 (* always_ready, always_enabled *)
106 method Action m_bvalid ((* port="bvalid" *) Bool bvalid, // in
107 (* port="bresp" *) Bit #(2) bresp, // in
108 (* port="buser" *) Bit #(wd_user) buser, // in
109 (* port="bid"*) Bit#(4) bid); // in
110 (* always_ready, result="bready" *)
111 method Bool m_bready; // out
112
113 // Rd Addr channel
114 (* always_ready, result="arvalid" *) method Bool m_arvalid; // out
115 (* always_ready, result="araddr" *) method Bit #(wd_addr) m_araddr; // out
116 (* always_ready, result="aruser" *) method Bit #(wd_user) m_aruser; // out
117 (* always_ready, result="arlen" *) method Bit #(8) m_arlen; // out
118 (* always_ready, result="arsize" *) method Bit #(3) m_arsize; // out
119 (* always_ready, result="arburst" *) method Bit #(2) m_arburst; // out
120 (* always_ready, result="arid" *) method Bit #(4) m_arid; // out
121 (* always_ready, always_enabled *) method Action m_arready ((* port="arready" *) Bool arready); // in
122
123 // Rd Data channel
124 (* always_ready, always_enabled *)
125 method Action m_rvalid ((* port="rvalid" *) Bool rvalid, // in
126 (* port="rresp" *) Bit #(2) rresp, // in
127 (* port="rdata" *) Bit #(wd_data) rdata, // in
128 (* port="rlast" *) Bool rlast, // in
129 (* port="ruser" *) Bit #(wd_user) ruser, // in
130 (* port="rid" *) Bit #(4) rid); // in
131 (* always_ready, result="rready" *)
132 method Bool m_rready; // out
133 endinterface: AXI4_Master_IFC
134
135 // ================================================================
136 // These are the signal-level interfaces for an AXI4-Lite slave.
137 // The (*..*) attributes ensure that when bsc compiles this to Verilog,
138 // we get exactly the signals specified in the ARM spec.
139
140 interface AXI4_Slave_IFC #(numeric type wd_addr,
141 numeric type wd_data,
142 numeric type wd_user);
143 // Wr Addr channel
144 (* always_ready, always_enabled *)
145 method Action m_awvalid ((* port="awvalid" *) Bool awvalid, // in
146 (* port="awaddr" *) Bit #(wd_addr) awaddr, // in
147 (* port="awsize" *) Bit #(3) awsize, // in
148 (* port="awuser" *) Bit #(wd_user) awuser, // in
149 (* port="awlen" *) Bit #(8) awlen, // in
150 (* port="awburst" *) Bit #(2) awburst, // in
151 (* port="awid" *) Bit#(4) awid);
152 (* always_ready, result="awready" *)
153 method Bool m_awready; // out
154
155 // Wr Data channel
156 (* always_ready, always_enabled *)
157 method Action m_wvalid ((* port="wvalid" *) Bool wvalid, // in
158 (* port="wdata" *) Bit #(wd_data) wdata, // in
159 (* port="wstrb" *) Bit #(TDiv #(wd_data,8)) wstrb, // in
160 (* port="wlast" *) Bool wlast,
161 (* port="wid" *) Bit#(4) wid);
162 (* always_ready, result="wready" *)
163 method Bool m_wready; // out
164
165 // Wr Response channel
166 (* always_ready, result="bvalid" *) method Bool m_bvalid; // out
167 (* always_ready, result="bresp" *) method Bit #(2) m_bresp; // out
168 (* always_ready, result="buser" *) method Bit #(wd_user) m_buser; // out
169 (* always_ready, result="bid" *) method Bit #(4) m_bid; // out
170 (* always_ready, always_enabled *) method Action m_bready ((* port="bready" *) Bool bready); // in
171
172 // Rd Addr channel
173 (* always_ready, always_enabled *)
174 method Action m_arvalid ((* port="arvalid" *) Bool arvalid, // in
175 (* port="araddr" *) Bit #(wd_addr) araddr, // in
176 (* port="arsize" *) Bit #(3) arsize, // in
177 (* port="aruser" *) Bit #(wd_user) aruser, // in
178 (* port="arlen" *) Bit #(8) arlen, // in
179 (* port="arburst" *) Bit #(2) arburst, // in
180 (* port="arid" *) Bit#(4) arid
181 );
182 (* always_ready, result="arready" *)
183 method Bool m_arready; // out
184
185 // Rd Data channel
186 (* always_ready, result="rvalid" *) method Bool m_rvalid; // out
187 (* always_ready, result="rresp" *) method Bit #(2) m_rresp; // out
188 (* always_ready, result="rdata" *) method Bit #(wd_data) m_rdata; // out
189 (* always_ready, result="rlast" *) method Bool m_rlast; // out
190 (* always_ready, result="ruser" *) method Bit #(wd_user) m_ruser; // out
191 (* always_ready, result="rid" *) method Bit #(4) m_rid; // out
192 (* always_ready, always_enabled *) method Action m_rready ((* port="rready" *) Bool rready); // in
193 endinterface: AXI4_Slave_IFC
194
195 // ================================================================
196 // Connecting signal-level interfaces
197
198 instance Connectable #(AXI4_Master_IFC #(wd_addr, wd_data, wd_user),
199 AXI4_Slave_IFC #(wd_addr, wd_data, wd_user));
200
201 module mkConnection #(AXI4_Master_IFC #(wd_addr, wd_data, wd_user) axim,
202 AXI4_Slave_IFC #(wd_addr, wd_data, wd_user) axis)
203 (Empty);
204
205 (* fire_when_enabled, no_implicit_conditions *)
206 rule rl_wr_addr_channel;
207 axis.m_awvalid (axim.m_awvalid, axim.m_awaddr, axim.m_awsize, axim.m_awuser, axim.m_awlen, axim.m_awburst, axim.m_awid);
208 axim.m_awready (axis.m_awready);
209 endrule
210
211 (* fire_when_enabled, no_implicit_conditions *)
212 rule rl_wr_data_channel;
213 axis.m_wvalid (axim.m_wvalid, axim.m_wdata, axim.m_wstrb, axim.m_wlast, axim.m_wid);
214 axim.m_wready (axis.m_wready);
215 endrule
216
217 (* fire_when_enabled, no_implicit_conditions *)
218 rule rl_wr_response_channel;
219 axim.m_bvalid (axis.m_bvalid, axis.m_bresp, axis.m_buser, axis.m_bid);
220 axis.m_bready (axim.m_bready);
221 endrule
222
223 (* fire_when_enabled, no_implicit_conditions *)
224 rule rl_rd_addr_channel;
225 axis.m_arvalid (axim.m_arvalid, axim.m_araddr, axim.m_arsize, axim.m_aruser, axim.m_arlen, axim.m_arburst, axim.m_arid);
226 axim.m_arready (axis.m_arready);
227 endrule
228
229 (* fire_when_enabled, no_implicit_conditions *)
230 rule rl_rd_data_channel;
231 axim.m_rvalid (axis.m_rvalid, axis.m_rresp, axis.m_rdata, axis.m_rlast, axis.m_ruser, axis.m_rid);
232 axis.m_rready (axim.m_rready);
233 endrule
234 endmodule
235 endinstance
236
237 // ================================================================
238 // AXI4-Lite dummy slave: never accepts requests, never produces responses
239
240 AXI4_Slave_IFC #(wd_addr, wd_data, wd_user)
241 dummy_AXI4_Slave_ifc = interface AXI4_Slave_IFC
242 // Wr Addr channel
243 method Action m_awvalid (Bool awvalid,
244 Bit #(wd_addr) awaddr,
245 Bit #(3) awsize,
246 Bit #(wd_user) awuser,
247 Bit #(8) awlen,
248 Bit #(2) awburst,
249 Bit #(4) awid);
250 noAction;
251 endmethod
252
253 method Bool m_awready;
254 return False;
255 endmethod
256
257 // Wr Data channel
258 method Action m_wvalid (Bool wvalid,
259 Bit #(wd_data) wdata,
260 Bit #(TDiv #(wd_data,8)) wstrb,
261 Bool wlast,
262 Bit#(4) wid);
263 noAction;
264 endmethod
265
266 method Bool m_wready;
267 return False;
268 endmethod
269
270 // Wr Response channel
271 method Bool m_bvalid;
272 return False;
273 endmethod
274
275 method Bit #(2) m_bresp;
276 return 0;
277 endmethod
278
279 method Bit #(wd_user) m_buser;
280 return ?;
281 endmethod
282 method Bit #(4) m_bid;
283 return ?;
284 endmethod
285
286 method Action m_bready (Bool bready);
287 noAction;
288 endmethod
289
290 // Rd Addr channel
291 method Action m_arvalid (Bool arvalid,
292 Bit #(wd_addr) araddr,
293 Bit#(3) arsize,
294 Bit #(wd_user) aruser,
295 Bit#(8) arlen,
296 Bit#(2) arburst,
297 Bit#(4) arid);
298 noAction;
299 endmethod
300
301 method Bool m_arready;
302 return False;
303 endmethod
304
305 // Rd Data channel
306 method Bool m_rvalid;
307 return False;
308 endmethod
309
310 method Bit #(2) m_rresp;
311 return 0;
312 endmethod
313
314 method Bit #(wd_data) m_rdata;
315 return 0;
316 endmethod
317 method Bool m_rlast;
318 return ?;
319 endmethod
320
321 method Bit #(wd_user) m_ruser;
322 return ?;
323 endmethod
324
325 method Action m_rready (Bool rready);
326 noAction;
327 endmethod
328 endinterface;
329
330 // ****************************************************************
331 // ****************************************************************
332 // Section: Higher-level FIFO-like interfaces and transactors
333 // ****************************************************************
334 // ****************************************************************
335
336 // ================================================================
337 // Higher-level types for payloads (rather than just bits)
338
339 typedef enum { AXI4_OKAY, AXI4_EXOKAY, AXI4_SLVERR, AXI4_DECERR } AXI4_Resp
340 deriving (Bits, Eq, FShow);
341
342 // Write Address channel
343
344 typedef struct {
345 Bit #(wd_addr) awaddr;
346 Bit #(wd_user) awuser;
347 Bit#(8) awlen;
348 Bit#(3) awsize;
349 Bit#(2) awburst;
350 Bit#(4) awid;
351 } AXI4_Wr_Addr #(numeric type wd_addr, numeric type wd_user)
352 deriving (Bits, FShow);
353
354 // Write Data channel
355
356 typedef struct {
357 Bit #(wd_data) wdata;
358 Bit #(TDiv #(wd_data, 8)) wstrb;
359 Bit#(4) wid;
360 Bool wlast;
361 } AXI4_Wr_Data #(numeric type wd_data)
362 deriving (Bits, FShow);
363
364 // Write Response channel
365
366 typedef struct {
367 AXI4_Resp bresp;
368 Bit #(wd_user) buser;
369 Bit#(4) bid;
370 } AXI4_Wr_Resp #(numeric type wd_user)
371 deriving (Bits, FShow);
372
373 // Read Address channel
374
375 typedef struct {
376 Bit #(wd_addr) araddr;
377 Bit #(wd_user) aruser;
378 Bit#(3) arsize;
379 Bit#(8) arlen;
380 Bit#(2) arburst;
381 Bit#(4) arid;
382 } AXI4_Rd_Addr #(numeric type wd_addr, numeric type wd_user)
383 deriving (Bits, FShow);
384
385 // Read Data channel
386
387 typedef struct {
388 AXI4_Resp rresp;
389 Bit #(wd_data) rdata;
390 Bool rlast;
391 Bit #(wd_user) ruser;
392 Bit#(4) rid;
393 } AXI4_Rd_Data #(numeric type wd_data, numeric type wd_user)
394 deriving (Bits, FShow);
395
396 // ================================================================
397 // Master transactor interface
398
399 interface AXI4_Master_Xactor_IFC #(numeric type wd_addr,
400 numeric type wd_data,
401 numeric type wd_user);
402 method Action reset;
403
404 // AXI side
405 interface AXI4_Master_IFC #(wd_addr, wd_data, wd_user) axi_side;
406
407 // FIFOF side
408 interface FIFOF_I #(AXI4_Wr_Addr #(wd_addr, wd_user)) i_wr_addr;
409 interface FIFOF_I #(AXI4_Wr_Data #(wd_data)) i_wr_data;
410 interface FIFOF_O #(AXI4_Wr_Resp #(wd_user)) o_wr_resp;
411
412 interface FIFOF_I #(AXI4_Rd_Addr #(wd_addr, wd_user)) i_rd_addr;
413 interface FIFOF_O #(AXI4_Rd_Data #(wd_data, wd_user)) o_rd_data;
414 endinterface: AXI4_Master_Xactor_IFC
415
416 // ----------------------------------------------------------------
417 // Master transactor
418
419 module mkAXI4_Master_Xactor (AXI4_Master_Xactor_IFC #(wd_addr, wd_data, wd_user));
420
421 Bool unguarded = True;
422 Bool guarded = False;
423
424 // These FIFOs are guarded on BSV side, unguarded on AXI side
425 FIFOF #(AXI4_Wr_Addr #(wd_addr, wd_user)) f_wr_addr <- mkGFIFOF (guarded, unguarded);
426 FIFOF #(AXI4_Wr_Data #(wd_data)) f_wr_data <- mkGFIFOF (guarded, unguarded);
427 FIFOF #(AXI4_Wr_Resp #(wd_user)) f_wr_resp <- mkGFIFOF (unguarded, guarded);
428
429 FIFOF #(AXI4_Rd_Addr #(wd_addr, wd_user)) f_rd_addr <- mkGFIFOF (guarded, unguarded);
430 FIFOF #(AXI4_Rd_Data #(wd_data, wd_user)) f_rd_data <- mkGFIFOF (unguarded, guarded);
431
432 // ----------------------------------------------------------------
433 // INTERFACE
434
435 method Action reset;
436 f_wr_addr.clear;
437 f_wr_data.clear;
438 f_wr_resp.clear;
439 f_rd_addr.clear;
440 f_rd_data.clear;
441 endmethod
442
443 // AXI side
444 interface axi_side = interface AXI4_Master_IFC;
445 // Wr Addr channel
446 method Bool m_awvalid = f_wr_addr.notEmpty;
447 method Bit #(wd_addr) m_awaddr = f_wr_addr.first.awaddr;
448 method Bit #(wd_user) m_awuser = f_wr_addr.first.awuser;
449 method Bit #(8) m_awlen = f_wr_addr.first.awlen;
450 method Bit #(3) m_awsize = f_wr_addr.first.awsize;
451 method Bit #(2) m_awburst = f_wr_addr.first.awburst;
452 method Bit #(4) m_awid = f_wr_addr.first.awid;
453 method Action m_awready (Bool awready);
454 if (f_wr_addr.notEmpty && awready) f_wr_addr.deq;
455 endmethod
456
457 // Wr Data channel
458 method Bool m_wvalid = f_wr_data.notEmpty;
459 method Bit #(wd_data) m_wdata = f_wr_data.first.wdata;
460 method Bit #(TDiv #(wd_data, 8)) m_wstrb = f_wr_data.first.wstrb;
461 method Bool m_wlast = f_wr_data.first.wlast;
462 method Bit#(4) m_wid = f_wr_data.first.wid;
463 method Action m_wready (Bool wready);
464 if (f_wr_data.notEmpty && wready) f_wr_data.deq;
465 endmethod
466
467 // Wr Response channel
468 method Action m_bvalid (Bool bvalid, Bit #(2) bresp, Bit #(wd_user) buser, Bit#(4) bid);
469 if (bvalid && f_wr_resp.notFull)
470 f_wr_resp.enq (AXI4_Wr_Resp {bresp: unpack (bresp), buser: buser, bid:bid});
471 endmethod
472
473 method Bool m_bready;
474 return f_wr_resp.notFull;
475 endmethod
476
477 // Rd Addr channel
478 method Bool m_arvalid = f_rd_addr.notEmpty;
479 method Bit #(wd_addr) m_araddr = f_rd_addr.first.araddr;
480 method Bit #(wd_user) m_aruser = f_rd_addr.first.aruser;
481 method Bit #(3) m_arsize = f_rd_addr.first.arsize;
482 method Bit #(8) m_arlen = f_rd_addr.first.arlen;
483 method Bit #(2) m_arburst = f_rd_addr.first.arburst;
484 method Bit #(4) m_arid = f_rd_addr.first.arid;
485 method Action m_arready (Bool arready);
486 if (f_rd_addr.notEmpty && arready) f_rd_addr.deq;
487 endmethod
488
489 // Rd Data channel
490 method Action m_rvalid (Bool rvalid,
491 Bit #(2) rresp,
492 Bit #(wd_data) rdata,
493 Bool rlast,
494 Bit #(wd_user) ruser,
495 Bit#(4) rid);
496 if (rvalid && f_rd_data.notFull)
497 f_rd_data.enq (AXI4_Rd_Data {rresp: unpack (rresp),
498 rdata: rdata,
499 rlast: rlast,
500 ruser: ruser,
501 rid: rid});
502 endmethod
503
504 method Bool m_rready;
505 return f_rd_data.notFull;
506 endmethod
507
508 endinterface;
509
510 // FIFOF side
511 interface i_wr_addr = to_FIFOF_I (f_wr_addr);
512 interface i_wr_data = to_FIFOF_I (f_wr_data);
513 interface o_wr_resp = to_FIFOF_O (f_wr_resp);
514
515 interface i_rd_addr = to_FIFOF_I (f_rd_addr);
516 interface o_rd_data = to_FIFOF_O (f_rd_data);
517 endmodule: mkAXI4_Master_Xactor
518
519 // ================================================================
520 // Slave transactor interface
521
522 interface AXI4_Slave_Xactor_IFC #(numeric type wd_addr,
523 numeric type wd_data,
524 numeric type wd_user);
525 method Action reset;
526
527 // AXI side
528 interface AXI4_Slave_IFC #(wd_addr, wd_data, wd_user) axi_side;
529
530 // FIFOF side
531 interface FIFOF_O #(AXI4_Wr_Addr #(wd_addr, wd_user)) o_wr_addr;
532 interface FIFOF_O #(AXI4_Wr_Data #(wd_data)) o_wr_data;
533 interface FIFOF_I #(AXI4_Wr_Resp #(wd_user)) i_wr_resp;
534
535 interface FIFOF_O #(AXI4_Rd_Addr #(wd_addr, wd_user)) o_rd_addr;
536 interface FIFOF_I #(AXI4_Rd_Data #(wd_data, wd_user)) i_rd_data;
537 endinterface: AXI4_Slave_Xactor_IFC
538
539 // ----------------------------------------------------------------
540 // Slave transactor
541
542 module mkAXI4_Slave_Xactor (AXI4_Slave_Xactor_IFC #(wd_addr, wd_data, wd_user));
543
544 Bool unguarded = True;
545 Bool guarded = False;
546
547 // These FIFOs are guarded on BSV side, unguarded on AXI side
548 FIFOF #(AXI4_Wr_Addr #(wd_addr, wd_user)) f_wr_addr <- mkGFIFOF (unguarded, guarded);
549 FIFOF #(AXI4_Wr_Data #(wd_data)) f_wr_data <- mkGFIFOF (unguarded, guarded);
550 FIFOF #(AXI4_Wr_Resp #(wd_user)) f_wr_resp <- mkGFIFOF (guarded, unguarded);
551
552 FIFOF #(AXI4_Rd_Addr #(wd_addr, wd_user)) f_rd_addr <- mkGFIFOF (unguarded, guarded);
553 FIFOF #(AXI4_Rd_Data #(wd_data, wd_user)) f_rd_data <- mkGFIFOF (guarded, unguarded);
554
555 // ----------------------------------------------------------------
556 // INTERFACE
557
558 method Action reset;
559 f_wr_addr.clear;
560 f_wr_data.clear;
561 f_wr_resp.clear;
562 f_rd_addr.clear;
563 f_rd_data.clear;
564 endmethod
565
566 // AXI side
567 interface axi_side = interface AXI4_Slave_IFC;
568 // Wr Addr channel
569 method Action m_awvalid (Bool awvalid,
570 Bit #(wd_addr) awaddr,
571 Bit#(3) awsize,
572 Bit #(wd_user) awuser,
573 Bit#(8) awlen,
574 Bit#(2) awburst,
575 Bit#(4) awid);
576 if (awvalid && f_wr_addr.notFull)
577 f_wr_addr.enq (AXI4_Wr_Addr {awaddr: awaddr,
578 awsize:awsize,
579 awuser: awuser,
580 awlen:awlen,
581 awburst:awburst,
582 awid:awid});
583 endmethod
584
585 method Bool m_awready;
586 return f_wr_addr.notFull;
587 endmethod
588
589 // Wr Data channel
590 method Action m_wvalid (Bool wvalid,
591 Bit #(wd_data) wdata,
592 Bit #(TDiv #(wd_data, 8)) wstrb,
593 Bool wlast,
594 Bit#(4) wid);
595 if (wvalid && f_wr_data.notFull)
596 f_wr_data.enq (AXI4_Wr_Data {wdata: wdata, wstrb: wstrb, wlast:wlast, wid:wid});
597 endmethod
598
599 method Bool m_wready;
600 return f_wr_data.notFull;
601 endmethod
602
603 // Wr Response channel
604 method Bool m_bvalid = f_wr_resp.notEmpty;
605 method Bit #(2) m_bresp = pack (f_wr_resp.first.bresp);
606 method Bit #(wd_user) m_buser = f_wr_resp.first.buser;
607 method Bit #(4) m_bid = f_wr_resp.first.bid;
608 method Action m_bready (Bool bready);
609 if (bready && f_wr_resp.notEmpty)
610 f_wr_resp.deq;
611 endmethod
612
613 // Rd Addr channel
614 method Action m_arvalid (Bool arvalid,
615 Bit #(wd_addr) araddr,
616 Bit#(3) arsize,
617 Bit #(wd_user) aruser,
618 Bit#(8) arlen,
619 Bit#(2) arburst,
620 Bit#(4) arid);
621 if (arvalid && f_rd_addr.notFull)
622 f_rd_addr.enq (AXI4_Rd_Addr {araddr: araddr,
623 arsize: arsize,
624 aruser: aruser,
625 arlen : arlen,
626 arburst:arburst,
627 arid:arid});
628 endmethod
629
630 method Bool m_arready;
631 return f_rd_addr.notFull;
632 endmethod
633
634 // Rd Data channel
635 method Bool m_rvalid = f_rd_data.notEmpty;
636 method Bit #(2) m_rresp = pack (f_rd_data.first.rresp);
637 method Bit #(wd_data) m_rdata = f_rd_data.first.rdata;
638 method Bool m_rlast = f_rd_data.first.rlast;
639 method Bit #(wd_user) m_ruser = f_rd_data.first.ruser;
640 method Bit#(4) m_rid=f_rd_data.first.rid;
641 method Action m_rready (Bool rready);
642 if (rready && f_rd_data.notEmpty)
643 f_rd_data.deq;
644 endmethod
645 endinterface;
646
647 // FIFOF side
648 interface o_wr_addr = to_FIFOF_O (f_wr_addr);
649 interface o_wr_data = to_FIFOF_O (f_wr_data);
650 interface i_wr_resp = to_FIFOF_I (f_wr_resp);
651
652 interface o_rd_addr = to_FIFOF_O (f_rd_addr);
653 interface i_rd_data = to_FIFOF_I (f_rd_data);
654 endmodule: mkAXI4_Slave_Xactor
655
656 // ================================================================
657
658 endpackage