Skip to content

Course: Clocks, resets and clock-domain crossing (9x3, hardware track) #1482

Description

@gHashTag

Parent epic: #1476

Course id: clocks-and-cdc
Audience: hardware engineers (RTL / FPGA / ASIC).
Prerequisites: Course 1 (FPGA) modules timing and board.

Why this course

Most field failures in FPGA designs are not logic bugs but clocking bugs: a missing synchronizer, a reset released on the wrong edge, a FIFO pointer crossing domains in binary. The repo already has clock_domain, cts, fifo (gray pointers), timing and XDC emission, yet no course explains them. This is the course a hardware hiring manager asks about first.

What already exists in the repo (grounding)

  • fpga/clock_domain.t27 + testbench/clock_domain_tb.t27 (12 tests, currently fail in the browser runner)
  • fpga/cts.t27, fpga/fifo.t27 + fifo_tb (18 tests), fpga/timing.t27
  • pins/emitter_xdc.t27, pins/ir.t27, boards/arty_a7.t27, boards/wukong_v1.t27
  • tools/trios/tri/clocks.t27, fpga-rxcap.t27 (real captured traffic)
  • fpga/vcd_trace.t27 for waveforms

Decomposition: 9 modules x 3 lessons

Module 1 -- what-a-clock-is: the clock as a contract

# Lesson id What the reader learns Spec Widget idea
1 one-edge-one-world why synchronous design works: one edge, one state update fpga/clock_domain.t27 edge stepper: click an edge, watch every flop update at once
2 period-and-jitter period, frequency, duty cycle, jitter budget tools/trios/tri/clocks.t27 jitter eye drawn from a real capture
3 where-the-clock-enters clock-capable pins, the board oscillator, IBUF to BUFG boards/wukong_v1.t27 pin-map highlighting the clock-capable balls

Module 2 -- clock-trees: distributing one edge to every flop

# Lesson id What the reader learns Spec Widget idea
4 skew-and-insertion skew vs insertion delay, why a tree and not a wire fpga/cts.t27 tree builder with per-leaf delay
5 global-buffers BUFG / BUFR / BUFH and clock regions on 7-series fpga/cts.t27 clock-region map of the XC7A200T
6 gated-clock-trap why gating a clock in fabric breaks timing; use a clock enable fpga/clock_domain.t27 side-by-side: gated clock vs CE, glitch shown

Module 3 -- pll-and-mmcm: making new clocks

# Lesson id What the reader learns Spec Widget idea
7 multiply-and-divide VCO range, M/D/O dividers, legal settings NEW fpga/mmcm.t27 MMCM calculator with legality checks as spec tests
8 phase-and-lock phase shift, LOCKED, holding logic in reset until lock NEW fpga/mmcm.t27 lock timeline
9 related-or-not when two clocks are related (same MMCM) vs asynchronous fpga/timing.t27 relation table derived from the spec

Module 4 -- resets: starting from a known state

# Lesson id What the reader learns Spec Widget idea
10 sync-or-async synchronous vs asynchronous reset, cost on 7-series flops NEW fpga/reset_sync.t27 LUT/FF count from a yosys run, both styles
11 reset-release async assert, sync deassert; the reset synchronizer NEW fpga/reset_sync.t27 wave: release near the edge, with and without sync
12 reset-fanout reset trees, why fewer resets is often better fpga/cts.t27 fanout histogram from a real netlist

Module 5 -- metastability: what happens between 0 and 1

# Lesson id What the reader learns Spec Widget idea
13 setup-hold-window the forbidden window and what a flop does inside it fpga/clock_domain.t27 window slider: data edge vs clock edge
14 mtbf MTBF formula, why two flops buy centuries NEW fpga/mtbf.t27 (numbers as spec tests) MTBF calculator, log scale
15 two-flop-sync the standard synchronizer and the ASYNC_REG attribute fpga/clock_domain.t27 netlist view with ASYNC_REG placement

Module 6 -- crossing-many-bits: when one synchronizer is not enough

# Lesson id What the reader learns Spec Widget idea
16 why-binary-fails multi-bit skew: binary counter read mid-change fpga/fifo.t27 glitch sampler showing impossible values
17 gray-code one bit changes at a time; bin2gray / gray2bin fpga/fifo.t27 gray counter next to binary counter
18 handshakes-and-pulses req/ack handshake, pulse synchronizer, toggle sync fpga/clock_domain.t27 two-domain timeline

Module 7 -- async-fifo: the workhorse of CDC

# Lesson id What the reader learns Spec Widget idea
19 pointers-and-flags write/read pointers, full and empty in gray fpga/fifo.t27 FIFO animation with both pointers
20 depth-sizing how deep: burst length, rate ratio, latency fpga/fifo.t27 depth calculator, spec tests as sizing rules
21 fifo-testbench what fifo_tb checks and what it does not fpga/testbench/fifo_tb.t27 test-waves of the tb run

Module 8 -- constraints: telling the tool what you meant

# Lesson id What the reader learns Spec Widget idea
22 create-clock create_clock, generated clocks, from spec to XDC pins/emitter_xdc.t27 spec -> XDC diff
23 false-path-and-max-delay set_false_path vs set_max_delay -datapath_only, clock groups fpga/timing.t27 constraint picker explaining what each hides
24 io-timing input/output delays, the RGMII-style source-synchronous case pins/emitter_xdc.t27 IO timing diagram

Module 9 -- on-the-board: proof on hardware

# Lesson id What the reader learns Spec Widget idea
25 cdc-report reading a CDC / timing report from the open flow fpga/timing.t27 slack-waterfall per clock domain
26 capture-a-crossing capturing a real crossing on the board tools/trios/tri/fpga-rxcap.t27 captured trace replay
27 capstone build a two-clock design with an async FIFO, prove it on the board fpga/fifo.t27 + fpga/clock_domain.t27 build receipt with both clocks

Specs that do not exist yet (write in gHashTag/t27 first)

  • fpga/mmcm.t27 -- MMCM/PLL parameter legality (VCO range, dividers) as tests
  • fpga/reset_sync.t27 -- reset synchronizer
  • fpga/mtbf.t27 -- MTBF model with documented constants

Honesty notes and traps

  • MTBF numbers depend on flop parameters that Xilinx publishes only partially; label any constant as an assumption with its source.
  • Course 1 already touches timing slack and cts.t27 (lesson timing-slack points at cts.t27); this course goes deeper and Course 1 should link here instead of duplicating.

Acceptance criteria

  • specs/course/<id>.t27 + <id>-ru.t27 exist, registered in specs/course/courses.t27, built by course-from-spec.mjs (recipe: specs/course_recipe/course-27.t27).
  • Exactly 9 modules x 3 lessons = 27 lessons; every lesson names one widget and one spec.
  • Every lesson spec compiles AND its test blocks pass in the reader's browser (blocked by the browser-runner issue), or the lesson says plainly that it is a recorded tri cast and links the recording.
  • Every number on a page comes from real tool output named in the widget's DATA_SOURCES (yosys / nextpnr / board run / spec test). No invented figures.
  • Board named on every hardware page (Wukong xc7a200tfgg676 vs AX7203 xc7a200tfbg484 vs Arty A7 / XC7A100T).
  • Black-and-white share cards and SEO pages generated for all 27 lessons (EN + RU).
  • The course PR carries a blog post: EN body + RU ruBody.
  • Lessons that need a spec that does not exist yet are listed as sub-tasks (spec first in gHashTag/t27, then copied here).

Blocked by: #1477 (browser test runner) for every lesson whose spec uses calls, locals or struct fields in tests.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions