Verilog -- 有符号与无符号运算

https://blog.csdn.net/vivid117/article/details/101427302
http://wscentity.lofter.com/post/1d00edbd_6476453

无符号乘法和加法

对于无符号的乘法和加法,没有什么好说的,就是直接用‘*’和‘+’。

有符号乘法和加法

有符号和无符号运算

verilog里如果有符号数和无符号数做运算,会强制当作无符号运算
这就涉及verilog处理运算时的法则:
例如 c = a + b; 其中a和b都是四位数,c是五位。在计算时,verilog会将a和b都扩展到5位,然后再做加法,而如果a和b中有无符号数,则位宽扩展就按照无符号数来,也就是高位补0。所以如果a和b中既有无符号又有有符号,结果就不正确了。
解决方法是用 \$signed()来修饰:c = a + $signed(b)这样在c = a + b,这个运算开始的扩位就会按照有符号数的方式进行扩位,在高位补符号位,加法得出的结果就是a、b视为有符号数的结果。
例子:

||| |||
||| |||

可见结果是不是signed倒是无所谓的。但是最好还是加上。

有符号数乘法

例如有符号数[3:0]a * [3:0]b. 其中a=-5,b=7。a用补码表示为1011,b用补码表示是0111,对于这个例子,乘法过程如下:


上面的结果101_1101,补码是1100011 = -35
其实乘法器就是由加法组成,所以b中的每一位跟a做乘法(异或)之后把部分积累加时,仍然需要遵从加法的原则,扩展符号位直到达到输出位宽,然后再加。
所以有符号乘法跟无符号乘法的区别就在这,无符号乘法不需要考虑符号位扩展问题,而有符号乘法在累加部分积的时候需要做符号位扩展。

猜你喜欢

转载自www.cnblogs.com/lyc-seu/p/12533226.html