2 / 24 · 概念
位元寬度、符號延伸與溢位
使用數值範例區分解讀方式、延伸與縮窄。
單元可免費閱讀,註冊課程即可儲存學習進度。
區分位元樣式與它的意義
八位元樣式 1111_1101 可以代表無號 253,也可以代表二補數有號 -3。儲存的位元完全相同,但比較與延伸的方式不同。八位元有號數的範圍是 -128 到 127;無號數的範圍是 0 到 255。位元寬度決定能表示多少種樣式,而是否有號則決定其數值解讀方式。
將無號 253 移至十六位元時,應做零延伸。將 -3 做符號延伸時,重複原本的最高有效位元,得到 1111_1111_1111_1101。零延伸會把 -3 變成 253。在 SystemVerilog 中,計算前應明確訂定運算元型別與位元寬度;不要假設串接或部分選取會保留你原本想要的有號解讀。
logic [7:0] ua, ub;
logic [8:0] usum;
logic signed [7:0] sa, sb;
logic signed [8:0] sax, sbx, ssum;
assign usum = {1'b0, ua} + {1'b0, ub};
assign sax = {sa[7], sa};
assign sbx = {sb[7], sb};
assign ssum = sax + sbx;這裡兩個輸入都先擴為九位元再相加。無號 255+1 得到 256,最低八個位元則為零。有號 127+1 的數學結果同樣是 128,但縮窄為八位元有號數時會變成 -128。進位表示無號邊界;有號溢位表示有號邊界。同號運算元相加後,若結果符號改變,便表示有號溢位。-1 加 1 可能產生進位,卻沒有有號溢位。
中間結果的位元寬度也必須規劃。最大的無號八位元乘積是 65025,需要十六位元。四個無號八位元數的總和最大為 1020,需要十位元。若每個部分和都截斷為八位元,遺失的資訊無法靠更寬的最終暫存器恢復。
| 操作 | 寬位元結果 | 縮窄後的解讀 |
|---|---|---|
| 無號 255+1 | 256 | 0,伴隨進位 |
| 有號 127+1 | 128 | -128,伴隨溢位 |
| 有號 -3+2 | -1 | -1,沒有溢位 |
使用 Verilator 的 WIDTH 警告 調查非預期的尺寸變化。本課程的 Node 檢查執行的是數值模型,而非這些 HDL 程式片段。在將一般正數範例視為正確性證據之前,先測試零、極值與混合正負號。
自己試試看
將八位元 -3 與 2 符號延伸為九位元後相加,求其結果。再求精確表示四個無號 255 相加所需的最小位元寬度。
查看解說
九位元運算元為 111111101 與 000000010。其總和為 111111111,也就是 -1。四個 255 的總和是 1020;九位元無號數最多只能表示 511,因此需要十位元。