0
votes

I have used following code to generate clock (whichever value I pass through task it will create that frequency), but the code only works if I use CLKSEL_global = clksel_local (i.e. blocking assignment) but that creates delta delay.

How do I generate variable clock without introducing delta delay? Is their another way of using a task. I am using task so that I can pass real values

`timescale 1ns/1ps
module tb();
  real CLKSEL_global;

  reg CLK7;


  new dut(clk,clk_out);

  task task_CLOCK;
    input real clksel_local;
    begin
      CLKSEL_global = clksel_local;
    end
  endtask

  initial begin
    CLK7 = 0;
    forever begin
      #(500.0/CLKSEL_global) CLK7 = 1;
      #(500.0/CLKSEL_global) CLK7 = 0;
    end
  end


  initial begin
    task_CLOCK(340.0);
  end

  initial begin
    #100 $finish ;
  end
endmodule
1
ya its not the part and can be removedra-one
Just need to also remove the line ` new dut(clk,clk_out);` then the question is all about CLK7.Morgan

1 Answers

2
votes

This solution feels like a nasty hack but I think achieves the requirement. When changing the Clock frequency it will change on the next edge, but allows @(posedge clk) to be used for the edge you want to change it on. The change is actually 1ns after the positive edge.

Normally the you would set the frequency and allow it to take effect on the edge giving a full cycle of setup.

Timing Diagram

module tb();
  real CLKSEL_global = 500;
  reg clk;

  task task_CLOCK;
    input real clksel_local;
    begin
      CLKSEL_global <= clksel_local;
    end
  endtask

  initial begin
    #1ns;        
    clk = 1'b0;
    forever begin  
      #((500.0ns/CLKSEL_global) -1ns) clk = ~clk;
    end
  end

  initial begin
    $dumpfile("dump.vcd"); $dumpvars;

    task_CLOCK(1);
    repeat(2)
      @(posedge clk);

    task_CLOCK(2);
    repeat(2)
      @(posedge clk);

    $finish ;
  end
endmodule

Working copy of above on EDA Playground.