Verilog移位扩展结果?

Verilog移位扩展结果?,verilog,hdl,synthesis,flip-flop,Verilog,Hdl,Synthesis,Flip Flop,我们有以下代码行,我们知道,regF长度为16位,regD长度为8位,regE长度为8位,regC长度为3位,假设为无符号: regF <= regF + ( ( regD << regC ) & { 16{ regE [ regC ]} }) ; regF移位子表达式本身的宽度为8位;移位的位宽度始终是左操作数的位宽度(参见2005 LRM中的表5-22) 然而,在那之后,事情变得更加复杂。移位子表达式显示为&运算符的操作数。&表达式的位长度是两个操作数中最大的一个

我们有以下代码行,我们知道,
regF
长度为16位,
regD
长度为8位,
regE
长度为8位,
regC
长度为3位,假设为无符号:

regF <= regF + ( ( regD << regC ) & { 16{ regE [ regC ]} }) ;

regF移位子表达式本身的宽度为8位;移位的位宽度始终是左操作数的位宽度(参见2005 LRM中的表5-22)

然而,在那之后,事情变得更加复杂。移位子表达式显示为
&
运算符的操作数。
&
表达式的位长度是两个操作数中最大的一个操作数的位长度;在本例中,为16位

此子表达式现在显示为
+
表达式的操作数;此表达式的结果宽度也是
+
的两个操作数的最大宽度,也是16

我们现在有一项任务。从技术上讲,这不是操作数,但使用相同的规则;在这种情况下,LHS也是16位的,因此RHS的大小不受影响

我们现在知道,整个表达式大小是16位;此大小向下传播到操作数,但“自定”操作数除外。这里唯一的自定操作数是移位表达式(
regC
)的RHS,它没有扩展

表达式的符号性现在已确定。传播以同样的方式发生。这里的总体效果是,因为我们至少有一个无符号操作数,所以表达式是无符号的,并且所有操作数都强制为无符号。因此,在实际执行任何操作之前,所有(非自定)操作数都强制为无符号16位

因此,换句话说,移位子表达式实际上以16位移位结束,尽管乍一看似乎是8位移位。请注意,它不是16位的,因为
&
的RHS是16位的,而是因为整个大小调整过程-表达式的宽度向上传播-得到了16位的答案。如果分配给18位
reg
,而不是16位
regF
,则移位将扩展到18位

这是非常复杂和非直观的,至少如果你有任何主流语言的经验。2005年LRM第5.4节和第5.5节对此进行了解释(或多或少)。如果你需要任何建议,千万不要写这样的表达。防御性写作-将所有内容分解为单独的子表达式,然后组合子表达式