Commit 2676022d authored by Maxime Perrotin's avatar Maxime Perrotin
Browse files

Support substrings in ternary operator

parent 224b89b1
......@@ -844,8 +844,10 @@ def write_statement(param, newline):
elif type_kind in ('IntegerType', 'RealType',
'BooleanType', 'Integer32Type'):
code, string, local = expression(param)
if type_kind in ('IntegerType', 'Integer32Type'):
if type_kind == 'IntegerType':
cast = "Asn1Int"
elif type_kind == 'Integer32Type':
cast = "Integer"
elif type_kind == 'RealType':
cast = 'Long_Float'
elif type_kind == 'BooleanType':
......@@ -1207,7 +1209,7 @@ def _prim_call(prim):
range_str = u"{}'Length".format(param_str)
else:
range_str = u"{}.Length".format(param_str)
ada_string += ('Asn1Int({})'.format(range_str))
ada_string += ('Integer({})'.format(range_str))
elif ident == 'present':
# User wants to know what CHOICE element is present
exp = params[0]
......@@ -1775,13 +1777,37 @@ def _conditional(cond):
local_decl.extend(then_local)
local_decl.extend(else_local)
stmts.append(u'if {if_str} then'.format(if_str=if_str))
stmts.append(u'tmp{idx} := {then_str};'.format(
idx=cond.value['tmpVar'],
then_str=then_str))
basic_then = find_basic_type(cond.value['then'].exprType)
basic_else = find_basic_type(cond.value['else'].exprType)
if isinstance(cond.value['then'],
(ogAST.PrimSequenceOf, ogAST.PrimStringLiteral)):
then_str = array_content(cond.value['then'], then_str, basic_then)
if isinstance(cond.value['else'],
(ogAST.PrimSequenceOf, ogAST.PrimStringLiteral)):
else_str = array_content(cond.value['else'], else_str, basic_else)
if isinstance(cond.value['then'], ogAST.PrimSubstring):
stmts.append(u"tmp{idx}.Data(1..{then_str}'Length) := {then_str};"
.format(idx=cond.value['tmpVar'], then_str=then_str))
if basic_then.Min != basic_then.Max:
stmts.append(u"tmp{idx}.Length := {then_str}'Length;"
.format(idx=cond.value['tmpVar'], then_str=then_str))
else:
stmts.append(u'tmp{idx} := {then_str};'
.format(idx=cond.value['tmpVar'], then_str=then_str))
stmts.append('else')
stmts.append(u'tmp{idx} := {else_str};'.format(
idx=cond.value['tmpVar'],
else_str=else_str))
if isinstance(cond.value['else'], ogAST.PrimSubstring):
stmts.append(u"tmp{idx}.Data(1..{else_str}'Length) := {else_str};"
.format(idx=cond.value['tmpVar'], else_str=else_str))
if basic_else.Min != basic_else.Max:
stmts.append(u"tmp{idx}.Length := {else_str}'Length;"
.format(idx=cond.value['tmpVar'], else_str=elsn_str))
else:
stmts.append(u'tmp{idx} := {else_str};'.format(
idx=cond.value['tmpVar'],
else_str=else_str))
stmts.append('end if;')
ada_string = u'tmp{idx}'.format(idx=cond.value['tmpVar'])
return stmts, unicode(ada_string), local_decl
......
......@@ -605,7 +605,8 @@ class Symbol(QObject, QGraphicsPathItem, object):
''' Collision Avoidance Manoeuvre for top level symbols '''
# Since the cam function is recursive it may be time consuming
# Call the Qt event prcessing to avoid blocking the application
QApplication.processEvents()
# Removed (had bad visual side effects)
# QApplication.processEvents()
ignore = ignore or []
if not self.scene():
# Make sure the item is in a scene. For instance, when loading
......
......@@ -1033,6 +1033,8 @@ def fix_expression_types(expr, context):
check_expr.right = expr.right.value[det]
fix_expression_types(check_expr, context)
expr.right.value[det] = check_expr.right
# Set the type of "then" and "else" to the reference type:
expr.right.value[det].exprType = expr.left.exprType
if expr.right.is_raw != expr.left.is_raw:
check_type_compatibility(raw_expr, ref_type, context)
......@@ -1609,8 +1611,9 @@ def primary_substring(root, context):
'Max':
str(int(max1) - int(min0) + 1)})
basic = find_basic_type(node.exprType)
if int(min0) > int(min1) or int(max0) > int(max1):
msg = 'Substring bounds are invalid'
if int(min0) < int(min1) or int(max0) > int(max1):
msg = 'Substring bounds are invalid ({}<{} or {}>{})'.format(
min0, min1, max0, max1)
errors.append(error(root, msg))
if int(min0) > int(receiver_bty.Max) \
or int(max1) > int(receiver_bty.Max):
......
include ../shared.mk
all: test-ada test-llvm
edit:
$(OPENGEODE) og.pr
test-parse:
$(OPENGEODE) og.pr --check
test-ada:
$(OPENGEODE) og.pr --toAda
$(ASN1SCC) -Ada dataview.asn -typePrefix asn1Scc -equal
$(GNATMAKE) -O$(O) -c *.adb
$(GNATBIND) -n og.ali
test-c:
$(OPENGEODE) og.pr --toC
$(ASN1SCC) -c dataview.asn -typePrefix asn1Scc -equal
$(CC) -O$(O) -c *.c
test-llvm:
$(OPENGEODE) og.pr --llvm -O$(O)
$(LLC) *.ll
$(CC) -O$(O) -c *.s
coverage:
coverage run -p $(OPENGEODE) og.pr --toAda
.PHONY: all edit test-parse test-ada test-llvm coverage
TASTE-Dataview DEFINITIONS ::=
BEGIN
SeqOf ::= SEQUENCE (SIZE(0..10)) OF BoolType
BoolType ::= BOOLEAN
END
SYSTEM og;
/* CIF TEXT (159, 221), (289, 188) */
-- Text area for declarations and comments
use dv comment 'dataview.asn';
signal run;
signal saved_signal(BoolType);
signal we;
/* CIF ENDTEXT */
CHANNEL c
FROM ENV TO og WITH run,
saved_signal;
FROM og TO ENV WITH we;
ENDCHANNEL;
BLOCK og;
SIGNALROUTE r
FROM ENV TO og WITH run,
saved_signal;
FROM og TO ENV WITH we;
CONNECT c AND r;
/* CIF PROCESS (225, 50), (150, 75) */
PROCESS og;
/* CIF TEXT (335, 58), (396, 136) */
-- Demonstrate how to simulate the behaviour of the SAVE
-- signal. The actual SAVE implies dynamic memory allocation.
-- But using a controlled-size array and a continuous signal it
-- is easy to reproduce the same behaviour.
dcl save_buffer SeqOf;
dcl param BoolType;
/* CIF ENDTEXT */
/* CIF START (0, 226), (70, 35) */
START;
/* CIF NEXTSTATE (0, 276), (70, 35) */
NEXTSTATE wait;
/* CIF STATE (291, 227), (70, 35) */
STATE wait;
/* CIF INPUT (91, 282), (84, 35) */
INPUT run;
/* CIF NEXTSTATE (79, 332), (107, 35) */
NEXTSTATE Running;
/* CIF INPUT (296, 282), (162, 35) */
INPUT saved_signal(param);
/* CIF DECISION (296, 332), (161, 50) */
DECISION length(save_buffer);
/* CIF ANSWER (253, 402), (60, 34) */
(<10):
/* CIF TASK (195, 451), (174, 40) */
TASK save_buffer :=
save_buffer // {param};
/* CIF ANSWER (457, 402), (53, 34) */
(10):
/* CIF PROCEDURECALL (382, 451), (202, 38) */
CALL writeln('Buffer Overflow!');
ENDDECISION;
/* CIF NEXTSTATE (342, 506), (70, 35) */
NEXTSTATE wait;
ENDSTATE;
/* CIF STATE (929, 221), (88, 35) */
STATE Running;
/* CIF INPUT (1053, 276), (70, 35) */
INPUT Run;
/* CIF PROCEDURECALL (990, 326), (194, 35) */
CALL writeln('Already running');
/* CIF NEXTSTATE (1053, 376), (70, 35) */
NEXTSTATE -;
/* CIF PROVIDED (718, 276), (181, 35) */
PROVIDED length(save_buffer) > 0;
/* CIF TASK (717, 326), (182, 35) */
TASK param := save_buffer(0);
/* CIF TASK (636, 376), (344, 35) */
TASK save_buffer := save_buffer(1, length(save_buffer));
/* CIF TASK (647, 426), (323, 56) */
TASK save_buffer := if length(save_buffer) > 1
then {true} else save_buffer // {false } fi;
/* CIF TASK (650, 497), (316, 56) */
TASK save_buffer := if length(save_buffer) > 1
then save_buffer(1, length(save_buffer))
else {} fi;
/* CIF PROCEDURECALL (708, 568), (200, 35) */
CALL writeln('Running: ', param);
/* CIF NEXTSTATE (764, 618), (88, 35) */
NEXTSTATE Running;
ENDSTATE;
ENDPROCESS og;
ENDBLOCK;
ENDSYSTEM;
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment