-
Notifications
You must be signed in to change notification settings - Fork 313
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
b4e2b29
commit 4ff3df1
Showing
50 changed files
with
2,679 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
import RightShifterTypes::*; | ||
import Gates::*; | ||
|
||
function Bit#(1) multiplexer1(Bit#(1) sel, Bit#(1) a, Bit#(1) b); | ||
// Part 1: Re-implement this function using the gates found in the Gates.bsv file | ||
// return (sel == 0)?a:b; | ||
// 使用与或非门实现这条语句,对return a&~sel | b&sel 即可 | ||
let a_out = andGate(a,notGate(sel)); | ||
let b_out = andGate(b,sel); | ||
let res = orGate(a_out , b_out); | ||
return res; | ||
|
||
endfunction | ||
|
||
function Bit#(32) multiplexer32(Bit#(1) sel, Bit#(32) a, Bit#(32) b); | ||
// Part 2: Re-implement this function using static elaboration (for-loop and multiplexer1) | ||
// return (sel == 0)?a:b; | ||
Bit#(32) aggregate = 0; | ||
for(Integer i = 0; i < 32; i = i + 1) | ||
begin | ||
aggregate[i] = multiplexer1(sel, a[i], b[i]); | ||
end | ||
return aggregate; | ||
endfunction | ||
|
||
function Bit#(n) multiplexerN(Bit#(1) sel, Bit#(n) a, Bit#(n) b); | ||
// Part 3: Re-implement this function as a polymorphic function using static elaboration | ||
// return (sel == 0)?a:b; | ||
Bit#(n) aggregate = 0; | ||
for(Integer i = 0; i < valueof(n); i = i + 1) | ||
begin | ||
aggregate[i] = multiplexer1(sel, a[i], b[i]); | ||
end | ||
return aggregate; | ||
endfunction | ||
|
||
function Bit#(n) copy_frontnum(Bit#(1) sign , Integer num); | ||
Bit#(n) result = 0; | ||
for(Integer i = 0;i < num;i = i+1) | ||
begin | ||
result[i] = sign; | ||
end | ||
return result; | ||
endfunction | ||
|
||
module mkRightShifter (RightShifter); | ||
method Bit#(32) shift(ShiftMode mode, Bit#(32) operand, Bit#(5) shamt); | ||
// Parts 4 and 5: Implement this function with the multiplexers you implemented | ||
// pack函数用于将各种Bit数据类型(例如Bool,Int或UInt)转换(或打包)为(Bit#(n))类型。 | ||
Bit#(32) result = 0; | ||
Bit#(1) flag = 0; | ||
Bit#(1) sign_bit = operand[31]; | ||
// flag用来判断是逻辑还是算数右移,逻辑右移前面补0,算数右移前面补符号位。 | ||
if(mode == LogicalRightShift) | ||
begin | ||
flag = 1; | ||
end | ||
// 确定要右移前面要填充的0 OR 1 | ||
sign_bit = multiplexerN(flag , operand[31] , 0); | ||
// 按照位置右移 | ||
result = multiplexerN( shamt[0] , operand, {sign_bit,operand[31:1]}); | ||
result = multiplexerN( shamt[1] , result, {copy_frontnum(sign_bit,2),result[31:2]}); | ||
result = multiplexerN( shamt[2] , result, {copy_frontnum(sign_bit,4),result[31:4]}); | ||
result = multiplexerN( shamt[3] , result, {copy_frontnum(sign_bit,8),result[31:8]}); | ||
result = multiplexerN( shamt[4] , result, {copy_frontnum(sign_bit,16),result[31:16]}); | ||
|
||
return result; | ||
endmethod | ||
endmodule |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
import RightShifterTypes::*; | ||
import RightShifter::*; | ||
|
||
(* synthesize *) | ||
module mkTests (Empty); | ||
RightShifter logicalShifter <- mkRightShifter; | ||
RightShifter arithmeticShifter <- mkRightShifter; | ||
|
||
// there are many ways to write tests. Here is a very simple | ||
// version, just to get you started. | ||
|
||
rule test; | ||
|
||
let g = multiplexer1(1, 1, 0); | ||
if (g != 0) begin | ||
$display("result is ", g, " but expected 0"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let c = logicalShifter.shift(LogicalRightShift, 12, 2); | ||
if (c != 3) begin | ||
$display("result is ", c, " but expected 3"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let b = logicalShifter.shift(LogicalRightShift, 12, 1); | ||
if (b != 6) begin | ||
$display("result is ", b, " but expected 6"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let a = logicalShifter.shift(LogicalRightShift, 1, 1); | ||
if (a != 0) begin | ||
$display("result is ", a); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let h = logicalShifter.shift(ArithmeticRightShift, 12, 2); | ||
if (h != 3) begin | ||
$display("result is ", h, " but expected 3"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let i = logicalShifter.shift(LogicalRightShift, -32, 3); | ||
if (i != 536870908) begin | ||
$display("result is ", i, " but expected 536870908"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
let p = logicalShifter.shift(ArithmeticRightShift, -32, 3); | ||
if (p != -4) begin | ||
$display("result is ", p, " but expected -4"); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
$finish(0); | ||
endrule | ||
endmodule |
Binary file not shown.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
Compile Link and Simulate the Project... | ||
+ bsc -u -sim -simdir . -bdir . -info-dir . -keep-fires -p %/Prelude:%/Libraries:%/Libraries/BlueNoC -g mkTests TestShifter.bsv | ||
checking package dependencies | ||
compiling ./RightShifter.bsv | ||
compiling TestShifter.bsv | ||
code generation for mkTests starts | ||
Elaborated module file created: mkTests.ba | ||
+ bsc -e mkTests -sim -o ./out -simdir . -p %/Prelude:%/Libraries:%/Libraries/BlueNoC -bdir . -keep-fires | ||
All packages are up to date. | ||
Bluesim object created: ./mkTests.{h,o} | ||
Bluesim object created: ./model_mkTests.{h,o} | ||
+ ./out | ||
Simulation shared library created: out.so | ||
Simulation executable created: ./out | ||
correct! | ||
correct! | ||
correct! | ||
correct! | ||
correct! | ||
correct! | ||
Compile/Link/Simulate finished |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,139 @@ | ||
import RightShifterTypes::*; | ||
import Gates::*; | ||
import FIFO::*; | ||
|
||
// 坑一:Lab1是return (sel == 0)?a:b;这里代码变成return (sel == 1)?a:b这不是坑人? | ||
function Bit#(1) multiplexer1(Bit#(1) sel, Bit#(1) a, Bit#(1) b); | ||
return orGate(andGate(a, notGate(sel)),andGate(b, sel)); | ||
endfunction | ||
|
||
function Bit#(32) multiplexer32(Bit#(1) sel, Bit#(32) a, Bit#(32) b); | ||
Bit#(32) res_vec = 0; | ||
for (Integer i = 0; i < 32; i = i+1) | ||
begin | ||
res_vec[i] = multiplexer1(sel, a[i], b[i]); | ||
end | ||
return res_vec; | ||
endfunction | ||
|
||
function Bit#(n) multiplexerN(Bit#(1) sel, Bit#(n) a, Bit#(n) b); | ||
Bit#(n) res_vec = 0; | ||
for (Integer i = 0; i < valueof(n); i = i+1) | ||
begin | ||
res_vec[i] = multiplexer1(sel, a[i], b[i]); | ||
end | ||
return res_vec; | ||
endfunction | ||
|
||
// 上一个Lab1编写的复制函数 | ||
function Bit#(n) copy_frontnum(Bit#(1) sign , Integer num); | ||
Bit#(n) result = 0; | ||
for(Integer i = 0;i < num;i = i+1) | ||
begin | ||
result[i] = sign; | ||
end | ||
return result; | ||
endfunction | ||
|
||
module mkRightShifterPipelined (RightShifterPipelined); | ||
FIFO#(Bit#(1)) high_num <- mkFIFO(); | ||
FIFO#(Bit#(5)) shift_num <- mkFIFO(); | ||
FIFO#(Bit#(32)) op_num <- mkFIFO(); | ||
FIFO#(Bit#(38)) step_for_shift_1 <- mkFIFO(); | ||
FIFO#(Bit#(38)) step_for_shift_2 <- mkFIFO(); | ||
FIFO#(Bit#(38)) step_for_shift_4 <- mkFIFO(); | ||
FIFO#(Bit#(38)) step_for_shift_8 <- mkFIFO(); | ||
FIFO#(Bit#(38)) step_for_shift_16 <- mkFIFO(); | ||
|
||
// 处理右移1位的规则,让流水线能够分段处理5种位移情况。 | ||
rule step1 (True); | ||
Bit#(32) operand = op_num.first(); | ||
Bit#(5) shamt = shift_num.first(); | ||
Bit#(1) high_bit = high_num.first(); | ||
|
||
let result = multiplexerN(shamt[0] , operand , {high_bit,operand[31:1]}); | ||
// 存储流水线step的结果 | ||
step_for_shift_1.enq({high_bit,shamt,result}); | ||
high_num.deq(); | ||
op_num.deq(); | ||
shift_num.deq(); | ||
|
||
endrule | ||
|
||
// 处理右移2位的规则 | ||
rule step2 (True); | ||
Bit#(32) result = step_for_shift_1.first()[31:0]; | ||
Bit#(5) shamt = step_for_shift_1.first()[36:32]; | ||
Bit#(1) high_bit = step_for_shift_1.first()[37]; | ||
|
||
result = multiplexerN(shamt[1] , result , {copy_frontnum(high_bit,2),result[31:2]}); | ||
|
||
step_for_shift_2.enq({high_bit,shamt,result}); | ||
step_for_shift_1.deq(); | ||
endrule | ||
|
||
// 处理右移4位的规则 | ||
rule step3 (True); | ||
Bit#(32) result = step_for_shift_2.first()[31:0]; | ||
Bit#(5) shamt = step_for_shift_2.first()[36:32]; | ||
Bit#(1) high_bit = step_for_shift_2.first()[37]; | ||
|
||
result = multiplexerN(shamt[2] , result , {copy_frontnum(high_bit,4),result[31:4]}); | ||
|
||
step_for_shift_4.enq({high_bit,shamt,result}); | ||
step_for_shift_2.deq(); | ||
endrule | ||
|
||
// 处理右移8位的规则 | ||
rule step4 (True); | ||
Bit#(32) result = step_for_shift_4.first()[31:0]; | ||
Bit#(5) shamt = step_for_shift_4.first()[36:32]; | ||
Bit#(1) high_bit = step_for_shift_4.first()[37]; | ||
|
||
result = multiplexerN(shamt[3] , result , {copy_frontnum(high_bit,8),result[31:8]}); | ||
|
||
step_for_shift_8.enq({high_bit,shamt,result}); | ||
step_for_shift_4.deq(); | ||
endrule | ||
|
||
// 处理右移16位的规则 | ||
rule step5 (True); | ||
Bit#(32) result = step_for_shift_8.first()[31:0]; | ||
Bit#(5) shamt = step_for_shift_8.first()[36:32]; | ||
Bit#(1) high_bit = step_for_shift_8.first()[37]; | ||
|
||
result = multiplexerN(shamt[4] , result , {copy_frontnum(high_bit,16),result[31:16]}); | ||
|
||
step_for_shift_16.enq({high_bit,shamt,result}); | ||
step_for_shift_8.deq(); | ||
endrule | ||
|
||
|
||
method Action push(ShiftMode mode, Bit#(32) operand, Bit#(5) shamt); | ||
/* Write your code here */ | ||
// Action push操作输入右移的类别、右移数字、右移位数 | ||
Bit#(1) sign_bit = operand[31]; | ||
Bit#(1) flag = 0; | ||
// 按照Lab1的思路进行:逻辑右移补0,算术右移补符号位 | ||
if(mode == LogicalRightShift) | ||
begin | ||
flag = 1; | ||
end | ||
sign_bit = multiplexerN(flag , sign_bit , 0); | ||
|
||
// 把计算出来的数字和参数入队列 | ||
high_num.enq(sign_bit); | ||
op_num.enq(operand); | ||
shift_num.enq(shamt); | ||
|
||
endmethod | ||
|
||
method ActionValue#(Bit#(32)) pull(); | ||
/* Write your code here */ | ||
// ActionValue这里返回右移的结果 | ||
Bit#(32) result = step_for_shift_16.first()[31:0]; | ||
step_for_shift_16.deq(); | ||
return result; | ||
endmethod | ||
|
||
endmodule |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
import RightShifterTypes::*; | ||
import RightShifter::*; | ||
import FIFO::*; | ||
|
||
(* synthesize *) | ||
module mkTests (Empty); | ||
RightShifterPipelined rsp <- mkRightShifterPipelined; | ||
Reg#(Bit#(32)) tbCounter <- mkReg(0); | ||
FIFO#(Bit#(32)) answerFifo <- mkSizedFIFO(6); | ||
|
||
// there are many ways to write tests. Here is a very simple | ||
// version, just to get you started. | ||
|
||
rule run; | ||
rsp.push(LogicalRightShift, tbCounter, 1); | ||
answerFifo.enq(tbCounter >> 1); | ||
tbCounter <=tbCounter + 1; | ||
endrule | ||
|
||
rule test; | ||
|
||
let b <- rsp.pull(); | ||
let answer = answerFifo.first(); | ||
answerFifo.deq(); | ||
|
||
if (b != answer) begin | ||
$display("result is ", b, " but expected ", answer); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
if (tbCounter > 13) $finish(0); | ||
|
||
endrule | ||
endmodule |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
import RightShifterTypes::*; | ||
import RightShifter::*; | ||
import FIFO::*; | ||
|
||
(* synthesize *) | ||
module mkTests (Empty); | ||
RightShifterPipelined rsp <- mkRightShifterPipelined; | ||
Reg#(Bit#(32)) tbCounter <- mkReg(0); | ||
FIFO#(Bit#(32)) answerFifo <- mkSizedFIFO(6); | ||
|
||
// there are many ways to write tests. Here is a very simple | ||
// version, just to get you started. | ||
|
||
rule run; | ||
rsp.push(ArithmeticRightShift, -32, 4); | ||
answerFifo.enq(-2); | ||
tbCounter <=tbCounter + 1; | ||
endrule | ||
|
||
rule test; | ||
|
||
let b <- rsp.pull(); | ||
let answer = answerFifo.first(); | ||
answerFifo.deq(); | ||
|
||
if (b != answer) begin | ||
$display("result is ", b, " but expected ", answer); | ||
end | ||
else begin | ||
$display("correct!"); | ||
end | ||
|
||
if (tbCounter > 13) $finish(0); | ||
|
||
endrule | ||
endmodule |
Oops, something went wrong.