Created
December 23, 2017 18:54
-
-
Save patrickroberts/3908606ece975eb4c20b4cd8f8b25dd6 to your computer and use it in GitHub Desktop.
Recursive ALU module in Verilog HDL
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
`timescale 1ns / 1ps | |
module alu32 (d, Cout, V, a, b, Cin, S); | |
output[31:0] d; | |
output Cout, V; | |
input [31:0] a, b; | |
input Cin; | |
input [2:0] S; | |
wire [31:0] c, g, p; | |
wire gout, pout; | |
alu_cell _alu_cells[31:0] ( | |
.d(d), | |
.g(g), | |
.p(p), | |
.a(a), | |
.b(b), | |
.c(c), | |
.S(S) | |
); | |
lac #(.LEVEL(4)) _lac( | |
.c(c), | |
.gout(gout), | |
.pout(pout), | |
.Cin(Cin), | |
.g(g), | |
.p(p) | |
); | |
overflow _ov( | |
.Cout(Cout), | |
.V(V), | |
.g(gout), | |
.p(pout), | |
.c31(c[31]), | |
.Cin(Cin) | |
); | |
endmodule | |
module alu_cell (d, g, p, a, b, c, S); | |
output d, g, p; | |
input a, b, c; | |
input [2:0] S; | |
reg g,p,d,cint,bint; | |
always @(a,b,c,S,p,g) begin | |
bint = S[0] ^ b; | |
g = a & bint; | |
p = a ^ bint; | |
cint = S[1] & c; | |
if(S[2]==0) begin | |
d = p ^ cint; | |
end | |
else if(S[2]==1) begin | |
if((S[1]==0) & (S[0]==0)) begin | |
d = a | b; | |
end | |
else if ((S[1]==0) & (S[0]==1)) begin | |
d = ~(a | b); | |
end | |
else if ((S[1]==1) & (S[0]==0)) begin | |
d = a & b; | |
end | |
else | |
d = 0; | |
end | |
end | |
endmodule | |
module overflow (Cout, V, g, p, c31, Cin); | |
output Cout, V; | |
input g, p, c31, Cin; | |
assign Cout = g|(p&Cin); | |
assign V = Cout^c31; | |
endmodule | |
module lac(c, gout, pout, Cin, g, p); | |
parameter LEVEL = 0; | |
output[(2<<LEVEL)-1:0] c; | |
output gout, pout; | |
input Cin; | |
input[(2<<LEVEL)-1:0] g, p; | |
generate | |
case(LEVEL) | |
0: begin | |
assign c[0] = Cin; | |
assign c[1] = g[0] | (p[0] & Cin); | |
assign gout = g[1] | (p[1] & g[0]); | |
assign pout = p[1] & p[0]; | |
end | |
default: begin | |
wire[1:0] cint, gint, pint; | |
lac #(.LEVEL(LEVEL-1)) leaf0 ( | |
.c(c[(1<<LEVEL)-1:0]), | |
.gout(gint[0]), | |
.pout(pint[0]), | |
.Cin(cint[0]), | |
.g(g[(1<<LEVEL)-1:0]), | |
.p(p[(1<<LEVEL)-1:0]) | |
); | |
lac #(.LEVEL(LEVEL-1)) leaf1 ( | |
.c(c[(2<<LEVEL)-1:1<<LEVEL]), | |
.gout(gint[1]), | |
.pout(pint[1]), | |
.Cin(cint[1]), | |
.g(g[(2<<LEVEL)-1:1<<LEVEL]), | |
.p(p[(2<<LEVEL)-1:1<<LEVEL]) | |
); | |
lac #(.LEVEL(0)) root ( | |
.c(cint), | |
.gout(gout), | |
.pout(pout), | |
.Cin(Cin), | |
.g(gint), | |
.p(pint) | |
); | |
end | |
endcase | |
endgenerate | |
endmodule |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Schematic:
Logic table: