====== Statements ======
//Statements// are the Arx language elements that are found in a
[[component]] description or a [[function]] declaration
between the keywords ''begin'' and ''end''. In this section, the
different type of statements are presented.
===== Assignment =====
The assignment statement is used to specify a new value for a signal,
where a signal is either a register or variable (see the page on
[[declarations]]). An assignment has the following syntax:
=
So, the equal sign (''='') indicates that the [[expressions|expression]] specified
at its right-hand side should become the new value of the signal
specified at its left-hand side. Here are some examples of assignment
statements:
sum = left + right
storage = storage + convert(T_narrow, data_in)
The left-hand side is either a //variable// signal or a //register//
signal. //Variable// signals need to be assigned first before they can
be used in an expression. So, as far as variable assignment is
concerned, Arx behaves as a sequential language.
//Register// signals can be used without
restrictions. An assignment specifies the value of that signal in the
next clock cycle.
In the presentation about Arx [[datatypes|data types]], examples can
be found of assignments involving individual bits in a vector, ranges
of bits and array elements.
===== If statement =====
An ''if'' statement is used to specify conditional computations. The
value of a //Boolean condition// determines
which one of the two provided computations should be chosen. An ''if''
statement corresponds to a multiplexer in hardware. The syntax of an
''if'' statement is as follows:
if
*{ elif
}*
-{ else
}-
end
Here is a fragment of Arx code that uses an ''if'' statement.
if data_in > 10
newval = data_in - 10
elif data_in > 20
newval = data_in - 15
else
newval = data_in
end
The fragment below illustrates that Arx is not a strict
single-assignment language. A variable may be assigned twice an
expression. A coding style where
the assignment is first performed unconditionally and
later inside an ''if'' statement without ''else'' branch, can save
many lines of code in complex situations with many nested conditional
statements.
It is, however, preferable to write single-assignment
code to stay as closely as possible to the semantics of hardware where
a wire cannot be both an input and an output of some computation
without creating an algebraic loop.
newval = data_in
if newval > 10
newval = newval - 10
end
===== Case statement =====
Whereas ''if'' statements are appropriate to model conditional
computations where the outcome of some expression has a Boolean value,
the ''case'' statement is used to model situations where the outcome
of some expression has usually more than the two values that determine
the flow of computation. Typical uses of ''case'' statements are found
in the descriptions of finite state machines or truth-table-style
specifications.
The ''case'' statement has the following syntax.
case
+{ when
}+
-{ else
}-
end
The expressed behavior states that should be evaluated
first. The ''when'' clause the of which matches the result of
the evaluation is then selected and its associated is then
performed. It may be that none of the ''when'' clauses matches in
which case the belonging to the ''else'' clause is
executed, if present.
The example below shows a typical next-state computation
in a finite-state machine. The register signal ''output_state'' is of
[[datatypes|enumeration type]] ''out_state''.
case output_state
when out_state.start
if start_of_processing
output_state = out_state.processing
end
when out_state.processing
if end_of_processing
output_state = out_state.ready
end
else # default case; no action
end
The next fragment of code shows a ''case'' statement to model a
truth-table style in which a number ''num_in'' is mapped onto a number ''num_out'':
case num_in
when 0
num_out = 3
when 1
num_out = 2
when 2
num_out = 0
else
num_out = 1
end
===== For statement =====
A ''for'' statement is used to indicate regularity in some
computation. It implies repetition in //space// as opposed to
repetition in //time// that is normally designated in traditional
imperative programming languages. All computations in a ''for
statement'' take place within a single clock cycle, the same way that
any component body is computed in one clock cycle. The ''for''
statement has the following syntax:
for in :
+{
}+
end
The is an integer that does not need to be declared.
The statements specified in the body of the ''for'' statement are
supposed to be executed as many times as there are integers between
the given lower and upper bounds (inclusive). The bounds should be
//manifest// or //data independent//, which means that they may be
either constants or expressions the values of which can be computed at
compile time. An example of a ''for'' statement is given below:
for i in 1:half_size
delay_group[i] = delay_line[half_size-i] + delay_line[half_size+i]
end