Menu

Verilog Timescale과 Delays: 시뮬레이션 시간 제어

timescale 지시문이 어떻게 #delay`의 단위를 설정하는지, 파일 간 서로 다른 단위 결합 규칙, 그리고 delay가 clocked logic과 상호작용하는 방식.

이 페이지에는 실행 가능한 에디터가 있습니다 - 편집하고 실행하면 결과를 바로 볼 수 있습니다.

Verilog에서 "시간"이 의미하는 것

Verilog에는 초의 내장 개념이 없습니다. 시뮬레이터는 "시간 단위" - 임의의 정수 tick - 를 진행시키고, 코드는 #N으로 N개를 대기합니다. `timescale 지시문이 그 tick을 실제 시간에 매핑합니다.

`timescale 1ns / 1ps

module test;
    initial begin
        $display("t = %0t", $time);   // 0
        #5;
        $display("t = %0t", $time);   // 5 ns
        #1.5;
        $display("t = %0t", $time);   // 6500 ps (또는 6.5 ns)
        $finish;
    end
endmodule

매개변수 둘.

  • 단위(첫 숫자): #1이 무엇을 의미하는지. 1ns는 한 tick이 1 ns라고 말합니다.
  • 정밀도(둘째 숫자): 그 단위 안에서 시간을 얼마나 미세하게 추적할지. 1ps는 소수 delay가 picosecond로 반올림된다고 말합니다.

정밀도는 단위보다 거칠 수 없습니다(1ps / 1ns는 불법). 흔한 선택.

  • 1ns / 1ps - 사실상의 표준. 모든 게 ns, 게이트 지연을 위한 sub-ns 정밀도.
  • 1ps / 1ps - 극히 빠른 회로를 모델링하거나 모든 지연이 sub-ns일 때.
  • 1us / 1ns - 느린 embedded 규모 시뮬레이션(UART 바이트 시간, 느린 프로토콜).

어디에 둘까

`timescale은 모듈 레벨 구성요소가 아니라 컴파일러 지시문 입니다. 파일 맨 위, 어떤 module보다도 앞에 둡니다.

`timescale 1ns / 1ps

module foo(...);
    // ...
endmodule

스코프는 "이 지점부터 컴파일 순서대로, 다음 `timescale이나 컴파일 끝까지"입니다. 미묘한 함의가 있습니다: 명시적 `timescale이 없는 파일은 이전에 컴파일된 파일이 선언한 것을 상속하고, 그건 컴파일러가 파일을 읽는 순서에 의존합니다. 놀라움을 피하세요: 모든 파일 맨 위에 `timescale을 두세요.

이 문서의 브라우저 에디터는 여러분을 위해 기본 timescale(보통 1ns / 1ps)을 설정해 줍니다. 그래서 앞 문서의 예제들이 timescale을 선언하지 않고도 동작했습니다. 실제 프로젝트에서는 명시적으로 적습니다.

실전에서 #delay

`timescale 1ns / 1ps 뒤에는

#5            // 5 ns 대기
#100          // 100 ns 대기
#1.5          // 1.5 ns 대기 (정밀도 허용)
#0.001        // 1 ps 대기 (정밀도 바로 위)
#0            // zero-delay; 같은 시각의 이벤트 순서 정리에 유용

initial이나 always 블록 안에서 #N은 procedural 흐름을 N 시간 단위 차단합니다. 시뮬레이터가 블록을 일시정지하고(다른 동시 블록은 계속) delay 후 재개합니다.

대입 앞에 delay를 붙일 수 있습니다.

#10 a = 1;        // 10 ns 대기 후 대입
data <= #2 new_value;   // non-blocking 대입을 2 ns 후로 스케줄

첫 형태가 testbench 단골입니다. 두 번째(지연된 non-blocking)는 전파 지연을 모델링하는 게이트 레벨 시뮬레이션에 쓰입니다.

클럭 생성

고전적 패턴.

`timescale 1ns / 1ps

module test;
    reg clk = 0;
    always #5 clk = ~clk;
    // ...
endmodule

timescale 1ns / 1ps에서 #5는 5 ns. 클럭이 5 ns마다 토글, 10 ns 주기 - 100 MHz 클럭. 주파수를 바꾸려면 delay를 바꿉니다.

반주기주기주파수
#12 ns500 MHz
#2.55 ns200 MHz
#510 ns100 MHz
#1020 ns50 MHz
#2550 ns20 MHz
#50100 ns10 MHz

