Clash is a functional hardware description language that borrows both its syntax and semantics from the functional programming language Haskell. It provides a familiar structural design approach to both combinational and synchronous sequential circuits. The Clash compiler transforms these high-level descriptions to low-level synthesizable VHDL, Verilog, or SystemVerilog.

Clash is an open-source project, licensed under the permissive BSD2 license, and actively maintained by QBayLogic. The Clash project is a Haskell Foundation affiliated project.

GitLab pipeline status badge Hackage version badge GitHub commit activity badge

Features

Strongly typed

Clash is built on Haskell which provides an excellent foundation for well-typed code. Together with Clash's standard library it is easy to build scalable and reusable hardware designs.

Interactive REPL

Load your designs in an interpreter and easily test all your component without needing to setup a test bench.

Low-level access

Although Clash offers many features, you sometimes need to directly access VHDL, Verilog, or SystemVerilog directly. Clash allows you to do this with its own templating system.

Get the book: Retrocomputing with Clash

Haskell has become the functional programming language of choice for many developers due to its excellent tools for abstraction and principled program design. The open source Clash hardware description language now brings these features to FPGA development.

Retrocomputing with Clash takes the experienced Haskell programmer on a journey into the world of hardware design with Clash. Our approach is based on using Haskell to its fullest potential, using abstractions like monads and lenses in building a library of reusable components.

Implement various retro-computing devices:
  • Pocket calculator
  • Pong (sample chapter)
  • An implementation of the CHIP-8 virtual computer specification
  • Intel 8080 CPU
  • Space Invaders arcade machine
  • Compucolor II, a home computer from 1977 complete with keyboard, color video, and a floppy drive

Examples

FIR Filter

Clash allows programmers to write function without hardcoded length or element type information, such as this FIR filter:

fir coeffs x = dotp coeffs (window x)
  where
    dotp as bs = sum (zipWith (*) as bs)

Clash will figure out the type of this function through its powerful type inference system. To "lock" types in place, we can partially apply `fir`:

-- inferred: Signal dom Int -> Signal dom Int
fir3int = fir (3 :> 4 :> 5 :> Nil)

-- inferred: Signal dom Float -> Signal dom Float
fir4float = fir (3.5 :> 4.2 :> 3.0 :> 6.1 :> Nil)

Matrix multiplication

If you do choose to write types explicitly, you can add additional constraints. Clash will check these constraints and refuse to compile if they are not met. The following example implements a fully parallel matrix multiplication algorithm:

mmult
  -- Dimension constraints:
  :: na ~ mb
  => 1 <= mb
  
  -- Allow simulation to access mb/nb:
  => KnownNat mb
  => KnownNat nb
  
  -- Arguments:
  => Vec ma (Vec na Int)
  -> Vec mb (Vec nb Int)
  
  -- Result:
  -> Vec ma (Vec nb Int)

mmult mA mB = result
  where
    mBT      = transpose mB
    dot a b  = sum $ zipWith (*) a b
    result   = map (\ar -> dot ar <$> mBT) mA

Open-source community

Clash benefits from an active community. Whether you need a question answered or want to contribute to open-source features, browse the features below to make the most of Clash. We expect participants on these public forums to observe our Guidelines for Respectful Communication.

Mailing list
Issue tracker
Slack: functionalprogramming.slack.com#clash (Invite yourself at fpslack.com)
IRC (webchat): libera.chat#clash (or ircs://irc.libera.chat:6697/clash when you want to connect with a regular IRC client)

Support

If you need professional support from the original developers of Clash, check out the support plan.