Day 1 · Welcome to Hardware Thinking

Synthesis vs. Simulation

Video 2 of 4 · ~15 minutes

Dr. Mike Borowczak · Electrical & Computer Engineering · CECS · UCF

HDL ≠ Software Synth vs Sim Module Anatomy Logic Refresher

One Source File, Two Consumers

module.v — your Verilog source

⚙️ Synthesis

"Turn this into hardware"

Yosys → netlist of real gates

🔍 Simulation

"Show me how it behaves"

Icarus Verilog → waveforms

Both consume the same .v file. They do completely different things with it.

The Open-Source iCE40 Toolchain

Two-path toolchain flowchart: synthesis and simulation

What Each Path Produces

Synthesis Output

Netlist — a circuit of real gates (LUTs, FFs)

Placement — which physical location on the chip

Routing — which wires connect them

Bitstream — binary file that configures the FPGA

Simulation Output

Waveforms — signal values over time

Text output — from $display

Pass/fail — from self-checking testbenches

VCD file — for GTKWave viewing

The Synthesizable Subset

Not everything in Verilog can become hardware.

Synthesizable

assign y = a & b;
always @(posedge clk)
    q <= d;
module, endmodule
wire, reg
if, case, for (fixed)

Simulation Only

#10          // delay
$display()   // print
$dumpfile()  // waveform dump
$finish      // end sim
initial      // no hardware equiv
$readmemh()  // file I/O*
Rule: Design code uses only the synthesizable subset. Testbench code can use everything.

The #10 Trap

// DANGER: this "works" in simulation...
always @(posedge clk) begin
    a <= 1'b1;
    #10;           // ← wait 10 time units
    a <= 1'b0;
end
Simulation: #10 pauses for 10 time units. It "works."
Synthesis: #10 is silently ignored. The behavior is completely different.
Result: Simulation passes, hardware fails. The worst kind of bug.
Never use #delay in synthesizable code. Not even "just for testing."

Your Day-to-Day Workflow

Write your Verilog module

Simulate it — does it behave correctly? (Icarus + GTKWave)

Synthesize it — does it fit? Does timing pass? (Yosys + nextpnr)

Program the FPGA — does it work on real hardware? (iceprog)

Always simulate first. Fixing bugs in simulation takes minutes. Debugging on hardware takes hours.

Your First Testbench

Step ② says "simulate it." But simulate it against what?

A testbench is a separate Verilog module that:

  Has no ports — it's the top of the simulation world

Instantiates your design (the "DUT" — Design Under Test)

Drives inputs and checks outputs

  Prints PASS / FAIL so you know immediately if something broke

You won't write testbenches from scratch until Week 2. For now you just need to read and run the ones we provide.

Reading a Testbench

// tb_button_logic.v — tests your button_logic module
`timescale 1ns / 1ps            // ← time units for simulation

module tb_button_logic;          // ← no ports!
    reg  sw1, sw2, sw3, sw4;    // ← inputs you control
    wire led1, led2, led3, led4; // ← outputs to check

    button_logic dut (           // ← your design goes here
        .i_switch1(sw1), .i_switch2(sw2),
        .i_switch3(sw3), .i_switch4(sw4),
        .o_led1(led1), ...
    );

    initial begin
        $dumpfile("dump.vcd");   // ← record waveforms
        $dumpvars(0, tb_button_logic);

        sw1=0; sw2=1; sw3=0; sw4=1; // ← drive inputs
        #1;                          // ← wait for logic to settle
        if (led1 === 1'b0) ...       // ← check with ===
    end
endmodule
Notice: reg, initial, #1, $dumpfileall sim-only constructs. A testbench will never become hardware.

Running a Testbench

# From any lab exercise directory:
make sim       # compile + run → prints PASS/FAIL
make wave      # opens GTKWave to inspect waveforms

What make sim does under the hood:

iverilog -g2012 -Wall -o sim.vvp tb_button_logic.v button_logic.v
vvp sim.vvp

iverilog compiles Verilog → simulator binary.  vvp runs it → prints output + writes VCD.

PASS: sw=0000 -> led=0001
PASS: sw=0011 -> led=1100
...
=== tb_button_logic: 16 passed, 0 failed ===
ALL TESTS PASSED
Green text, zero failures → safe to synthesize.

Your Hardware Platform

Nandland Go Board with labeled I/O

Everything you need: 4 LEDs, 4 buttons, dual 7-seg, VGA, UART via USB.
You'll get your board in class today.

🤖 Check the Machine

Ask an AI assistant: “I have an initial block that uses $display inside it. Will this affect my synthesized hardware?”

TASK

Ask about initial + $display in synthesis.

BEFORE

Your prediction: “$display is printing, so it must not synthesize — but initial might?”

AFTER

AI should explain: $display is ignored by synth; initial may set FF initial values on FPGAs (ignored on ASIC).

TAKEAWAY

Same source, two tools, different answers. Yosys strips sim-only constructs — verify with write_verilog.

Verify: Run yosys -p "read_verilog foo.v; synth_ice40; write_verilog synth_out.v" and grep for $display — it's gone. That's the one-command proof that synthesis ignores simulation directives.

Key Takeaways

  Same source file → two paths: synthesis (hardware) and simulation (behavior).

  Not all Verilog synthesizes. #delay, $display, initial are sim-only.

  A testbench drives your design's inputs, checks its outputs, and prints PASS/FAIL.

Always simulate firstmake sim before make prog.

🔗 Transfer

Anatomy of a Module

Day 1, Video 3 of 4 · ~12 minutes

▸ WHY THIS MATTERS NEXT

You now know that Verilog is consumed by two different tools. Next up: the structural shell every Verilog file lives inside — the module declaration. Every FPGA, every ASIC, every IP block in a modern SoC is made of modules. In Video 3 you'll write your first one, and it'll be the template for every design you write for the rest of this course.