Alwaysblock1

Since digital circuits are composed of logic gates connected with wires, any circuit can be expressed as some combination of modules and assign statements. However, sometimes this is not the most convenient way to describe the circuit. Procedures (of which always blocks are one example) provide an alternative syntax for describing circuits.

For synthesizing hardware, two types of always blocks are relevant:

  • Combinational: always @(*)
  • Clocked: always @(posedge clk)

Combinational always blocks are equivalent to assign statements, thus there is always a way to express a combinational circuit both ways. The choice between which to use is mainly an issue of which syntax is more convenient. The syntax for code inside a procedural block is different from code that is outside. Procedural blocks have a richer set of statements (e.g., if-then, case), cannot contain continuous assignments*, but also introduces many new non-intuitive ways of making errors. (*Procedural continuous assignments do exist, but are somewhat different from continuous assignments, and are not synthesizable.)

For example, the assign and combinational always block describe the same circuit. Both create the same blob of combinational logic. Both will recompute the output whenever any of the inputs (right side) changes value.

assign out1 = a & b | c ^ d;

always @(*) out2 = a & b | c ^ d;

由于数字电路是由用导线连接的逻辑门组成的,因此任何电路都可以表示为模块和赋值语句的某种组合。然而,有时这并不是描述电路的最方便的方法。过程(其中块始终是一个示例)为描述电路提供了另一种语法。

对于合成硬件,有两种类型的始终块是相关的:

组合:总是@(*)
时钟:始终@(posedge clk)
组合块总是等价于赋值语句,因此总有一种方法可以双向表示组合电路。选择使用哪种语法主要是哪种语法更方便的问题。过程块内的代码语法与外部的代码不同。程序块具有更丰富的语句集(例如if-then、case),不能包含连续赋值*,但也引入了许多新的非直观的错误方式。(*程序性连续作业确实存在,但与连续作业有些不同,并且不可合成。)

例如,分配和组合总是块描述同一电路。两者都创建了相同的组合逻辑块。每当任何输入(右侧)改变值时,两者都会重新计算输出。

For combinational always blocks, always use a sensitivity list of (*). Explicitly listing out the signals is error-prone (if you miss one), and is ignored for hardware synthesis. If you explicitly specify the sensitivity list and miss a signal, the synthesized hardware will still behave as though (*) was specified, but the simulation will not and not match the hardware's behaviour. (In SystemVerilog, use always_comb.)

A note on wire vs. reg: The left-hand-side of an assign statement must be a net type (e.g., wire), while the left-hand-side of a procedural assignment (in an always block) must be a variable type (e.g., reg). These types (wire vs. reg) have nothing to do with what hardware is synthesized, and is just syntax left over from Verilog's use as a hardware simulation language.

// synthesis verilog_input_version verilog_2001
module top_module(
    input a, 
    input b,
    output wire out_assign,
    output reg out_alwaysblock
);
  
assign out_assign = a&b;
always @(*)begin
    out_alwaysblock = a&b;
    end
endmodule

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值