Half Adder using NAND Primitive

Solving Approach

How do you plan to solve it?

 

 

Code

/*Write your code here*/module ha_nand_only(
    input  wire a,
    input  wire b,
    output wire sum,
    output wire cout
);

    wire n1, n2, n3, n4;

    // NAND-only XOR for sum
    nand (n1, a, b);     // n1 = ~(a & b)
    nand (n2, a, n1);    // n2 = ~(a & n1)
    nand (n3, b, n1);    // n3 = ~(b & n1)
    nand (sum, n2, n3);  // sum = ~(n2 & n3) = a ⊕ b

    // NAND-only AND for cout
    nand (n4, a, b);     // n4 = ~(a & b)
    nand (cout, n4, n4); // cout = ~(~(a & b) & ~(a & b)) = a & b

endmodule

 

Upvote
Downvote

Testbench Code

`timescale 1ns/1ps
module tb_ha_nand_only;
  reg  a, b;
  wire sum, cout;

  wire expected_sum, expected_cout;
  wire mismatch;

  ha_nand_only dut(.a(a), .b(b), .sum(sum), .cout(cout));

  assign expected_sum  = a ^ b;
  assign expected_cout = a & b;

  assign mismatch = (sum !== expected_sum) | (cout !== expected_cout);

  initial begin
    $dumpfile("tb_ha_nand_only.vcd");
    $dumpvars(0,
      a, b,
      sum, cout,
      expected_sum, expected_cout,
      mismatch
    );
  end

  integer TOTAL_TEST_CASES, TOTAL_PASSED_TEST_CASES, TOTAL_FAILED_TEST_CASES;
  integer ia, ib;

  initial begin
    TOTAL_TEST_CASES = 0; TOTAL_PASSED_TEST_CASES = 0; TOTAL_FAILED_TEST_CASES = 0;

    for (ia = 0; ia < 2; ia = ia + 1) begin
      for (ib = 0; ib < 2; ib = ib + 1) begin
        a = ia[0]; b = ib[0]; #1;
        $display("CASE=a%0d_b%0d : sum=%0b expected_sum=%0b  cout=%0b expected_cout=%0b  %s",
                 a, b, sum, expected_sum, cout, expected_cout, mismatch ? "MISMATCH" : "OK");
        TOTAL_TEST_CASES = TOTAL_TEST_CASES + 1;
        if (!mismatch) TOTAL_PASSED_TEST_CASES = TOTAL_PASSED_TEST_CASES + 1;
        else begin
          TOTAL_FAILED_TEST_CASES = TOTAL_FAILED_TEST_CASES + 1;
          $display("  FAILED INPUTS: a=%0b b=%0b", a, b);
        end
        #4;
      end
    end

    $display("TOTAL_TEST_CASES=%0d",        TOTAL_TEST_CASES);
    $display("TOTAL_PASSED_TEST_CASES=%0d", TOTAL_PASSED_TEST_CASES);
    $display("TOTAL_FAILED_TEST_CASES=%0d", TOTAL_FAILED_TEST_CASES);
    $display("ALL_TEST_CASES_PASSED=%s",    (TOTAL_FAILED_TEST_CASES==0) ? "true" : "false");
    $finish;
  end
endmodule