Commit 6ccdef40 authored by Maxime Perrotin's avatar Maxime Perrotin
Browse files

Added checks when accessing SEQUENCE OF with index

parent ffec06ca
...@@ -279,8 +279,8 @@ def _decision(ast, scene, parent, states): ...@@ -279,8 +279,8 @@ def _decision(ast, scene, parent, states):
if not parent: if not parent:
symbol.setPos(ast.pos_x, ast.pos_y) symbol.setPos(ast.pos_x, ast.pos_y)
for branch in ast.answers: for branch in ast.answers:
render(branch, render(branch, scene=scene, parent=symbol, states=states)
scene=scene, parent=symbol, states=states) symbol.updateConnectionPointPosition()
return symbol return symbol
...@@ -300,8 +300,7 @@ def _answer(ast, scene, parent, states): ...@@ -300,8 +300,7 @@ def _answer(ast, scene, parent, states):
if not parent: if not parent:
symbol.setPos(ast.pos_x, ast.pos_y) symbol.setPos(ast.pos_x, ast.pos_y)
if ast.transition: if ast.transition:
render(ast.transition, render(ast.transition, scene=scene, parent=symbol, states=states)
scene=scene, parent=symbol, states=states)
return symbol return symbol
......
...@@ -899,9 +899,9 @@ class Symbol(QObject, QGraphicsPathItem, object): ...@@ -899,9 +899,9 @@ class Symbol(QObject, QGraphicsPathItem, object):
# Minimum size is the size of the text inside the symbol # Minimum size is the size of the text inside the symbol
try: try:
height = max(user_height, height = max(user_height,
self.text.boundingRect().height() + 10) self.text.boundingRect().height() + 10)
width = max(user_width, width = max(user_width,
self.text.boundingRect().width() + 30) self.text.boundingRect().width() + 30)
except AttributeError: except AttributeError:
height = max(user_height, 15) height = max(user_height, 15)
width = max(user_width, 30) width = max(user_width, 30)
...@@ -1327,6 +1327,8 @@ class HorizontalSymbol(Symbol, object): ...@@ -1327,6 +1327,8 @@ class HorizontalSymbol(Symbol, object):
self.connection = self.connect_to_parent() self.connection = self.connect_to_parent()
self.updateConnectionPoints() self.updateConnectionPoints()
self.cam(self.pos(), self.pos()) self.cam(self.pos(), self.pos())
LOG.debug('{} positionned at {}'.format(unicode(self),
unicode(self.scenePos())))
def update_connections(self): def update_connections(self):
''' '''
...@@ -1470,8 +1472,6 @@ class VerticalSymbol(Symbol, object): ...@@ -1470,8 +1472,6 @@ class VerticalSymbol(Symbol, object):
Determine the coordinates based on the position Determine the coordinates based on the position
and size of the parent item, and make proper connections and size of the parent item, and make proper connections
''' '''
LOG.debug('insert_symbol: ' + unicode(self) + ' at ' + unicode(x) +
', ' + unicode(y))
if not parent: if not parent:
# Place standalone item on the scene at given coordinates # Place standalone item on the scene at given coordinates
# (e.g. floating state) # (e.g. floating state)
...@@ -1533,11 +1533,12 @@ class VerticalSymbol(Symbol, object): ...@@ -1533,11 +1533,12 @@ class VerticalSymbol(Symbol, object):
# Create the connection with the parent symbol # Create the connection with the parent symbol
self.connection = self.connect_to_parent() self.connection = self.connect_to_parent()
self.update_position() self.update_position()
LOG.debug(unicode(self) + ' positionned at ' + unicode(self.pos()))
self.updateConnectionPoints() self.updateConnectionPoints()
if y is not None: if y is not None:
self.setY(y) self.setY(y)
self.cam(self.pos(), self.pos()) self.cam(self.pos(), self.pos())
LOG.debug('{} positionned at {}'.format(unicode(self),
unicode(self.scenePos())))
def update_position(self): def update_position(self):
''' '''
......
...@@ -133,6 +133,14 @@ type_name = lambda t: \ ...@@ -133,6 +133,14 @@ type_name = lambda t: \
types = lambda: getattr(DV, 'types', {}) types = lambda: getattr(DV, 'types', {})
def substring_range(substring):
''' Return the range of a substring '''
left, right = substring.value[1]['substring']
left_bty = find_basic_type(left.exprType)
right_bty = find_basic_type(right.exprType)
return left_bty.Min, right_bty.Max
def is_integer(ty): def is_integer(ty):
''' Return true if a type is an Integer Type ''' ''' Return true if a type is an Integer Type '''
return find_basic_type(ty).kind in ( return find_basic_type(ty).kind in (
...@@ -1434,7 +1442,22 @@ def primary_index(root, context): ...@@ -1434,7 +1442,22 @@ def primary_index(root, context):
node.value = [receiver, {'index': params}] node.value = [receiver, {'index': params}]
if receiver_bty.kind == 'SequenceOfType': if receiver_bty.kind == 'SequenceOfType':
# Range check
if isinstance(receiver, ogAST.PrimSubstring):
r_min, r_max = substring_range(receiver)
else:
r_min, r_max = receiver_bty.Min, receiver_bty.Max
node.exprType = receiver_bty.type node.exprType = receiver_bty.type
idx_bty = find_basic_type(params[0].exprType)
if not is_integer(idx_bty):
errors.append(error(root, 'Index is not an integer'))
else:
if float(idx_bty.Min) < float(r_min) or\
float(idx_bty.Max) >= float(r_max):
errors.append(error(root,
'Index outside of range [{} .. <{}]'
.format(r_min,
r_max)))
else: else:
msg = 'Index can only be applied to type SequenceOf' msg = 'Index can only be applied to type SequenceOf'
errors.append(error(root, msg)) errors.append(error(root, msg))
......
...@@ -242,6 +242,7 @@ class Decision(VerticalSymbol): ...@@ -242,6 +242,7 @@ class Decision(VerticalSymbol):
def updateConnectionPointPosition(self): def updateConnectionPointPosition(self):
''' Compute the joining point of decision branches ''' ''' Compute the joining point of decision branches '''
LOG.debug('UpdateConnectionPointPosition of {}'.format(unicode(self)))
new_y = 0 new_y = 0
new_x = self.boundingRect().width() / 2.0 new_x = self.boundingRect().width() / 2.0
answers = False answers = False
......
/* CIF PROCESS (200, 143), (150, 75) */ /* CIF PROCESS (197, 146), (150, 75) */
PROCESS myfunction; PROCESS myfunction;
/* CIF TEXT (7, 43), (334, 41) */ /* CIF TEXT (7, 43), (334, 41) */
-- Test substrings in various contexts and operators -- Test substrings in various contexts and operators
...@@ -48,7 +48,7 @@ endfor; ...@@ -48,7 +48,7 @@ endfor;
TASK for x in iseq: TASK for x in iseq:
call writeln(x); call writeln(x);
endfor endfor
/* CIF COMMENT (480, 422), (81, 72) */ /* CIF COMMENT (494, 420), (81, 72) */
COMMENT 'print COMMENT 'print
0 0
1 1
...@@ -63,136 +63,140 @@ endfor ...@@ -63,136 +63,140 @@ endfor
TASK seqof := seqof(0,1) TASK seqof := seqof(0,1)
/* CIF COMMENT (482, 595), (208, 35) */ /* CIF COMMENT (482, 595), (208, 35) */
COMMENT 'equivalent to seqof := seqof'; COMMENT 'equivalent to seqof := seqof';
/* CIF DECISION (324, 645), (123, 50) */ /* CIF TASK (303, 645), (165, 35) */
TASK n := iseq(0,2)(0,1)(0);
/* CIF TASK (314, 695), (141, 35) */
TASK n := iseq(100- 1);
/* CIF DECISION (324, 745), (123, 50) */
DECISION hello in seqof DECISION hello in seqof
/* CIF COMMENT (467, 646), (179, 53) */ /* CIF COMMENT (467, 746), (179, 53) */
COMMENT 'Check IN operator with COMMENT 'Check IN operator with
enumerated type'; enumerated type';
/* CIF ANSWER (253, 715), (70, 24) */ /* CIF ANSWER (242, 815), (70, 24) */
(true): (true):
/* CIF PROCEDURECALL (199, 754), (177, 35) */ /* CIF PROCEDURECALL (188, 854), (177, 35) */
CALL writeln(hello in seqof) CALL writeln(hello in seqof)
/* CIF COMMENT (397, 754), (114, 35) */ /* CIF COMMENT (386, 854), (114, 35) */
COMMENT 'print "TRUE"'; COMMENT 'print "TRUE"';
/* CIF ANSWER (515, 715), (70, 24) */ /* CIF ANSWER (505, 815), (70, 24) */
(false): (false):
ENDDECISION; ENDDECISION;
/* CIF DECISION (308, 804), (155, 50) */ /* CIF DECISION (308, 904), (155, 50) */
DECISION hello in seqof(0,0) DECISION hello in seqof(0,0)
/* CIF COMMENT (491, 767), (236, 56) */ /* CIF COMMENT (479, 865), (236, 56) */
COMMENT 'Check IN operator with COMMENT 'Check IN operator with
list substring - first element only list substring - first element only
should go to branch TRUE'; should go to branch TRUE';
/* CIF ANSWER (254, 827), (66, 33) */ /* CIF ANSWER (232, 929), (66, 33) */
(true): (true):
/* CIF PROCEDURECALL (187, 875), (201, 35) */ /* CIF PROCEDURECALL (165, 977), (201, 35) */
CALL writeln(hello in seqof(0,1)) CALL writeln(hello in seqof(0,1))
/* CIF COMMENT (412, 875), (114, 35) */ /* CIF COMMENT (400, 977), (114, 35) */
COMMENT 'print "TRUE"'; COMMENT 'print "TRUE"';
/* CIF ANSWER (532, 828), (70, 24) */ /* CIF ANSWER (522, 929), (70, 24) */
(false): (false):
ENDDECISION; ENDDECISION;
/* CIF PROCEDURECALL (289, 925), (191, 35) */ /* CIF PROCEDURECALL (289, 1027), (191, 35) */
CALL writeln(variable_str(0,4)) CALL writeln(variable_str(0,4))
/* CIF COMMENT (492, 860), (113, 35) */ /* CIF COMMENT (496, 988), (113, 35) */
COMMENT 'print "Hello"'; COMMENT 'print "Hello"';
/* CIF TASK (297, 975), (176, 56) */ /* CIF TASK (297, 1077), (176, 56) */
TASK for x in seqof: TASK for x in seqof:
call writeln(num(x)); call writeln(num(x));
endfor endfor
/* CIF COMMENT (492, 918), (96, 56) */ /* CIF COMMENT (498, 1039), (96, 56) */
COMMENT 'print: COMMENT 'print:
12 12
13'; 13';
/* CIF TASK (295, 1046), (180, 56) */ /* CIF TASK (295, 1148), (180, 56) */
TASK for x in seqof(0,1): TASK for x in seqof(0,1):
call writeln(-num(x)); call writeln(-num(x));
endfor endfor
/* CIF COMMENT (494, 982), (96, 56) */ /* CIF COMMENT (502, 1116), (96, 56) */
COMMENT 'print: COMMENT 'print:
-12 -12
-13'; -13';
/* CIF PROCEDURECALL (295, 1117), (180, 35) */ /* CIF PROCEDURECALL (295, 1219), (180, 35) */
CALL writeln(length(seqof)) CALL writeln(length(seqof))
/* CIF COMMENT (495, 1067), (77, 35) */ /* CIF COMMENT (507, 1180), (77, 35) */
COMMENT 'print 2'; COMMENT 'print 2';
/* CIF PROCEDURECALL (281, 1167), (209, 35) */ /* CIF PROCEDURECALL (281, 1269), (209, 35) */
CALL writeln(length(seqof(0,1))) CALL writeln(length(seqof(0,1)))
/* CIF COMMENT (510, 1117), (77, 35) */ /* CIF COMMENT (516, 1237), (77, 35) */
COMMENT 'print 2'; COMMENT 'print 2';
/* CIF LABEL (304, 1217), (162, 35) */ /* CIF LABEL (304, 1319), (162, 35) */
variable_length_seq: variable_length_seq:
/* CIF TASK (314, 1267), (142, 56) */ /* CIF TASK (314, 1369), (142, 56) */
TASK for x in seqint: TASK for x in seqint:
call writeln(x); call writeln(x);
endfor endfor
/* CIF COMMENT (476, 1203), (96, 53) */ /* CIF COMMENT (488, 1331), (96, 53) */
COMMENT 'print: COMMENT 'print:
1'; 1';
/* CIF TASK (309, 1338), (152, 56) */ /* CIF TASK (309, 1440), (152, 56) */
TASK for x in seqint(0,0): TASK for x in seqint(0,0):
call writeln(x); call writeln(x);
endfor endfor
/* CIF COMMENT (482, 1274), (96, 53) */ /* CIF COMMENT (473, 1412), (96, 53) */
COMMENT 'print: COMMENT 'print:
1'; 1';
/* CIF DECISION (324, 1409), (123, 50) */ /* CIF DECISION (324, 1511), (123, 50) */
DECISION 1 in seqint DECISION 1 in seqint
/* CIF COMMENT (466, 1349), (179, 53) */ /* CIF COMMENT (470, 1470), (179, 53) */
COMMENT 'Check IN operator with COMMENT 'Check IN operator with
variable-length seqOf'; variable-length seqOf';
/* CIF ANSWER (253, 1441), (66, 33) */ /* CIF ANSWER (228, 1536), (66, 33) */
(true): (true):
/* CIF PROCEDURECALL (198, 1489), (177, 35) */ /* CIF PROCEDURECALL (173, 1584), (177, 35) */
CALL writeln(1 in seqint) CALL writeln(1 in seqint)
/* CIF COMMENT (398, 1489), (114, 35) */ /* CIF COMMENT (382, 1584), (114, 35) */
COMMENT 'print "TRUE"'; COMMENT 'print "TRUE"';
/* CIF ANSWER (513, 1441), (70, 24) */ /* CIF ANSWER (497, 1536), (70, 24) */
(false): (false):
ENDDECISION; ENDDECISION;
/* CIF DECISION (321, 1539), (128, 50) */ /* CIF DECISION (321, 1634), (128, 50) */
DECISION 1 in seqint(0,0) DECISION 1 in seqint(0,0)
/* CIF COMMENT (469, 1479), (179, 53) */ /* CIF COMMENT (459, 1594), (179, 53) */
COMMENT 'Check IN operator with COMMENT 'Check IN operator with
variable-length seqOf'; variable-length seqOf';
/* CIF ANSWER (243, 1571), (70, 24) */ /* CIF ANSWER (234, 1659), (70, 24) */
(true): (true):
/* CIF PROCEDURECALL (187, 1610), (182, 35) */ /* CIF PROCEDURECALL (177, 1698), (182, 35) */
CALL writeln(1 in seqint(0,0)) CALL writeln(1 in seqint(0,0))
/* CIF COMMENT (391, 1610), (114, 35) */ /* CIF COMMENT (382, 1698), (114, 35) */
COMMENT 'print "TRUE"'; COMMENT 'print "TRUE"';
/* CIF ANSWER (514, 1571), (70, 24) */ /* CIF ANSWER (497, 1659), (70, 24) */
(false): (false):
ENDDECISION; ENDDECISION;
/* CIF PROCEDURECALL (295, 1660), (180, 35) */ /* CIF PROCEDURECALL (295, 1748), (180, 35) */
CALL writeln(length(seqint)) CALL writeln(length(seqint))
/* CIF COMMENT (495, 1610), (77, 35) */ /* CIF COMMENT (497, 1709), (77, 35) */
COMMENT 'print 1'; COMMENT 'print 1';
/* CIF PROCEDURECALL (279, 1710), (212, 35) */ /* CIF PROCEDURECALL (279, 1798), (212, 35) */
CALL writeln(length(seqint(0,0))) CALL writeln(length(seqint(0,0)))
/* CIF COMMENT (511, 1660), (77, 35) */ /* CIF COMMENT (516, 1764), (77, 35) */
COMMENT 'print 1'; COMMENT 'print 1';
/* CIF TASK (303, 1760), (163, 35) */ /* CIF TASK (303, 1848), (163, 35) */
TASK seqint := seqint // {2}; TASK seqint := seqint // {2};
/* CIF TASK (290, 1810), (190, 35) */ /* CIF TASK (290, 1898), (190, 35) */
TASK seqint := seqint(0,0) // {5}; TASK seqint := seqint(0,0) // {5};
/* CIF TASK (314, 1860), (142, 56) */ /* CIF TASK (314, 1948), (142, 56) */
TASK for x in seqint: TASK for x in seqint:
call writeln(x); call writeln(x);
endfor endfor
/* CIF COMMENT (478, 1820), (96, 56) */ /* CIF COMMENT (494, 1911), (96, 56) */
COMMENT 'print: COMMENT 'print:
1 1
5'; 5';
/* CIF TASK (269, 1931), (233, 35) */ /* CIF TASK (269, 2019), (233, 35) */
TASK seqbool := seqbool and seqbool TASK seqbool := seqbool and seqbool
/* CIF COMMENT (522, 1905), (194, 35) */ /* CIF COMMENT (527, 1979), (194, 35) */
COMMENT 'should not raise any error'; COMMENT 'should not raise any error';
/* CIF TASK (256, 1981), (258, 38) */ /* CIF TASK (256, 2069), (258, 38) */
TASK 'seqbool2 := seqbool2 and seqbool2' TASK 'seqbool2 := seqbool2 and seqbool2'
/* CIF COMMENT (535, 1967), (213, 35) */ /* CIF COMMENT (537, 2033), (213, 35) */
COMMENT 'Variable-length -> raise error'; COMMENT 'Variable-length -> raise error';
/* CIF NEXTSTATE (349, 2034), (68, 33) */ /* CIF NEXTSTATE (339, 2122), (68, 33) */
NEXTSTATE Wait; NEXTSTATE Wait;
/* CIF STATE (839, 313), (70, 35) */ /* CIF STATE (839, 313), (70, 35) */
STATE wait; STATE wait;
......
Supports Markdown
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