소수 반주기(#2.5)를 원하면 정밀도가 그것을 지원해야 합니다 - 1ps 정밀도는 0.001 ns까지 처리하므로 합리적 주파수면 다 됩니다.

파일 간 timescale 섞기

실제 설계는 많은 파일을 가지고, 그들은 서로 다른 timescale을 선언할 수 있습니다. 시뮬레이터는 각 파일 자체의 timescale로 그 파일의 delay를 해석합니다. module_a.v`timescale 1ns / 1ps라고 적고 #5를 쓰면 5 ns입니다. module_b.v`timescale 1us / 1ns라고 적고 #5를 쓰면 5 us입니다.

시뮬레이터가 어쨌든 전역 시간 축을 제시하므로 이건 대체로 보이지 않습니다 - 하지만 두 파일의 같은 #N이 크게 다른 것을 의미할 수 있다는 뜻이기도 합니다. 해법: 하나의 timescale을 고르고(산업 표준은 1ns / 1ps) 모든 파일 맨 위에 두세요. 섞지 마세요.

delay는 synthesizable이 아니다

중요: #delay는 시뮬레이션을 위해서만 존재합니다. synthesis 도구는

// synthesizable RTL에서 - 잘못
always @(posedge clk) begin
    out <= #2 in;
end

…을 읽고 #2를 무시하거나(대부분 도구) 구성을 거부합니다(더 엄격한 linter). 실제 하드웨어의 timing은 클럭과 게이트 전파 지연으로 결정되며 - 둘 다 소스 코드에 보이지 않습니다.

규칙: #은 testbench에서만. synthesizable RTL에는 # delay 없음. synthesizable 코드에서 delay가 필요해진다면 사실 클럭에서 카운트다운하는 카운터를 원하는 것입니다 - 그게 실제 하드웨어가 "대기"하는 방식입니다.

$time vs $realtime

현재 시뮬레이션 시간을 읽는 두 가지 방법.

  • $time 은 현재 timescale 단위의 64비트 정수를 반환.
  • $realtime 은 현재 timescale 단위의 real을 반환하지만 전체 정밀도로.

testbench 로깅에는 거의 항상 $time이면 충분합니다. print 문에서 sub-tick 정밀도가 필요할 때만 $realtime으로 손이 갑니다.

실용 팁

  • 모든 파일 맨 위에 항상 `timescale을 선언. 1ns / 1ps가 안전한 기본.
  • #delay는 testbench에서만. synthesizable 코드에서 없는 것을 정적 규칙으로 다루세요.
  • 클럭 주기를 목표 주파수에 맞추세요. 50 MHz 설계를 시뮬레이션한다면 20 ns 클럭 주기를 쓰세요 - 어긋난 주기는 timing 민감 버그를 가릴 수 있습니다.
  • 사이클 카운트 자극에는 # 대신 @(posedge clk). 클럭 주기 변경에 견고합니다.

다음에 볼 내용

이제 이 Verilog 튜토리얼의 모든 문서를 봤습니다. 언어 기초(wire vs reg, 모듈, 연산자)부터, procedural 블록과 흐름 제어, 동기 설계와 상태 머신, 그리고 마지막으로 모든 게 동작함을 증명하는 testbench까지. 이제 무언가를 만들 시간입니다 - 이 문서 옆 playground가 우리가 내내 사용한 같은 시뮬레이터이고, 여러분이 스케치하는 어떤 모듈에든 준비되어 있습니다.

자주 묻는 질문

Verilog에서 `timescale 1ns / 1ps는 무엇을 의미하나요?

시뮬레이터에게 '이 파일의 한 시간 단위는 1 나노초이고 시간은 picosecond 정밀도로 추적한다'고 알립니다. 그 지시문 이후 #5는 5 ns 대기, #1.5는 1.5 ns 대기(picosecond로 반올림)이고 $time은 ns 단위로 보고됩니다. 첫 숫자가 단위, 둘째가 정밀도입니다.

모든 Verilog 파일에 `timescale이 필요한가요?

권장: 네. 지시문의 스코프는 다음 \timescale이나 컴파일 끝에서 종료되므로, 없는 파일은 이전에 컴파일된 파일이 선언한 것을 상속합니다. 그러면 빌드 간 timing이 비결정적이 됩니다. 모든 소스 파일 맨 위에 `timescale 1ns / 1ps`를 두는 게 가장 흔한 관례이고 - 그러면 놀랄 일이 없습니다.

Verilog에서 #5는 무엇을 의미하나요?

#5는 시뮬레이션 시간을 5 시간 단위 진행시킵니다. 단위는 활성 \timescale지시문에서 옵니다.`timescale 1ns / 1ps라면 #5는 5 ns. `timescale 1us / 1ns라면 #5는 5 us. 수가 소수여도 됩니다 - 정밀도가 단위보다 곱다면 #1.5`가 동작합니다.

Verilog에서 #delay는 synthesizable인가요?

아니요. #delay는 시뮬레이션에만 영향을 미칩니다 - synthesis 도구가 무시하거나 거부합니다. 실제 하드웨어의 timing은 클럭 신호와 게이트 전파 지연에서 오지 # 문에서 오지 않습니다. testbench에서는 자유롭게 쓰고; synthesizable RTL에는 절대 쓰지 마세요.

Coddy programming languages illustration

Coddy로 코딩 배우기

시작하기