日本黄色一级经典视频|伊人久久精品视频|亚洲黄色色周成人视频九九九|av免费网址黄色小短片|黄色Av无码亚洲成年人|亚洲1区2区3区无码|真人黄片免费观看|无码一级小说欧美日免费三级|日韩中文字幕91在线看|精品久久久无码中文字幕边打电话

當前位置:首頁 > > ZYNQ
		


內容

FIFO緩存是介于兩個子系統(tǒng)之間的彈性存儲器,其概念圖如圖1所示。它有兩個控制信號,wr和rd,用于讀操作和寫操作。當wr被插入時,輸入的數(shù)據(jù)被寫入緩存,此時讀操作被忽視。FIFO緩存的head一般情況下總是有效的,因此可在任意時間被讀取。rd信號實際上就像“remove”信號;當其被插入的時候,F(xiàn)IFO緩存的第一個項(即head)被移除,下一個項變?yōu)榭捎庙棥?

圖1 FIFO緩存的概念框圖

在許多應用中,F(xiàn)IFO緩存是一種臨界組件,其實現(xiàn)的優(yōu)化相當復雜。在本節(jié)中,我們介紹一種簡單的、真實的基于循環(huán)序列設計的FIFO緩存。更有效的、基于指定器件實現(xiàn)的FIFO緩存可在Altera或Xilinx的相關手冊中找到。

基于循環(huán)隊列的實現(xiàn)

一種實現(xiàn)FIFO緩存的方法是給寄存器文件添加一個控制電路。寄存器文件通過兩個指針像循環(huán)隊列一樣來排列寄存器。寫指針(write poniter)指向隊列的頭(head);讀指針(read poniter)指向隊列的尾(tail)。每次讀操作或寫操作,指針都會前進一個位置。8-字循環(huán)隊列的操作如圖2所示。

圖2 基于循環(huán)隊列的FIFO緩存

FIFO緩存通常包括兩個標志信號,full和empty,相應地來指示FIFO滿(即不可寫)或FIFO空(即不可讀)。這兩種情況發(fā)生在讀指針和寫指針相等的時候,如圖2(a)、(f)和(i)所示的情況??刂破髯铍y的設計任務是獲取一種分辨這兩種情形的機制。一種方案是使用觸發(fā)器來跟蹤empty和full標志。當系統(tǒng)被初始化時,觸發(fā)器被設置為1和0;然后在每一個時鐘周期根據(jù)wr和rd的值來修改。

代碼 FIFO緩存

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

modulefifo

#(

parameterB=8,// number of bits in a word

W=3// number of address bits

)

(

// global clock and aysn reset

inputclk,

inputrst_n,

// fifo interface

//  fifo control signnal

inputrd,

inputwr,

//  fifo status signal

outputempty,

outputfull,

// fifo data bus

input[B-1:0] w_data,

output[B-1:0] r_data

);


// signal declaration

reg[B-1:0] array_reg [2**W-1:0];// register array

reg[W-1:0] w_ptr_reg, w_ptr_next, w_ptr_succ;

reg[W-1:0] r_ptr_reg, r_ptr_next, r_ptr_succ;

regfull_reg, empty_reg, full_next, empty_next;

wirewr_en;


// body

// register file write operation

always@(posedgeclk)

if(wr_en)

array_reg[w_ptr_reg] <= w_data;

// register file read operation

assignr_data = array_reg[r_ptr_reg];

// write enabled only when FIFO is not full

assignwr_en = wr & ~full_reg;


// fifo control logic

// register for read and write pointers

always@(posedgeclk,negedgerst_n)

if(!rst_n)

begin

w_ptr_reg <= 0;

r_ptr_reg <= 0;

full_reg <=1'b0;

empty_reg <=1'b1;

end

else

begin

w_ptr_reg <= w_ptr_next;

r_ptr_reg <= r_ptr_next;

full_reg <= full_next;

empty_reg <= empty_next;

end


// next-state logic for read and write pointers

always@*

begin

// successive pointer values

w_ptr_succ = w_ptr_reg + 1;

r_ptr_succ = r_ptr_reg + 1;

// default: keep old values

