ModMultiSim help v3.07 - 5.2. Phrase Structure
Download manual: HTML
An expression is a sequence of operators and operands that specifies the computation of a value.
The precedence of operators decreases from the top of the list of operators (see the "Operators" section under Lexical Structure section), to the bottom. So the primary_expr operator has highest precedence and the logical_or has the lowest. The unary_sign ( ) operators have higher precedence than the binary_sign ( ) operators.
Operators on the same line in the list of operators have the same precedence.
For binary operators with the same precedence, evaluation occurs from left to right.
The ModMultiSim compiler evaluates operands of the mathematically associative and commutative operators
in the order in which they appear (i.e. it does not rearrange the order of evaluating several additions, multiplications or bitwise operations at the same level).The usual arithmetic conversions are performed.
-
- grouping operator
primary_expr:
identifier
constant
left_parenth bitwise_expr right_parenth
left_parenth :
right_parenth :
Use the left_parenth and right_parenth operators to signal the start and end of the expression to be evaluated. This will change the order of evaluation, or simply clarify the order if it is the same as the order would be without the . For example:
3 * ($4 - 10) / 2
will cause ModMultiSim to do the subtraction before the multiplication or division.
-
- complement operator
bitwise_complement_expr:
bitwise_complement ? primary_expr
bitwise_complement :
The bitwise_complement operator manipulates bits in integer types. (This description assumes an understanding of the way integers are represented in binary.)
The bitwise_complement operator has only one operand, which must have arithmetic type. If the operator is applied to a float or double, it will be converted to an integer first.
The
operator returns the complement of its operand, that is to say, it converts each bit containing a 1 to zero and vice versa. As the next example shows, taking the complement of -1 yields the result 0 since -1 is represented in binary as 16 1s (in an integer of size 16 bits). The second example yields the result 8, when doing the complement of -9. (This will be clearer if you are familiar with the representation of numbers in binary.)~(-1): 1111111111111111 : -1 0000000000000000 : result 0
~(-9): 1111111111110111 : -9 0000000000001000 : result 8
In a bitwise_complement_expr the bitwise_complement operator is optional.
For ways to use the bitwise_complement operator see Handling Control/Status Flags in Holding/Input registers.
-
- multiplicative operators
term_expr :
bitwise_complement_expr {multiplier bitwise_complement_expr}*
multiplier : | |
The
operator returns the product of its operands.The
operator returns the quotient from the division of the first operand by the second.The
operator returns the remainder from the division of the first operand by the second.Both operands of these operators must have arithmetic type.
In a term_expr there may be zero or more of the multiplier bitwise_complement_expr expressions. For example, the following are all valid term_exprs:
4 * 9 4 * 9 / (3 / 6)* 8 4 * 9 / (3 / 6 *(8 * 9 /2))* 8
-
- additive operators
numeric_expr :
unary_sign? term_expr {binary_sign term_expr}*
unary_sign : |
binary_sign : |
The unary_sign operators have one operand. The unary_sign operator returns the value of its operand (i.e. it has no affect). The unary_sign operator returns the negative of its operand.
The binary_sign operators have two operands, both of arithmetic type. The binary_sign operator returns the sum of its operands. The binary_sign operator returns the difference between the operands.
In a numeric_expr the unary_sign is optional. There may be zero or more of the binary_sign term_exprs. For example, the following are all valid numeric_exprs:
-4 - 9 -4 + (9 +-3) / 8 * 6
-
- shift operators
bitwise_shift_expr :
numeric_expr {bitwise_shift numeric_expr}*
bitwise_shift : |
The bitwise_shift operators manipulate bits in integer types. If applied to a float or double, it will be converted to an integer first. (This description assumes an understanding of the way integers are represented in binary.)
The bitwise_shift operators have two operands, both of arithmetic type. These operators shift their left operands by the number of bit positions specified by their right operand.
The
operator shifts the bits to the left and fills vacated bits on the right with 0s. The operator shifts the bits to the right and fills the vacated bits on the left with 0s if the left operand is positive, or it fills it with 1s if the left operand is negative (this is to preserve the sign).In the following example, the result of the shift is 28 (shifting to the left by 2 is the same as multiplying by 4 and shifting to the right by 2 is the same as dividing 4). The binary representation below shows the shift.
7 << 2: 0000000000000111 : 7 0000000000011100 : result 28
There may be zero or more of the bitwise_shift numeric_exprs. For example, the following are valid bitwise_shift_exprs:
7 << 2 + $12 + ~($201 / 2) 7 << 2 << $1
For ways to use the bitwise_shift operators see Handling Control/Status Flags in Holding/Input registers.
-
- bitwise-and operator
bitwise_and_expr :
bitwise_shift_expr {bitwise_and bitwise_shift_expr}*
bitwise_and :
This operator manipulates bits in integer types. If applied to a float or double, it will be converted to an integer first. (This description assumes an understanding of the way integers are represented in binary.)
The bitwise_and operator has two operands, both of arithmetic type. It sets bits to 1 only if the value of the corresponding bit in both left and right operands is 1.
For example, the following expression yields 0 since none of the corresponding bit positions in the binary representation of 6 and 8 are both 1.
6 & 8: 0000000000000110 : 6 0000000000001000 : 8 0000000000000000 : result 0
In the next example, the result is 4 since the third bit position in each operand is a 1-bit, so will be set to 1 in that bit position, which is 4 in decimal radix.
6 & 4 0000000000000110 : 6 0000000000000100 : 4 0000000000000100 : result 4
There may be zero or more of the bitwise_and bitwise_shift_exprs. For example, the following are valid bitwise_and_exprs:
7 & 2 & $7000 5 & $1 << 1 & ($6 - 1)
For ways to use the bitwise_and operator see Handling Control/Status Flags in Holding/Input registers.
-
- bitwise-or operators
bitwise_expr :
bitwise_and_expr {bitwise_or bitwise_and_expr}*
bitwise_or :
inclusive_or
exclusive_or
inclusive_or :
exclusive_or :
The bitwise_or operators manipulate bits in integer types. If applied to a float or double, it will be converted to an integer first. (This description assumes an understanding of the way integers are represented in binary.)
These operators have two operands, both of arithmetic type.
The inclusive_or operator sets a bit to 1 if the value of the bit in the same bit-position of either or both operands is 1.
The exclusive_or operator sets a bit to 1 if the bit-position is set to 1 in one of the operands and only one.
In the following example, the result of the inclusive-or is 12 since 1 is set in the bit-positions that represent 8 in one operand and 1 is set for the bit-position that represents 4 in the other operand.
8 | 4: 0000000000001000 : 8 0000000000000100 : 4 0000000000001100 : result 12
In the next example the result is zero since both operands have the same bit-position set to 1.
8 ^ 8: 0000000000001000 : 8 0000000000001000 : 8 0000000000000000 : result 0
There may be zero or more of the bitwise_or bitwise_and_exprs. For example, the following are all valid bitwise_exprs:
12 | $4 | $7000 6 ^ 6 ^ 4 5 | $12 >> 1 ^ (($6 << 1) & $1)
For ways to use the bitwise_or operators see Handling Control/Status Flags in Holding/Input registers.
-
- relation operators
comparison_expr:
bitwise_expr relation bitwise_expr
relation:
less_than
greater_than
not_greater_than
not_less_than
equal_to
not_equal_to
less_than :
greater_than :
not_greater_than :
not_less_than :
equal_to :
not_equal_to :
Both operands of these operators must have arithmetic type. The operators returns true if the relation is true, otherwise false.
A comparison_expr occurs in the controlling expression within a selection_statement.
-
- negation operator
relational_term_expr:
logical_not? relational_primary_expr
relational_primary_expr:
comparison_expr
left_parenth relational_expr right_parenth
logical_not :
A relational_term_expr may be preceded by logical_not. The operator has only one operand, which must be boolean type. It returns true if the value of the relational_primary_expr is false, and false otherwise. In the example that follows, the parentheses are not necessary - they are there to aid clarity:
!($23 / 60 > $12)
-
- conjunction operator
conjunction_expr :
relational_term_expr {logical_and relational_term_expr}*
logical_and :
Both operands must have boolean type. The operator returns true if both operands are true, otherwise false.
There may be zero or more of the logical_and relational_term_exprs. For example:
$23 / 60 > $12 && !($4 == 100) && (5 > 6 )
-
- disjunction operator
relational_expr:
conjunction_expr {logical_or conjunction_expr}*
logical_or :
Both operands of the
operator have boolean type. The operator returns true if either operand is true, otherwise false.There may be zero or more of the logical_or relational_term_exprs. For example:
$5 > $2 || $64 < $65 || (CycleTime > 1 || $2 == $9)
statement:
expr_statement
selection_statement
A statement denotes an action to be performed. The only ModMultiSim actions are the assignment of a value to a register or environment property (see expr_statement) and the selection of an action based on an evaluation (see selection_statement).
-
expr_statement:
bitwise_expr
The expr_statement is an assignment statement: the value of the expression is assigned to the register or environment property for which it is a statement.
-
selection_statement:
relational_expr statement
relational_expr statement statement
The expression after the if must have boolean type. If the expression after the if is true, then the statement after then is executed. If false, then in the first form of the selection_statement, no action is taken, and in the second, the statement after else is executed. An is connected to the last without an . Note that the grammar allows nested selection statements, as in:
if (($62 % 3600) == 0) then if ($1 + $4) > $5 then 0 else $1 + $4 else $5