% \comment{TODO: Describe ALU example (no code)}
\subsection{State}
- A very important concept in hardware it the concept of state. In a
+ A very important concept in hardware is the concept of state. In a
stateful design, the outputs depend on the history of the inputs, or the
state. State is usually stored in registers, which retain their value
during a clock cycle. As we want to describe more than simple
% This purity property is important for functional languages, since it
% enables all kinds of mathematical reasoning that could not be guaranteed
% correct for impure functions.
- Pure functions are as such a perfect match or a combinatorial circuit,
- where the output solely depends on the inputs. When a circuit has state
+ Pure functions are as such a perfect match for combinatorial circuits,
+ where the output solely depends on the inputs. When a circuit has state
however, it can no longer be simply described by a pure function.
% Simply removing the purity property is not a valid option, as the
% language would then lose many of it mathematical properties.
- In an effort to include the concept of state in pure
- functions, the current value of the state is made an argument of the
- function; the updated state becomes part of the result. In this sense the
- descriptions made in \CLaSH are the describing the combinatorial parts of
- a mealy machine.
+ In \CLaSH\ we deal with the concept of state in pure functions by making
+ current value of the state an additional argument of the function and the
+ updated state part of result. In this sense the descriptions made in
+ \CLaSH\ are the combinatorial parts of a mealy machine.
A simple example is adding an accumulator register to the earlier
multiply-accumulate circuit, of which the resulting netlist can be seen in
\Cref{img:mac-state}:
\begin{code}
- macS (State c) a b = (State c', outp)
+ macS (State c) a b = (State c', c')
where
- outp = mac a b c
- c' = outp
+ c' = mac a b c
\end{code}
\begin{figure}
The \hs{State} keyword indicates which arguments are part of the current
state, and what part of the output is part of the updated state. This
- aspect will also reflected in the type signature of the function.
+ aspect will also be reflected in the type signature of the function.
Abstracting the state of a circuit in this way makes it very explicit:
which variables are part of the state is completely determined by the
type signature. This approach to state is well suited to be used in
stateful descriptions using the recursive \hs{run} function:
\begin{code}
- run f s (i:inps) = o : (run f s' inps)
+ run f s (i : inps) = o : (run f s' inps)
where
(s', o) = f s i
\end{code}
- The \hs{run} function maps a list of inputs over the function that a
- developer wants to simulate, passing the state to each new iteration. Each
- value in the input list corresponds to exactly one cycle of the (implicit)
- clock. The result of the simulation is a list of outputs for every clock
- cycle. As both the \hs{run} function and the hardware description are
- plain Haskell, the complete simulation can be compiled by an optimizing
- Haskell compiler.
+ The \hs{(:)} operator is the list concatenation operator, where the
+ left-hand side is the head of a list and the right-hand side is the
+ remainder of the list. The \hs{run} function applies the function the
+ developer wants to simulate, \hs{f}, to the current state, \hs{s}, and the
+ first input value, \hs{i}. The result is the first output value, \hs{o},
+ and the updated state \hs{s'}. The next iteration of the \hs{run} function
+ is then called with the updated state, \hs{s'}, and the rest of the
+ inputs, \hs{inps}. Each value in the input list corresponds to exactly one
+ cycle of the (implicit) clock.
+
+ As both the \hs{run} function, the hardware description, and the test
+ inputs are plain Haskell, the complete simulation can be compiled to an
+ executable binary by an optimizing Haskell compiler, or executed in an
+ Haskell interpreter. Both simulation paths are much faster than first
+ translating the description to \VHDL\ and then running a \VHDL\
+ simulation, where the executable binary has an additional simulation speed
+ bonus in case there is a large set of test inputs.
\section{\CLaSH\ prototype}
id="path3994"
d="m 242.13,661.29 -0.01,-0.02 -0.02,-0.01 -0.01,-0.02 -0.02,-0.01 -0.01,-0.02 -0.01,-0.02 -0.01,-0.01 -0.02,-0.02 -0.01,-0.02 0,-0.01 -0.01,-0.02 -0.01,-0.01 -0.01,-0.02 0,-0.02 -0.01,-0.01 -0.01,-0.02 0,-0.01 0,-0.02 -0.01,-0.01 0,-0.02 -0.01,-0.01 0,-0.02 0,-0.01 0,-0.01 0,-0.02 0,-0.01 -0.01,-0.01 0,-0.01 0,-0.01 0,-0.01 0,-0.01 0,-0.01 c 0,-0.44 0.35,-0.63 0.62,-0.63 0.31,0 0.63,0.21 0.63,0.63 0,0.86 -1.16,0.92 -1.74,0.92 -1.78,0 -2.52,-1.15 -2.52,-2.31 0,-1.32 0.94,-2.27 2.47,-2.27 1.62,0 1.92,1.16 1.92,1.23 0,0.14 -0.14,0.14 -0.24,0.14 -0.18,0 -0.19,-0.02 -0.24,-0.15 -0.26,-0.63 -0.74,-0.82 -1.25,-0.82 -1.38,0 -1.38,1.47 -1.38,1.92 0,0.56 0,1.86 1.28,1.86 0.35,0 0.52,-0.03 0.65,-0.06 z"
style="fill:#000000;stroke-width:0" />
+</g> <g
+ id="g3387"
+ transform="matrix(1,0,0,-1,213.25,1264.2792)"
+ xml:space="preserve"
+ stroke-miterlimit="10.433"
+ font-style="normal"
+ font-variant="normal"
+ font-weight="normal"
+ font-stretch="normal"
+ font-size-adjust="none"
+ letter-spacing="normal"
+ word-spacing="normal"
+ ns0:text="$\\mathit{c}$\n\n"
+ ns0:preamble=""
+ style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;letter-spacing:normal;word-spacing:normal;text-anchor:start;fill:none;stroke:#000000;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:10.43299961;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0">
+<path
+ d="m 227.77,660.99 -0.03,-0.01 -0.02,0 -0.02,0 -0.02,-0.01 -0.02,0 -0.02,-0.01 -0.02,0 -0.02,-0.01 -0.02,-0.01 -0.01,0 -0.02,-0.01 -0.01,-0.01 -0.02,-0.01 -0.01,0 -0.02,-0.01 -0.01,-0.01 -0.01,-0.01 -0.02,-0.01 -0.01,-0.01 -0.01,-0.01 -0.01,-0.01 -0.01,-0.01 -0.02,-0.02 -0.02,-0.02 -0.01,-0.02 -0.02,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 0,-0.02 -0.01,-0.02 0,-0.02 0,-0.01 -0.01,-0.02 0,-0.01 0,-0.01 0,-0.02 0,0 0,-0.01 0,0 0,-0.01 0,0 0,0 c 0,-0.16 0.11,-0.32 0.34,-0.32 0.27,0 0.51,0.22 0.51,0.6 0,0.49 -0.43,0.86 -1.07,0.86 -1.24,0 -2.52,-1.42 -2.52,-2.87 0,-0.99 0.59,-1.65 1.46,-1.65 1.28,0 2.11,1 2.11,1.15 0,0.05 -0.09,0.16 -0.16,0.16 -0.04,0 -0.05,-0.01 -0.13,-0.11 -0.74,-0.94 -1.63,-0.98 -1.8,-0.98 -0.53,0 -0.78,0.45 -0.78,1.03 0,0.53 0.26,1.57 0.52,2.05 0.36,0.65 0.86,1 1.31,1 0.11,0 0.56,-0.02 0.71,-0.43 z"
+ id="path3389"
+ style="fill:#000000;stroke-width:0" />
+</g> <g
+ style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;letter-spacing:normal;word-spacing:normal;text-anchor:start;fill:none;stroke:#000000;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:10.43299961;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
+ ns0:preamble=""
+ ns0:text="$\\mathit{c\'}$\n\n\n"
+ word-spacing="normal"
+ letter-spacing="normal"
+ font-size-adjust="none"
+ font-stretch="normal"
+ font-weight="normal"
+ font-variant="normal"
+ font-style="normal"
+ stroke-miterlimit="10.433"
+ xml:space="preserve"
+ transform="matrix(1,0,0,-1,261.73,1253.7692)"
+ id="g3471">
+<path
+ id="path3473"
+ d="m 227.77,660.99 -0.03,-0.01 -0.02,0 -0.02,0 -0.02,-0.01 -0.02,0 -0.02,-0.01 -0.02,0 -0.02,-0.01 -0.02,-0.01 -0.01,0 -0.02,-0.01 -0.01,-0.01 -0.02,-0.01 -0.01,0 -0.02,-0.01 -0.01,-0.01 -0.01,-0.01 -0.02,-0.01 -0.01,-0.01 -0.01,-0.01 -0.01,-0.01 -0.01,-0.01 -0.02,-0.02 -0.02,-0.02 -0.01,-0.02 -0.02,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 -0.01,-0.02 0,-0.02 -0.01,-0.02 0,-0.02 0,-0.01 -0.01,-0.02 0,-0.01 0,-0.01 0,-0.02 0,0 0,-0.01 0,0 0,-0.01 0,0 0,0 c 0,-0.16 0.11,-0.32 0.34,-0.32 0.27,0 0.51,0.22 0.51,0.6 0,0.49 -0.43,0.86 -1.07,0.86 -1.24,0 -2.52,-1.42 -2.52,-2.87 0,-0.99 0.59,-1.65 1.46,-1.65 1.28,0 2.11,1 2.11,1.15 0,0.05 -0.09,0.16 -0.16,0.16 -0.04,0 -0.05,-0.01 -0.13,-0.11 -0.74,-0.94 -1.63,-0.98 -1.8,-0.98 -0.53,0 -0.78,0.45 -0.78,1.03 0,0.53 0.26,1.57 0.52,2.05 0.36,0.65 0.86,1 1.31,1 0.11,0 0.56,-0.02 0.71,-0.43 z"
+ style="fill:#000000;stroke-width:0" />
+<path
+ id="path3475"
+ d="m 230.6,664.14 0.01,0.01 0,0.01 0,0.01 0.01,0.01 0,0.01 0.01,0.01 0,0.01 0,0.01 0.01,0.01 0,0 0,0.01 0,0.01 0.01,0.01 0,0 0,0.01 0,0.01 0,0 0.01,0.01 0,0.01 0,0 0,0.01 0,0 0,0.01 0,0 0,0.01 0,0.01 0,0.01 0,0.01 c 0,0.22 -0.19,0.39 -0.41,0.39 -0.26,0 -0.35,-0.22 -0.38,-0.33 l -0.92,-3.02 c -0.01,-0.01 -0.04,-0.11 -0.04,-0.11 0,-0.09 0.22,-0.16 0.27,-0.16 0.05,0 0.06,0.02 0.11,0.12 z"
+ style="fill:#000000;stroke-width:0" />
</g> </g>
</svg>