w_ptr_next = w_ptr_reg;

r_ptr_next = r_ptr_reg;

full_next = full_reg;

empty_next = empty_reg;

case({wr, rd})

// 2'b00:  no op

2'b01:// read

if(~empty_reg)// not empty

begin

r_ptr_next = r_ptr_succ;

full_next =1'b0;

if(r_ptr_succ==w_ptr_reg)

empty_next =1'b1;

end

2'b10:// write

if(~full_reg)// not full

begin

w_ptr_next = w_ptr_succ;

empty_next =1'b0;

if(w_ptr_succ==r_ptr_reg)

full_next =1'b1;

end

2'b11:// write and read

begin

w_ptr_next = w_ptr_succ;

r_ptr_next = r_ptr_succ;

end

endcase

end


// output

assignfull = full_reg;

assignempty = empty_reg;


endmodule

代碼被分為寄存器文件和FIFO控制器兩部分??刂破饔蓛蓚€指針和兩個標志觸發(fā)器組成,它們的次態(tài)邏輯會檢測wr和rd信號,以采取相應的動作。舉例說,在“10”條件下,即暗示只發(fā)生寫操作。先檢查標志觸發(fā)器,以確保緩存不為滿。如果滿足條件,我們將寫指針前進一位,并清除空標志。再多存儲一個字(偏移地址為1所對應的數(shù)據(jù))可能使得FIFO緩存滿,即新的寫指針趕上了讀指針,我們使用w_ptr_succ==r_ptr_reg表達式來描述這一情況。

根據(jù)圖2,我寫了下面的testbench,其RTL仿真結果與圖2一致。

代碼 FIFO緩存的testbench

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

`timescale1ns/1ns


modulefifo_tb;

localparam T=20;// clock period

// global clock and asyn reset

regclk, rst_n;

// fifo interface

regrd, wr;

wireempty, full;

reg[7:0] w_data;

wire[7:0] r_data;


// fifo instantiation

fifo #(.B(8), .W(3)) fifo_inst

(

.clk(clk), .rst_n(rst_n),

.rd(rd), .wr(wr),

.empty(empty), .full(full),

.w_data(w_data), .r_data(r_data)

);



// clcok

always

begin

clk =1'b0;

#(T/2);

clk =1'b1;

#(T/2);

end



// reset

initial

begin

rst_n =1'b0;

#(T/2)

rst_n =1'b1;

end



// stimulus body

initial

begin

// initial input; empty

rd=0; wr=0; w_data=8'h00;

@(posedgerst_n);// wait to deassert rst_n

@(negedgeclk);// wait for a clock

// 1 write

wr=1; w_data=8'h11;

@(negedgeclk);// wait to assert wr

wr=0;

@(negedgeclk);// wait to deassert wr

// 3 writes

wr=1;

repeat(3)

begin

w_data=w_data+8'h11;

@(negedgeclk);

end

wr=0;

@(negedgeclk);

// 1 read

rd=1;

@(negedgeclk);// wait to assert rd

rd=0;

@(negedgeclk)// wait to deassert rd

// 4 writes

wr=1;

repeat(4)

begin

w_data=w_data+8'h11;

@(negedgeclk);

end

wr=0;

@(negedgeclk);

// 1 write; full

wr=1; w_data=8'hAA;

@(negedgeclk);

wr=0;

@(negedgeclk);

// 2 reads

rd=1;

repeat(2) @(negedgeclk);

rd=0;

@(negedgeclk);

// 5 reads

rd=1;

repeat(5) @(negedgeclk);

rd=0;

@(negedgeclk);

// 1 read; empty

rd=1;

@(negedgeclk);

rd=0;

@(negedgeclk);

$stop;

end


endmodule

圖3 RTL級仿真波形

參考

1 Pong P. Chu.FPGA Prototyping By Verilog Examples: Xilinx Spartan-3 Version.Wiley


本站聲明: 本文章由作者或相關機構授權發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點,本站亦不保證或承諾內容真實性等。需要轉載請聯(lián)系該專欄作者,如若文章內容侵犯您的權益,請及時聯(lián)系本站刪除。
關閉