summaryrefslogtreecommitdiff
path: root/midterm/SRC/bfm.sv
blob: 2d81ad6012e427f68150fde854f0cdeabb7c8fab (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
import typedef_pkg::*;

class bfm;
  localparam int TOTAL_TESTS = 4 * 256 * 256;

  virtual intf alu_if;
  transaction  tr;

  function new(virtual intf alu_if_in, transaction tr_in);
    alu_if = alu_if_in;
    tr = tr_in;
  endfunction

  task drive();
    for (int op_i = 0; op_i < 4; op_i++) begin
      for (int a_i = 0; a_i < 256; a_i++) begin
        for (int b_i = 0; b_i < 256; b_i++) begin
          automatic operation_t op_val = operation_t'(op_i[1:0]);
          automatic operand_t   a_val = operand_t'(a_i[7:0]);
          automatic operand_t   b_val = operand_t'(b_i[7:0]);

          `RND_CHECK(std::randomize(tr.operation, tr.operand_a, tr.operand_b) with {
                     tr.operation == op_val;
                     tr.operand_a == a_val;
                     tr.operand_b == b_val;
                     })
          drive_trxn();
        end
      end
    end

    $display("BFM drive complete. Total tests: %0d", TOTAL_TESTS);
  endtask

  task drive_trxn();
    @(negedge alu_if.clk);

    alu_if.op_start  = 1'b1;
    alu_if.operation = tr.operation;
    alu_if.operand_a = tr.operand_a;
    alu_if.operand_b = tr.operand_b;

    @(negedge alu_if.clk);

    alu_if.op_start = 1'b0;

    @(posedge alu_if.clk);
    @(posedge alu_if.clk);
    @(negedge alu_if.clk);

    tr.actual_result = alu_if.result;
  endtask
endclass