0
\$\begingroup\$

I want to design a 8 bit adder-subtracter in verilog. when cin is 1, it should add 2 numbers, when 0, it should subtracts.

For performing subtraction, I said to add number1 and ~number2 and 1. here is the code:(when subtracting, cin = 0. so ~cin = 1. and it the 3 values will be added by a full_adder which works truly) this is done for all 8 bits.

`timescale 1ns/100ps
module full_adder(input a, b, cin, clock, output reg sum, cout);
 always @(negedge clock) begin
 sum = #7 a ^ b ^ cin;
 cout = #7 (a & b) | (a & cin) | (b & cin);
 end
endmodule
module adder_subtracter_8bit
 (input [7:0] num1, num2, input cin, clock, output [7:0] result, output cout);
 //1 is for adding, 0 for subtracting
 wire w0, w1, w2, w3, w4, w5, w6;
 assign #3 num2[0] = (num2[0] ~^ cin);
 full_adder ADD0 (.a(num1[0]), .b(num2[0]), .cin(~cin), .clock(clock)
 , .sum(result[0]), .cout(w0));
 assign #3 num2[1] = (num2[1] ~^ w0);
 full_adder ADD1 (.a(num1[1]), .b(num2[1]), .cin(w0), .clock(clock)
 , .sum(result[1]), .cout(w1));
 assign #3 num2[2] = (num2[2] ~^ w1);
 full_adder ADD2 (.a(num1[2]), .b(num2[2]), .cin(w1), .clock(clock)
 , .sum(result[2]), .cout(w2));
 assign #3 num2[3] = (num2[3] ~^ w2);
 full_adder ADD3 (.a(num1[3]), .b(num2[3]), .cin(w2), .clock(clock)
 , .sum(result[3]), .cout(w3));
 assign #3 num2[4] = (num2[4] ~^ w3);
 full_adder ADD4 (.a(num1[4]), .b(num2[4]), .cin(w3), .clock(clock)
 , .sum(result[4]), .cout(w4));
 assign #3 num2[5] = (num2[5] ~^ w4);
 full_adder ADD5 (.a(num1[5]), .b(num2[5]), .cin(w4), .clock(clock)
 , .sum(result[5]), .cout(w5));
 assign #3 num2[6] = (num2[6] ~^ w5);
 full_adder ADD6 (.a(num1[6]), .b(num2[6]), .cin(w5), .clock(clock)
 , .sum(result[6]), .cout(w6));
 assign #3 num2[7] = (num2[7] ~^ w6);
 full_adder ADD7 (.a(num1[7]), .b(num2[7]), .cin(w6), .clock(clock)
 , .sum(result[7]), .cout(cout));
endmodule

however, this isn't work properly and the outputs(which are wires showing the result) are all X. Signals

testbench:

`timescale 1ns/100ps
module TEST_adder_subtracter_8bit();
 reg [7:0] a, b;
 reg clock, cin;
 wire [7:0] result;
 wire cout;
 adder_subtracter_8bit UUT(.num1(a), .num2(b), .cin(cin), .clock(clock),
 .result(result), .cout(cout));
 initial repeat (2000) #7 clock = ~clock;
 initial begin
 a = 8'b0000_0000;
 b = 8'b0000_0000;
 clock = 0;
 cin = 1;
 #180;
 a = 8'b0000_0001;
 b = 8'b0000_0001;
 #180;
 a = 8'b0000_0111;
 #180;
 a = 8'b0000_0001;
 b = 8'b0000_0111;
 #180;
 a = 8'b0001_1010;
 b = 8'b0001_0011;
 #180;
 a = 8'b0000_0001;
 b = 8'b1111_1111;
 #180;
 a = 8'b1111_1111;
 b = 8'b0000_0001;
 #180;
 a = 8'b1111_0000;
 b = 8'b1111_0110;
 #180;
 a = 8'b0111_0011;
 b = 8'b0111_0111;
 #180;
 a = 8'b1111_1111;
 b = 8'b1111_1111;
 end
endmodule

Can anyone say how should I fix it?

Solar Mike
6,8841 gold badge14 silver badges28 bronze badges
asked Mar 2, 2018 at 12:02
\$\endgroup\$
10
  • 1
    \$\begingroup\$ You should provide more of your code and the test bench. Looks like your Cin is unknown (undefined). \$\endgroup\$ Commented Mar 2, 2018 at 13:05
  • \$\begingroup\$ @Nazar I entered the whole code \$\endgroup\$ Commented Mar 2, 2018 at 13:07
  • \$\begingroup\$ Also I advice to change your name. cin is often a carry-in. If it controls add/subtract it should be called something like that. \$\endgroup\$ Commented Mar 2, 2018 at 13:07
  • \$\begingroup\$ Double post: You also posted this here: stackoverflow.com/questions/49068571/… \$\endgroup\$ Commented Mar 2, 2018 at 13:08
  • 1
    \$\begingroup\$ Based on your timing diagram, the cin is unknown, so you would expect the outputs to be unknown too. Try changing the cin = 1 to cin = 1'b1in your test bench \$\endgroup\$ Commented Mar 2, 2018 at 13:25

1 Answer 1

2
\$\begingroup\$

what I feel as the mistake in your code is assign #3 num2[0] = (num2[0] ~^ cin) and other similar expressions. Try changing the name of the net 'num2[0]' on the left-hand side. It will then work. Further, there is a mistake in your code for the expression series that involves 'num2'. All such expressions should be assign #3 NUM2[i] = (num2[i] ~^ cin), i = 1,...,7. You may find my version of the Verilog code for the problem below.

Verilog Code:

`timescale 1 ns / 100 ps
module FullAdder (
input a, b, cin, Clk,
output reg s, cout
);
 always @(negedge Clk)
 begin
 s = #7 a ^ b ^ cin;
 cout = #7 (a & b) | (b & cin) | (cin & a);
 end
endmodule
module AddSubtract (
 input [7:0] a, b,
 input Cin, Clk,
 output [7:0] sum,
 output Cout
);
 genvar i;
 wire [8:0] C;
 wire [7:0] B;
 assign C[0] = ~Cin;
 generate
 for (i = 0; i < 8; i = i + 1)
 begin : AddSubArray
 assign #3 B[i] = b[i] ~^ Cin;
 FullAdder FA (.a(a[i]), .b(B[i]), .cin(C[i]), .Clk(Clk), .s(sum[i]), .cout(C[i + 1]));
 end
 endgenerate
 assign Cout = C[8];
endmodule
answered Mar 2, 2018 at 17:27
\$\endgroup\$
1
  • 1
    \$\begingroup\$ It may be worth clarifying that HDL are continuously evaluated (event triggered) rather than sequential like a lot of programming languages. \$\endgroup\$ Commented Mar 2, 2018 at 17:34

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.