---
# System prepended metadata

title: 數位系統 第四次實驗報告
tags: [digital system]

---

# 數位系統 第四次實驗報告
###### tags: `digital system`
    姓名：高聖傑
    系級：資工113
    學號：B093040016
    實驗日期：2021/11/1
	
## 實驗一

### 內容

- 目標 & 要求
	- $F(w,x,y,z)=w'yz + w'xy + wxy + xyz + wx'y'$
	- 畫出 F 的 K map，並找到所有最簡 sum of products as F1, F2 ... Fn
	- 使用 dataflow level modeling 模擬並驗證所有最簡 sum of products 等效


### 過程
先依照 $w'yz + w'xy + wxy + xyz + wx'y'$ 畫出 F 的 K map
![](https://i.imgur.com/3yOtWGE.jpg =360x)

樣子是個樓梯，可以用 4 個 2x1 或 1x2 的區域拼起來，共有 3 種組合方式
- $F_1=w′yz′+xyz+wy′z+wx′y′$
![](https://i.imgur.com/oBnWomS.jpg =360x)
- $F_2=w′yz′+w′xy+wxz+wx′y′$
![](https://i.imgur.com/xOJOGgj.jpg =360x)
- $F_3=w′yz′+xyz+wxz+wx′y′$
![](https://i.imgur.com/VG6bblD.jpg =360x)

以下的 module exe1_1, exe1_2, exe1_3 分別為 F1, F2, F3
三個 module 皆使用 dataflow level modeling 

```verilog=
`timescale 1ns / 1ps

module exe1_1(w,x,y,z,res);
    input w,x,y,z;
    output res;
    assign res = (~w&y&~z) | (x&y&z) | (w&~y&z) | (w&~x&~y);
endmodule

module exe1_2(w,x,y,z,res);
    input w,x,y,z;
    output res;
    assign res = (~w&y&~z) | (~w&x&y) | (w&x&z) | (w&~x&~y);
endmodule 

module exe1_3(w,x,y,z,res);
    input w,x,y,z;
    output res;
    assign res = (~w&y&~z) | (x&y&z) | (w&x&z) | (w&~x&~y);
endmodule
```
### 模擬結果
res1 → F1 , res2 → F2 , res3 → F3

![e1](https://i.imgur.com/YhQ1bhF.png =700x)

三個 function 所產生的波形圖一樣，因此可證明 $F_1, F_2, F_3$ 等效

## 實驗二

### 內容

- 目標 & 要求
	- $F1(v,w,x,y,z) = \Sigma(1,2,3,6,7,9,10,11,14,15,17,18,19,22,25,26,27,30)$
	- 畫出 F1 的 K map
	- 並利用此 K map ，找出最簡 sum of products as F2
	- 使用 Structural level modeling 模擬並驗證 F1, F2 等效


### 過程
由以下圖之 K map ，可化簡：$F2 = x'z + v'y + yz'$
![](https://i.imgur.com/kbc7EV2.png =700x)


以下的 module exe2_1, exe2_2 分別為 F1, F2
兩者皆使用 Structural level modeling 

```verilog=
`timescale 1ns / 1ps

module exe2_1(v, w, x, y, z, res);
    input v, w, x, y, z;
    output res;
    wire nv, nw, nx, ny, nz;
    wire m1, m2, m3, m6, m7, m9, m10, m11, m14,
    m15, m17, m18, m19, m22, m25, m26, m27, m30;
    not(nv, v);
    not(nw, w);
    not(nx, x);
    not(ny, y);
    not(nz, z);
    and(m1,nv,nw,nx,ny, z);
    and(m2,nv,nw,nx, y,nz);
    and(m3,nv,nw,nx, y, z);
    and(m6,nv,nw, x, y,nz);
    and(m7,nv,nw, x, y, z);
    and(m9,nv, w,nx,ny, z);
    and(m10,nv, w,nx, y,nz);
    and(m11,nv, w,nx, y, z);
    and(m14,nv, w, x, y,nz);
    and(m15,nv, w, x, y, z);
    and(m17, v,nw,nx,ny, z);
    and(m18, v,nw,nx, y,nz);
    and(m19, v,nw,nx, y, z);
    and(m22, v,nw, x, y,nz);
    and(m25, v, w,nx,ny, z);
    and(m26, v, w,nx, y,nz);
    and(m27, v, w,nx, y, z);
    and(m30, v, w, x, y,nz);
    or(res, m1, m2, m3, m6, m7, m9, m10, m11, m14,
    m15, m17, m18, m19, m22, m25, m26, m27, m30);
endmodule

module exe2_2(v, w, x, y, z, res);
    input v, w, x, y, z;
    output res;
    wire nv, nx, nz, a1, a2, a3;
    not(nv, v);
    not(nx, x);
    not(nz, z);
    and(a1, nv, y);
    and(a2, nx, z);
    and(a3, y, nz);
    or(res, a1, a2, a3);
endmodule

```
### 模擬結果
res1 → F1 , res2 → F2

![e2](https://i.imgur.com/pnSplh1.png =700x)

兩個 function 所產生的波形圖一樣，因此可證明 $F_1, F_2$ 等效

## 實驗三

### 內容

- 目標 & 要求
	- 使用 K map & don’t-care conditions，設計 4 位元輸入的 9 補數轉換器
	- 畫出 9 補數轉換器的 logic diagram
	- 使用 Structural level modeling 模擬並驗證此轉換器


### 過程
使用 K map & don’t-care conditions 化簡
- $y_3=x_3'x_2'x_1'$
![](https://i.imgur.com/aWmmTxj.jpg =360x)

- $y_2=x_1\oplus x_2$
![](https://i.imgur.com/RN1GIRo.jpg =360x)

- $y_1=x_1$
![](https://i.imgur.com/8Ji1M4l.jpg =360x)

- $y_0=x_0'$
![](https://i.imgur.com/x1bC1co.jpg =360x)



由以上 K map 可得 9 補數轉換器的 logic diagram
![](https://i.imgur.com/yrSRrnf.png =650x)


```verilog=
`timescale 1ns / 1ps

module exe3( x0, x1, x2, x3, y0, y1, y2, y3);
    input x0, x1, x2, x3;
    output y0, y1, y2, y3;
    wire nx1, nx2, nx3;
    not(y0, x0);
    not(nx1, x1);
    not(nx2, x2);
    not(nx3, x3);
    
    buf(y1, x1);
    xor(y2, x1, x2);
    and(y3, nx1, nx2, nx3);
    
endmodule

```
### 模擬結果
$D → x_0, C → x_1, B → x_2, A → x_3$

![e3](https://i.imgur.com/Ew1l652.png =700x)

由 waveform 可確認 9 補數轉換器的輸出正確

## testbench code
3 個實驗皆使用我額外寫的 python 腳本，
所自動生成的 testbench code，最後加上部分修改。
僅展示實驗 1 之 tb.v，其餘實驗大致相同

```verilog=
`timescale 1ns / 1ps

module tbGen();

reg A, B, C, D;
wire res1, res2, res3;

exe1_1 _tb1(.w(A), .x(B), .y(C), .z(D), .res(res1));
exe1_2 _tb2(.w(A), .x(B), .y(C), .z(D), .res(res2));
exe1_3 _tb3(.w(A), .x(B), .y(C), .z(D), .res(res3));

initial begin

    A = 1'b0; B = 1'b0; C = 1'b0; D = 1'b0;
    #10
    A = 1'b0; B = 1'b0; C = 1'b0; D = 1'b1;
    #10
    A = 1'b0; B = 1'b0; C = 1'b1; D = 1'b0;
    #10
    A = 1'b0; B = 1'b0; C = 1'b1; D = 1'b1;
    #10
    A = 1'b0; B = 1'b1; C = 1'b0; D = 1'b0;
    #10
    A = 1'b0; B = 1'b1; C = 1'b0; D = 1'b1;
    #10
    A = 1'b0; B = 1'b1; C = 1'b1; D = 1'b0;
    #10
    A = 1'b0; B = 1'b1; C = 1'b1; D = 1'b1;
    #10
    A = 1'b1; B = 1'b0; C = 1'b0; D = 1'b0;
    #10
    A = 1'b1; B = 1'b0; C = 1'b0; D = 1'b1;
    #10
    A = 1'b1; B = 1'b0; C = 1'b1; D = 1'b0;
    #10
    A = 1'b1; B = 1'b0; C = 1'b1; D = 1'b1;
    #10
    A = 1'b1; B = 1'b1; C = 1'b0; D = 1'b0;
    #10
    A = 1'b1; B = 1'b1; C = 1'b0; D = 1'b1;
    #10
    A = 1'b1; B = 1'b1; C = 1'b1; D = 1'b0;
    #10
    A = 1'b1; B = 1'b1; C = 1'b1; D = 1'b1;
    #10
$finish;
end
endmodule

```

## 實驗心得

> 這次的實驗主要是練習 verilog 程式碼以及 K map 化簡的實驗。
> 
> 實驗一做到模擬的時候 vivado 當掉了，我把他強制關掉，結果就沒辦法再次模擬了，搞的我要重開一個專案才能完成實驗
> 
> 在做實驗二的時候，覺得重複性過高，所以我當場寫了一個 python 腳本，讓我能在 2 分鐘內完成程式中有一大串 AND 的部分，省下大量時間，也省得我複製貼上、一個字一個字改的精力，甚至是以後做類似實驗也可以用上。
> 
> 第三個實驗有遇到需要直接把 input x1 接到 output y2 上的部分，但這不像其他兩種設計方式可以直接 assign 上去。於是我想到課堂中提到的 buffer 元件，我先試了 buffer()，發現沒有變色，換成 buf() 就正確了，後來有聽到助教提醒 buffer 的寫法是 buf()，覺得能自己試出來也是挺酷的。

## Extra Coding
在做實驗二的時候，覺得重複性過高，所以我當場寫了一個臨時用的 python 腳本，這裡是我課後改良的版本，替換掉當時為了貪快而寫死的東西，也改良到不用額外補字了。
他可以根據第 4 行 ts 給予的 canonical form ，生成 module 裡 sum of products 的部分。

> product of sums 也可以，把第 20, 22 行的 and, or 交換，
> 然後第 4 行的 ts 改成找題目 result 裡的 maxterm 即可。


```python=
# num of ports
n = 5
# canonical form
ts = [1,2,3,6,7,9,10,11,14,15,17,18,19,22,25,26,27,30]
# lookups
c = ord('z')+1-n
ports = list(map(chr, range(c, ord("z")+1)))
r = range(n)
# wires
print(f'wire n{", n".join(map(str, ports))};')
print(f'wire m{", m".join(map(str, ts))};\n')
# nots
for i in r:
    print(f"not(n{chr(c+i)}, {chr(c+i)});")
# products
for i in range(2**n):
    # print(f"{f'{i:0{n}b}'}")
    if i in ts:
        tgt = ["n "[int(j)]+k for j,k in zip(f"{f'{i:0{n}b}'}", ports)]
        print(f"and(m{i}, {','.join(tgt)});")
# sum
print(f"or(res, m{', m'.join(map(str, ts))});")

```


### 測試生成結果
測試生成參數：
3 個接口 (n = 3)，欲求 sum of products = $\Sigma(m_1, m_2, m_3, m_6, m_7)$ (ts = [1,2,3,6,7])

```verilog=
wire nx, ny, nz;
wire m1, m2, m3, m6, m7;

not(nx, x);
not(ny, y);
not(nz, z);
and(m1, nx,ny, z);
and(m2, nx, y,nz);
and(m3, nx, y, z);
and(m6,  x, y,nz);
and(m7,  x, y, z);

or(res, m1, m2, m3, m6, m7);
```