ブロックと非ブロックの割り当て
29537 ワード
無双兄貴のブログを見て
http://www.cnblogs.com/oomusou/archive/2010/07/30/blocking_vs_nonblocking.html
自分の考えを少し書き留める
まず
こんな風に変えたら?またいくつかreg
RTLレベル
2つのブロック賦値を1つのalwaysに入れると、以下に示すようにregが1つだけ統合されます.
2つの非ブロック付与値を1つのalwaysに変更すると、以下に示すように2つのregが統合されます.
特権同志のhttp://blog.ednchina.com/ilove314/141803/message.aspxを見てみましょう
このコードは、1クロック周期で13パスのパルス信号がハイレベルの個数を算出することを意図している.
普通の人はこの任務をfor循環に任せるのが適当だと感じますが、for循環はこの任務を完成することができますか?
シミュレーションの結果,この方法はだめであることが分かったが,もしブロックに変えたら?
今回でいいです...
理由:Always文で非ブロック付与<=を使用する場合、alwaysが終了してから左のレジスタに値を付与するため、最初のケースです.
テストコード:
http://www.cnblogs.com/oomusou/archive/2010/07/30/blocking_vs_nonblocking.html
自分の考えを少し書き留める
まず
module
nonblocking (
clk,
rst_n,
a_i,
b_i,
a_o,
b_o
);
input
clk;
input
rst_n;
input
a_i;
input
b_i;
output
a_o;
output
b_o;
reg
a;
reg
b;
assign
a_o
=
a;
assign
b_o
=
b;
always
@(
posedge
clk
or
negedge
rst_n)
begin
if
(
~
rst_n)
begin
a
<=
a_i;
b
<=
b_i;
end
else
begin
a
<=
b;
b
<=
a;
end
end
endmodule
こんな風に変えたら?またいくつかreg
module
div_2(
clk,
Din,
OUT
);
input
wire
clk;
input
wire
[
1
:
0
] Din;
output
reg
[
1
:
0
] OUT;
reg
[
1
:
0
] DFF_inst;
always
@(
posedge
clk)
begin
begin
DFF_inst[
1
:
0
]
=
Din[
1
:
0
];
end
end
always
@(
posedge
clk)
begin
begin
OUT[
1
:
0
]
=
DFF_inst[
1
:
0
];
end
end
endmodule
RTLレベル
2つのブロック賦値を1つのalwaysに入れると、以下に示すようにregが1つだけ統合されます.
1
always
@(
posedge
clk)
2
begin
3
DFF_inst[
1
:
0
]
=
Din[
1
:
0
];
4
OUT[
1
:
0
]
=
DFF_inst[
1
:
0
];
5
end
2つの非ブロック付与値を1つのalwaysに変更すると、以下に示すように2つのregが統合されます.
1
always
@(
posedge
clk)
2
begin
3
DFF_inst[
1
:
0
]
<=
Din[
1
:
0
];
4
OUT[
1
:
0
]
<=
DFF_inst[
1
:
0
];
5
end
特権同志のhttp://blog.ednchina.com/ilove314/141803/message.aspxを見てみましょう
このコードは、1クロック周期で13パスのパルス信号がハイレベルの個数を算出することを意図している.
普通の人はこの任務をfor循環に任せるのが適当だと感じますが、for循環はこの任務を完成することができますか?
1
module
test(clk,rst_n,data,numout);
2
input
clk;
3
4
input
rst_n;
5
6
input
[
12
:
0
] data;
//
the input data
7
8
output
[
15
:
0
] numout;
//
the total number of the input data
9
10
wire
[
15
:
0
] numout;
11
12
reg
[
3
:
0
] i;
13
14
reg
[
15
:
0
] num;
15
16
always
@ (
posedge
clk)
begin
17
if
(
!
rst_n)
begin
18
num
<=
0
;
19
end
20
else
begin
21
for
(i
=
0
;i
<
13
;i
=
i
+
1
'
b1) begin //use for to number
22
if
(data[i]) num
<=
num
+
1
'
b1;end
23
end
24
25
end
26
27
assign
numout
=
num;
28
29
endmodule
30
31
シミュレーションの結果,この方法はだめであることが分かったが,もしブロックに変えたら?
1
module
test(clk,rst_n,data,numout);
2
input
clk;
3
4
input
rst_n;
5
6
input
[
12
:
0
] data;
//
the input data
7
8
output
[
15
:
0
] numout;
//
the total number of the input data
9
10
wire
[
15
:
0
] numout;
11
12
reg
[
3
:
0
] i;
13
14
reg
[
15
:
0
] num;
15
16
always
@ (
posedge
clk)
begin
17
if
(
!
rst_n)
begin
18
num
=
0
;
19
end
20
else
begin
21
for
(i
=
0
;i
<
13
;i
=
i
+
1
'
b1) begin //use for to number
22
if
(data[i]) num
=
num
+
1
'
b1;end
23
end
24
25
end
26
27
assign
numout
=
num;
28
29
endmodule
30
31
今回でいいです...
理由:Always文で非ブロック付与<=を使用する場合、alwaysが終了してから左のレジスタに値を付与するため、最初のケースです.
テストコード:
`timescale 1ns/1ns
module test_tb();
reg clk;
reg rst_n;
reg [12:0] data;
wire[15:0] numout;
test U1
(
.clk(clk),
.rst_n(rst_n),
.data(data),
.numout(numout)
);
initial
begin
clk=0;
rst_n=0;
#3 rst_n=1;
data=13'b0101010110101;
#40 data=13'b1111000000111;
#40 data=13'b0000000000000;
end
always #10 clk=~clk;
endmodule