Update MatIEC version

This commit is contained in:
Autonomy Server
2024-12-11 15:00:37 -05:00
parent 5807cb3285
commit 138b62bdb3
89 changed files with 1899 additions and 740 deletions
Vendored
BIN
View File
Binary file not shown.
+19
View File
@@ -0,0 +1,19 @@
{
"configurations": [
{
"name": "Mac",
"includePath": [
"${workspaceFolder}/**"
],
"defines": [],
"macFrameworkPath": [
"/Library/Developer/CommandLineTools/SDKs/MacOSX.sdk/System/Library/Frameworks"
],
"compilerPath": "/usr/bin/clang",
"cStandard": "c17",
"cppStandard": "c++17",
"intelliSenseMode": "macos-clang-x64"
}
],
"version": 4
}
+3
View File
@@ -0,0 +1,3 @@
{
"cmake.ignoreCMakeListsMissing": true
}
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
+68 -11
View File
@@ -58,6 +58,7 @@ symbol_c::symbol_c(
this->last_column = last_column;
this->last_order = last_order;
this->parent = NULL;
this->token = NULL;
this->datatype = NULL;
this->scope = NULL;
}
@@ -69,6 +70,7 @@ token_c::token_c(const char *value,
int ll, int lc, const char *lfile, long int lorder)
:symbol_c(fl, fc, ffile, forder, ll, lc, lfile, lorder) {
this->value = value;
this->token = this; // every token is its own reference token.
// printf("New token: %s\n", value);
}
@@ -83,7 +85,7 @@ list_c::list_c(
int ll, int lc, const char *lfile, long int lorder)
:symbol_c(fl, fc, ffile, forder, ll, lc, lfile, lorder),c(LIST_CAP_INIT) {
n = 0;
elements = (symbol_c**)malloc(LIST_CAP_INIT*sizeof(symbol_c*));
elements = (element_entry_t*)malloc(LIST_CAP_INIT*sizeof(element_entry_t));
if (NULL == elements) ERROR_MSG("out of memory");
}
@@ -93,20 +95,59 @@ list_c::list_c(symbol_c *elem,
int ll, int lc, const char *lfile, long int lorder)
:symbol_c(fl, fc, ffile, forder, ll, lc, lfile, lorder),c(LIST_CAP_INIT) {
n = 0;
elements = (symbol_c**)malloc(LIST_CAP_INIT*sizeof(symbol_c*));
elements = (element_entry_t*)malloc(LIST_CAP_INIT*sizeof(element_entry_t));
if (NULL == elements) ERROR_MSG("out of memory");
add_element(elem);
}
/*******************************************/
/* get element in position pos of the list */
/*******************************************/
symbol_c *list_c::get_element(int pos) {return elements[pos].symbol;}
/******************************************/
/* find element associated to token value */
/******************************************/
symbol_c *list_c::find_element(symbol_c *token) {
token_c *t = dynamic_cast<token_c *>(token);
if (t == NULL) ERROR;
return find_element((const char *)t->value);
}
symbol_c *list_c::find_element(const char *token_value) {
// We could use strcasecmp(), but it's best to always use the same
// method of string comparison throughout matiec
nocasecmp_c ncc;
for (int i = 0; i < n; i++)
if (!ncc(elements[i].token_value, token_value))
return elements[i].symbol;
return NULL; // not found
}
/***********************************************/
/* append a new element to the end of the list */
void list_c::add_element(symbol_c *elem) {
// printf("list_c::add_element()\n");
/***********************************************/
void list_c::add_element(symbol_c *elem) {add_element(elem, elem);}
void list_c::add_element(symbol_c *elem, symbol_c *token) {
token_c *t = (token == NULL)? NULL : token->token;
add_element(elem, (t == NULL)? NULL : t->value);
}
void list_c::add_element(symbol_c *elem, const char *token_value) {
if (c <= n)
if (!(elements=(symbol_c**)realloc(elements,(c+=LIST_CAP_INCR)*sizeof(symbol_c *))))
if (!(elements=(element_entry_t*)realloc(elements,(c+=LIST_CAP_INCR)*sizeof(element_entry_t))))
ERROR_MSG("out of memory");
elements[n++] = elem;
//elements[n++] = {token_value, elem}; // only available from C++11 onwards, best not use it for now.
elements[n].symbol = elem;
elements[n].token_value = token_value;
n++;
if (NULL == elem) return;
/* Sometimes add_element() is called in stage3 or stage4 to temporarily add an AST symbol to the list.
* Since this symbol already belongs in some other place in the aST, it will have the 'parent' pointer set,
@@ -143,10 +184,21 @@ void list_c::add_element(symbol_c *elem) {
}
}
/*********************************************/
/* insert a new element before position pos. */
/*********************************************/
/* To insert into the begining of list, call with pos=0 */
/* To insert into the end of list, call with pos=list->n */
void list_c::insert_element(symbol_c *elem, int pos) {
void list_c::insert_element(symbol_c *elem, int pos) {insert_element(elem, elem, pos);}
void list_c::insert_element(symbol_c *elem, symbol_c *token, int pos) {
token_c *t = (token == NULL)? NULL : token->token;
insert_element(elem, (t == NULL)? NULL : t->value, pos);
}
void list_c::insert_element(symbol_c *elem, const char *token_value, int pos) {
if((pos<0) || (n<pos)) ERROR;
/* add new element to end of list. Basically alocate required memory... */
@@ -155,12 +207,15 @@ void list_c::insert_element(symbol_c *elem, int pos) {
/* if not inserting into end position, shift all elements up one position, to open up a slot in pos for new element */
if(pos < (n-1)){
for(int i=n-2 ; i>=pos ; --i) elements[i+1] = elements[i];
elements[pos] = elem;
elements[pos].symbol = elem;
elements[pos].token_value = token_value;
}
}
/***********************************/
/* remove element at position pos. */
/***********************************/
void list_c::remove_element(int pos) {
if((pos<0) || (n<=pos)) ERROR;
@@ -168,12 +223,14 @@ void list_c::remove_element(int pos) {
for (int i = pos; i < n-1; i++) elements[i] = elements[i+1];
/* corrent the new size */
n--;
/* elements = (symbol_c **)realloc(elements, n * sizeof(symbol_c *)); */
/* elements = (symbol_c **)realloc(elements, n * sizeof(element_entry_t)); */
/* TODO: adjust the location parameters, taking into account the removed element. */
}
/* remove element at position pos. */
/**********************************/
/* Remove all elements from list. */
/**********************************/
void list_c::clear(void) {
n = 0;
/* TODO: adjust the location parameters, taking into account the removed element. */
+3 -1
View File
@@ -267,6 +267,7 @@ SYM_REF0(dword_type_name_c)
SYM_REF0(lword_type_name_c)
SYM_REF0(string_type_name_c)
SYM_REF0(wstring_type_name_c)
SYM_REF0(void_type_name_c) /* a non-standard extension! */
/*****************************************************************/
/* Keywords defined in "Safety Software Technical Specification" */
@@ -1287,4 +1288,5 @@ SYM_REF2(repeat_statement_c, statement_list, expression)
/* EXIT */
SYM_REF0(exit_statement_c)
/* continue */
SYM_REF0(continue_statement_c)
+51 -22
View File
@@ -154,7 +154,8 @@ class const_value_c {
{return (_int64.is_valid() || _uint64.is_valid() || _real64.is_valid() || _bool.is_valid());}
};
// A forward declaration
class token_c;
/* The base class of all symbols */
class symbol_c {
@@ -167,7 +168,18 @@ class symbol_c {
* Annotations produced during stage 1_2
*/
/* Points to the parent symbol in the AST, i.e. the symbol in the AST that will contain the current symbol */
symbol_c *parent;
symbol_c *parent;
/* Some symbols may not be tokens, but may be clearly identified by a token.
* For e.g., a FUNCTION declaration is not itself a token, but may be clearly identified by the
* token_c object that contains it's name. Another example is an element in a STRUCT declaration,
* where the structure_element_declaration_c is not itself a token, but can be clearly identified
* by the structure_element_name
* To make it easier to find these tokens from the top level object, we will have the stage1_2 populate this
* token_c *token wherever it makes sense.
* NOTE: This was a late addition to the AST. Not all objects may be currently so populated.
* If you need this please make sure the bison code is populating it correctly for your use case.
*/
token_c *token;
/* Line number for the purposes of error checking. */
int first_line;
@@ -260,7 +272,14 @@ class list_c: public symbol_c {
virtual const char *absyntax_cname(void) {return "list_c";};
int c,n; /* c: current capacity of list (malloc'd memory); n: current number of elements in list */
symbol_c **elements;
private:
// symbol_c **elements;
typedef struct {
const char *token_value;
symbol_c *symbol;
} element_entry_t;
element_entry_t *elements;
public:
list_c(int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, /* order in which it is read by lexcial analyser */
@@ -271,12 +290,22 @@ class list_c: public symbol_c {
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, /* order in which it is read by lexcial analyser */
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0 /* order in which it is read by lexcial analyser */
);
/* get element in position pos of the list */
virtual symbol_c *get_element(int pos);
/* find element associated to token value */
virtual symbol_c *find_element(symbol_c *token);
virtual symbol_c *find_element(const char *token_value);
/* append a new element to the end of the list */
virtual void add_element(symbol_c *elem);
virtual void add_element(symbol_c *elem, symbol_c *token);
virtual void add_element(symbol_c *elem, const char *token_value);
/* insert a new element before position pos. */
/* To insert into the begining of list, call with pos=0 */
/* To insert into the end of list, call with pos=list->n */
virtual void insert_element(symbol_c *elem, int pos = 0);
virtual void insert_element(symbol_c *elem, const char *token_value, int pos = 0);
virtual void insert_element(symbol_c *elem, symbol_c *token, int pos = 0);
virtual void insert_element(symbol_c *elem, int pos = 0);
//virtual void insert_element(symbol_c *elem, int pos, std::string map_ref);
/* remove element at position pos. */
virtual void remove_element(int pos = 0);
/* remove all elements from list. Does not delete the elements in the list! */
@@ -342,7 +371,7 @@ class class_name_c: public symbol_c { \
symbol_c *ref1; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
class_name_c(symbol_c *ref1 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
virtual void *accept(visitor_c &visitor); \
@@ -358,7 +387,7 @@ class class_name_c: public symbol_c { \
symbol_c *ref2; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
class_name_c(symbol_c *ref1 = NULL, \
symbol_c *ref2 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
@@ -376,9 +405,9 @@ class class_name_c: public symbol_c { \
symbol_c *ref3; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
symbol_c *ref2, \
symbol_c *ref3, \
class_name_c(symbol_c *ref1 = NULL, \
symbol_c *ref2 = NULL, \
symbol_c *ref3 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
virtual void *accept(visitor_c &visitor); \
@@ -396,9 +425,9 @@ class class_name_c: public symbol_c { \
symbol_c *ref4; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
symbol_c *ref2, \
symbol_c *ref3, \
class_name_c(symbol_c *ref1 = NULL, \
symbol_c *ref2 = NULL, \
symbol_c *ref3 = NULL, \
symbol_c *ref4 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
@@ -418,11 +447,11 @@ class class_name_c: public symbol_c { \
symbol_c *ref5; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
symbol_c *ref2, \
symbol_c *ref3, \
symbol_c *ref4, \
symbol_c *ref5, \
class_name_c(symbol_c *ref1 = NULL, \
symbol_c *ref2 = NULL, \
symbol_c *ref3 = NULL, \
symbol_c *ref4 = NULL, \
symbol_c *ref5 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
virtual void *accept(visitor_c &visitor); \
@@ -442,11 +471,11 @@ class class_name_c: public symbol_c { \
symbol_c *ref6; \
__VA_ARGS__ \
public: \
class_name_c(symbol_c *ref1, \
symbol_c *ref2, \
symbol_c *ref3, \
symbol_c *ref4, \
symbol_c *ref5, \
class_name_c(symbol_c *ref1 = NULL, \
symbol_c *ref2 = NULL, \
symbol_c *ref3 = NULL, \
symbol_c *ref4 = NULL, \
symbol_c *ref5 = NULL, \
symbol_c *ref6 = NULL, \
int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, long int forder=0, \
int ll = 0, int lc = 0, const char *lfile = NULL /* filename */, long int lorder=0); \
+2 -2
View File
@@ -168,7 +168,7 @@ iterator_visitor_c::~iterator_visitor_c(void) {return;}
void *iterator_visitor_c::visit_list(list_c *list) {
for(int i = 0; i < list->n; i++) {
list->elements[i]->accept(*this);
list->get_element(i)->accept(*this);
}
return NULL;
}
@@ -310,7 +310,7 @@ search_visitor_c::~search_visitor_c(void) {return;}
void *search_visitor_c::visit_list(list_c *list) {
for(int i = 0; i < list->n; i++) {
void *res = list->elements[i]->accept(*this);
void *res = list->get_element(i)->accept(*this);
if (res != NULL)
return res;
}
View File
+1 -1
View File
@@ -84,7 +84,7 @@ add_en_eno_param_decl_c::~add_en_eno_param_decl_c(void) {
void* add_en_eno_param_decl_c::iterate_list(list_c *list) {
for (int i = 0; i < list->n; i++) {
list->elements[i]->accept(*this);
list->get_element(i)->accept(*this);
}
return NULL;
}
View File
+1 -1
View File
@@ -64,7 +64,7 @@
void* array_dimension_iterator_c::iterate_list(list_c *list) {
void *res;
for (int i = 0; i < list->n; i++) {
res = list->elements[i]->accept(*this);
res = list->get_element(i)->accept(*this);
if (res != NULL)
return res;
}
View File
+1 -1
View File
@@ -78,7 +78,7 @@ void* case_element_iterator_c::handle_case_element(symbol_c *case_element) {
void* case_element_iterator_c::iterate_list(list_c *list) {
void *res;
for (int i = 0; i < list->n; i++) {
res = list->elements[i]->accept(*this);
res = list->get_element(i)->accept(*this);
if (res != NULL)
return res;
}
View File
+18 -16
View File
@@ -56,12 +56,12 @@ static void dump_cvalue(const_value_c const_value) {
else if (const_value._real64.is_nonconst()) fprintf(stderr, "nc");
else fprintf(stderr, "?");
fprintf(stderr, ", i=");
if (const_value. _int64.is_valid ()) fprintf(stderr, "%"PRId64"", const_value. _int64.get());
if (const_value. _int64.is_valid ()) fprintf(stderr, "%" PRId64 "", const_value. _int64.get());
else if (const_value. _int64.is_overflow()) fprintf(stderr, "ov");
else if (const_value. _int64.is_nonconst()) fprintf(stderr, "nc");
else fprintf(stderr, "?");
fprintf(stderr, ", u=");
if (const_value._uint64.is_valid ()) fprintf(stderr, "%"PRIu64"", const_value._uint64.get());
if (const_value._uint64.is_valid ()) fprintf(stderr, "%" PRIu64 "", const_value._uint64.get());
else if (const_value._uint64.is_overflow()) fprintf(stderr, "ov");
else if (const_value._uint64.is_nonconst()) fprintf(stderr, "nc");
else fprintf(stderr, "?");
@@ -120,13 +120,16 @@ void print_symbol_c::fcall(symbol_c* symbol) {
void print_symbol_c::dump_symbol(symbol_c* symbol) {
fprintf(stderr, "(%s->%03d:%03d..%03d:%03d) \t%s\t", symbol->first_file, symbol->first_line, symbol->first_column, symbol->last_line, symbol->last_column, symbol->absyntax_cname());
fprintf(stderr, "(%s->%03d:%03d..%03d:%03d) \t%s", symbol->first_file, symbol->first_line, symbol->first_column, symbol->last_line, symbol->last_column, symbol->absyntax_cname());
fprintf(stderr, " datatype=");
if ((NULL != symbol->token) && (NULL != symbol->token->value))
fprintf(stderr, "(%s)", symbol->token->value);
fprintf(stderr, "\t datatype=");
if (NULL == symbol->datatype)
fprintf(stderr, "NULL\t\t");
else {
fprintf(stderr, "%s", symbol->datatype->absyntax_cname());
fprintf(stderr, "%s", symbol->datatype->absyntax_cname());
}
fprintf(stderr, "\t<-{");
if (symbol->candidate_datatypes.size() == 0) {
@@ -153,26 +156,25 @@ void *print_symbol_c::visit(il_instruction_c *symbol) {
dump_symbol(symbol);
/* NOTE: std::map.size() returns a size_type, whose type is dependent on compiler/platform. To be portable, we need to do an explicit type cast. */
fprintf(stderr, " next_il_=%lu ", (unsigned long int)symbol->next_il_instruction.size());
fprintf(stderr, " prev_il_=%lu ", (unsigned long int)symbol->prev_il_instruction.size());
if (symbol->prev_il_instruction.size() == 0)
fprintf(stderr, "(----,");
fprintf(stderr, "(----)");
else if (symbol->prev_il_instruction[0]->datatype == NULL)
fprintf(stderr, "(NULL,");
fprintf(stderr, "(NULL)");
else if (!get_datatype_info_c::is_type_valid(symbol->prev_il_instruction[0]->datatype))
fprintf(stderr, "(****,");
fprintf(stderr, "(****)");
else
fprintf(stderr, "( ,");
fprintf(stderr, "( )");
fprintf(stderr, " next_il_=%lu ", (unsigned long int)symbol->next_il_instruction.size());
if (symbol->next_il_instruction.size() == 0)
fprintf(stderr, "----)");
fprintf(stderr, "(----)");
else if (symbol->next_il_instruction[0]->datatype == NULL)
fprintf(stderr, "NULL)");
fprintf(stderr, "(NULL)");
else if (!get_datatype_info_c::is_type_valid(symbol->next_il_instruction[0]->datatype))
fprintf(stderr, "****)");
fprintf(stderr, "(****)");
else
fprintf(stderr, " )");
fprintf(stderr, "( )");
fprintf(stderr, "\n");
View File
View File
View File
View File
+4 -4
View File
@@ -67,7 +67,7 @@ void *function_call_param_iterator_c::search_list(list_c *list) {
switch (current_operation) {
case iterate_nf_op:
for(int i = 0; i < list->n; i++) {
void *res = list->elements[i]->accept(*this);
void *res = list->get_element(i)->accept(*this);
if (NULL != res) {
/* It went through the handle_parameter_assignment() function,
* and is therefore a parameter assignment (<param> = <value>),
@@ -77,7 +77,7 @@ void *function_call_param_iterator_c::search_list(list_c *list) {
} else {
param_count++;
if (param_count == iterate_nf_next_param) {
return list->elements[i];
return list->get_element(i);
}
}
}
@@ -86,7 +86,7 @@ void *function_call_param_iterator_c::search_list(list_c *list) {
case iterate_f_op:
for(int i = 0; i < list->n; i++) {
void *res = list->elements[i]->accept(*this);
void *res = list->get_element(i)->accept(*this);
if (NULL != res) {
/* It went through the handle_parameter_assignment() function,
* and is therefore a parameter assignment (<param> = <value>),
@@ -105,7 +105,7 @@ void *function_call_param_iterator_c::search_list(list_c *list) {
case search_f_op:
for(int i = 0; i < list->n; i++) {
void *res = list->elements[i]->accept(*this);
void *res = list->get_element(i)->accept(*this);
if (res != NULL)
return res;
}
View File
@@ -167,7 +167,7 @@ void* function_param_iterator_c::handle_param_list(list_c *list) {
switch (current_operation) {
case iterate_op:
if (next_param <= param_count + list->n)
return list->elements[next_param - param_count - 1];
return list->get_element(next_param - param_count - 1);
/* the desired param is not on this list... */
param_count += list->n;
@@ -175,7 +175,7 @@ void* function_param_iterator_c::handle_param_list(list_c *list) {
case search_op:
for(int i = 0; i < list->n; i++) {
symbol_c *sym = list->elements[i];
symbol_c *sym = list->get_element(i);
extensible_input_parameter_c *extensible_parameter = dynamic_cast<extensible_input_parameter_c *>(sym);
if (extensible_parameter != NULL) {
sym = extensible_parameter->var_name;
@@ -243,7 +243,7 @@ void* function_param_iterator_c::handle_single_param(symbol_c *var_name) {
void* function_param_iterator_c::iterate_list(list_c *list) {
void *res;
for (int i = 0; i < list->n; i++) {
res = list->elements[i]->accept(*this);
res = list->get_element(i)->accept(*this);
if (res != NULL)
return res;
}
View File
@@ -127,6 +127,8 @@ class get_datatype_id_c: null_visitor_c {
void *visit(safestring_type_name_c *symbol) {return (void *)symbol;};
void *visit(safewstring_type_name_c *symbol) {return (void *)symbol;};
void *visit(void_type_name_c *symbol) {return (void *)symbol;};
/********************************/
/* B 1.3.3 - Derived data types */
/********************************/
@@ -260,6 +262,8 @@ class get_datatype_id_str_c: public null_visitor_c {
void *visit(safestring_type_name_c *symbol) {return (void *)"SAFESTRING"; };
void *visit(safewstring_type_name_c *symbol) {return (void *)"SAFEWSTRING"; };
void *visit(void_type_name_c *symbol) {return (void *)"VOID"; };
/********************************/
/* B.1.3.2 - Generic data types */
/********************************/
@@ -358,7 +362,7 @@ class get_struct_info_c : null_visitor_c {
void *visit(structure_element_declaration_list_c *symbol) {
/* now search the structure declaration */
for(int i = 0; i < symbol->n; i++) {
void *tmp = symbol->elements[i]->accept(*this);
void *tmp = symbol->get_element(i)->accept(*this);
if (NULL != tmp) return tmp;
}
return NULL; // not found!!
@@ -709,8 +713,8 @@ bool get_datatype_info_c::is_arraytype_equal_relaxed(symbol_c *first_type, symbo
// comparison of each subrange start and end elements
for (int i = 0; i < subrange_list_1->n; i++) {
subrange_c *subrange_1 = dynamic_cast<subrange_c *>(subrange_list_1->elements[i]);
subrange_c *subrange_2 = dynamic_cast<subrange_c *>(subrange_list_2->elements[i]);
subrange_c *subrange_1 = dynamic_cast<subrange_c *>(subrange_list_1->get_element(i));
subrange_c *subrange_2 = dynamic_cast<subrange_c *>(subrange_list_2->get_element(i));
if ((NULL == subrange_1) || (NULL == subrange_2)) ERROR;
/* check whether the subranges have the same values, using the result of the constant folding agorithm.
@@ -1352,6 +1356,21 @@ bool get_datatype_info_c::is_ANY_STRING_compatible(symbol_c *type_symbol) {
bool get_datatype_info_c::is_VOID(symbol_c *type_symbol) {
if (type_symbol == NULL) {return false;}
if (typeid(*type_symbol) == typeid(void_type_name_c)) {return true;}
return false;
}
/* Can't we do away with this?? */
bool get_datatype_info_c::is_ANY_REAL_literal(symbol_c *type_symbol) {
if (type_symbol == NULL) {return true;} /* Please make sure things will work correctly before changing this to false!! */
@@ -1381,6 +1400,7 @@ bool get_datatype_info_c::is_ANY_INT_literal(symbol_c *type_symbol) {
invalid_type_name_c get_datatype_info_c::invalid_type_name;
generic_type_any_c get_datatype_info_c::any_type_name;
/**********************/
/* B.1.3 - Data types */
@@ -165,6 +165,8 @@ class get_datatype_info_c {
static bool is_ANY_SAFESTRING (symbol_c *type_symbol);
static bool is_ANY_STRING_compatible (symbol_c *type_symbol);
// A non-standard extension --> data type 'VOID' (used for functions that do not return any data)
static bool is_VOID (symbol_c *type_symbol);
@@ -173,6 +175,9 @@ class get_datatype_info_c {
/* This is only used from stage3 onwards. Stages 1 and 2 will never create any instances of invalid_type_name_c */
static invalid_type_name_c invalid_type_name;
/* object used to identify ANY datya type */
static generic_type_any_c any_type_name;
/**********************/
/* B.1.3 - Data types */
/**********************/
View File
View File
+18 -24
View File
@@ -184,6 +184,8 @@ void *search_base_type_c::visit(lword_type_name_c *symbol) {return (void
void *search_base_type_c::visit(string_type_name_c *symbol) {return (void *)symbol;}
void *search_base_type_c::visit(wstring_type_name_c *symbol) {return (void *)symbol;}
/* A non standard datatype! */
void *search_base_type_c::visit(void_type_name_c *symbol) {return (void *)symbol;}
/******************************************************/
/* Extensions to the base standard as defined in */
@@ -253,7 +255,7 @@ void *search_base_type_c::visit(subrange_specification_c *symbol) {
}
/* signed_integer DOTDOT signed_integer */
void *search_base_type_c::visit(subrange_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(subrange_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* enumerated_type_name ':' enumerated_spec_init */
void *search_base_type_c::visit(enumerated_type_declaration_c *symbol) {
@@ -291,7 +293,7 @@ void *search_base_type_c::visit(enumerated_value_list_c *symbol) {
/* enumerated_type_name '#' identifier */
// SYM_REF2(enumerated_value_c, type, value)
void *search_base_type_c::visit(enumerated_value_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(enumerated_value_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* identifier ':' array_spec_init */
void *search_base_type_c::visit(array_type_declaration_c *symbol) {
@@ -310,20 +312,20 @@ void *search_base_type_c::visit(array_spec_init_c *symbol) {
}
/* ARRAY '[' array_subrange_list ']' OF non_generic_type_name */
void *search_base_type_c::visit(array_specification_c *symbol) {return (void *)symbol;}
void *search_base_type_c::visit(array_specification_c *symbol) {return (void *)symbol;}
/* helper symbol for array_specification */
/* array_subrange_list ',' subrange */
void *search_base_type_c::visit(array_subrange_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(array_subrange_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* array_initialization: '[' array_initial_elements_list ']' */
/* helper symbol for array_initialization */
/* array_initial_elements_list ',' array_initial_elements */
void *search_base_type_c::visit(array_initial_elements_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(array_initial_elements_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* integer '(' [array_initial_element] ')' */
/* array_initial_element may be NULL ! */
void *search_base_type_c::visit(array_initial_elements_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(array_initial_elements_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* structure_type_name ':' structure_specification */
/* NOTE: structure_specification will point to either a
@@ -337,31 +339,27 @@ void *search_base_type_c::visit(structure_type_declaration_c *symbol) {
}
/* var1_list ':' structure_type_name */
void *search_base_type_c::visit(structured_var_declaration_c *symbol) {
return symbol;
}
void *search_base_type_c::visit(structured_var_declaration_c *symbol) {return symbol;}
/* structure_type_name ASSIGN structure_initialization */
/* structure_initialization may be NULL ! */
void *search_base_type_c::visit(initialized_structure_c *symbol) {
return symbol->structure_type_name->accept(*this);
}
void *search_base_type_c::visit(initialized_structure_c *symbol) {return symbol->structure_type_name->accept(*this);}
/* helper symbol for structure_declaration */
/* structure_declaration: STRUCT structure_element_declaration_list END_STRUCT */
/* structure_element_declaration_list structure_element_declaration ';' */
void *search_base_type_c::visit(structure_element_declaration_list_c *symbol) {return (void *)symbol;}
void *search_base_type_c::visit(structure_element_declaration_list_c *symbol) {return (void *)symbol;}
/* structure_element_name ':' *_spec_init */
void *search_base_type_c::visit(structure_element_declaration_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(structure_element_declaration_c *symbol) {return symbol->spec_init->accept(*this);}
/* helper symbol for structure_initialization */
/* structure_initialization: '(' structure_element_initialization_list ')' */
/* structure_element_initialization_list ',' structure_element_initialization */
void *search_base_type_c::visit(structure_element_initialization_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(structure_element_initialization_list_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* structure_element_name ASSIGN value */
void *search_base_type_c::visit(structure_element_initialization_c *symbol) {ERROR; return NULL;} /* should never get called... */
void *search_base_type_c::visit(structure_element_initialization_c *symbol) {ERROR; return NULL;} /* should never get called... */
/* string_type_name ':' elementary_string_type_name string_type_declaration_size string_type_declaration_init */
/*
@@ -370,7 +368,7 @@ SYM_REF4(string_type_declaration_c, string_type_name,
string_type_declaration_size,
string_type_declaration_init) // may be == NULL!
*/
void *search_base_type_c::visit(string_type_declaration_c *symbol) {return (void *)symbol;}
void *search_base_type_c::visit(string_type_declaration_c *symbol) {return (void *)symbol;}
/* function_block_type_name ASSIGN structure_initialization */
@@ -384,15 +382,13 @@ void *search_base_type_c::visit(fb_spec_init_c *symbol) {
/* ref_spec: REF_TO (non_generic_type_name | function_block_type_name) */
// SYM_REF1(ref_spec_c, type_name)
void *search_base_type_c::visit(ref_spec_c *symbol) {return (void *)symbol;}
void *search_base_type_c::visit(ref_spec_c *symbol) {return (void *)symbol;}
/* For the moment, we do not support initialising reference data types */
/* ref_spec_init: ref_spec [ ASSIGN ref_initialization ]; */
/* NOTE: ref_initialization may be NULL!! */
// SYM_REF2(ref_spec_init_c, ref_spec, ref_initialization)
void *search_base_type_c::visit(ref_spec_init_c *symbol) {
return symbol->ref_spec->accept(*this);
}
void *search_base_type_c::visit(ref_spec_init_c *symbol) {return symbol->ref_spec->accept(*this);}
/* ref_type_decl: identifier ':' ref_spec_init */
// SYM_REF2(ref_type_decl_c, ref_type_name, ref_spec_init)
@@ -408,9 +404,7 @@ void *search_base_type_c::visit(ref_type_decl_c *symbol) {
/*****************************/
/* FUNCTION_BLOCK derived_function_block_name io_OR_other_var_declarations function_block_body END_FUNCTION_BLOCK */
// SYM_REF3(function_block_declaration_c, fblock_name, var_declarations, fblock_body)
void *search_base_type_c::visit(function_block_declaration_c *symbol) {
return (void *)symbol;
}
void *search_base_type_c::visit(function_block_declaration_c *symbol) {return (void *)symbol;}
+1
View File
@@ -141,6 +141,7 @@ class search_base_type_c: public null_visitor_c {
void *visit(lword_type_name_c *symbol);
void *visit(string_type_name_c *symbol);
void *visit(wstring_type_name_c *symbol);
void *visit(void_type_name_c *symbol); /* A non standard datatype! */
/******************************************************/
/* Extensions to the base standard as defined in */
+1 -1
View File
@@ -95,7 +95,7 @@ void *search_fb_instance_decl_c::visit(fb_name_decl_c *symbol) {
void *search_fb_instance_decl_c::visit(fb_name_list_c *symbol) {
list_c *list = symbol;
for(int i = 0; i < list->n; i++) {
if (compare_identifiers(list->elements[i], search_name) == 0)
if (compare_identifiers(list->get_element(i), search_name) == 0)
/* by now, current_fb_declaration should be != NULL */
return current_fb_type_name;
}
View File
View File
View File
@@ -313,7 +313,7 @@ void *search_var_instance_decl_c::visit(var1_init_decl_c *symbol) {
void *search_var_instance_decl_c::visit(var1_list_c *symbol) {
list_c *list = symbol;
for(int i = 0; i < list->n; i++) {
if (compare_identifiers(list->elements[i], search_name) == 0)
if (compare_identifiers(list->get_element(i), search_name) == 0)
/* by now, current_type_decl should be != NULL */
return current_type_decl;
}
@@ -335,7 +335,7 @@ void *search_var_instance_decl_c::visit(fb_name_decl_c *symbol) {
void *search_var_instance_decl_c::visit(fb_name_list_c *symbol) {
list_c *list = symbol;
for(int i = 0; i < list->n; i++) {
if (compare_identifiers(list->elements[i], search_name) == 0)
if (compare_identifiers(list->get_element(i), search_name) == 0)
/* by now, current_fb_declaration should be != NULL */
return current_type_decl;
}
@@ -409,7 +409,7 @@ void *search_var_instance_decl_c::visit(global_var_spec_c *symbol) {
void *search_var_instance_decl_c::visit(global_var_list_c *symbol) {
list_c *list = symbol;
for(int i = 0; i < list->n; i++) {
if (compare_identifiers(list->elements[i], search_name) == 0)
if (compare_identifiers(list->get_element(i), search_name) == 0)
/* by now, current_type_decl should be != NULL */
return current_type_decl;
}
+1 -1
View File
@@ -244,7 +244,7 @@ void *search_varfb_instance_type_c::visit(structure_element_declaration_list_c *
/* now search the structure declaration */
for(int i = 0; i < symbol->n; i++) {
symbol->elements[i]->accept(*this);
symbol->get_element(i)->accept(*this);
}
return NULL;
View File
View File
View File
@@ -224,7 +224,7 @@ void *type_initial_value_c::visit(enumerated_value_list_c *symbol) {
/* stage1_2 never creates an enumerated_value_list_c with no entries. If this occurs, then something must have changed! */
if (symbol->n <= 0) ERROR;
/* if no initial value explicitly given, then use the lowest value of the subrange */
return (void *)symbol->elements[0];
return (void *)symbol->get_element(0);
}
/* enumerated_type_name '#' identifier */
// SYM_REF2(enumerated_value_c, type, value)
View File
+5 -2
View File
@@ -28,8 +28,7 @@ AC_PROG_RANLIB
AC_PROG_AWK
# Check bison version, we need a version great or equal than 2.4 to build matiec.
version_bison="$(bison --version | sed q | cut -d' ' -f4)"
version_bison=${version_bison:0:3}
version_bison="$(bison --version | sed q | cut -d' ' -f4 | cut -d'.' -f1,2 )"
AS_IF([awk -v ver="$version_bison" 'BEGIN { if (ver < 2.4) exit 1; }'],
[have_bison_correct=yes], [have_bison_correct=no])
@@ -42,6 +41,10 @@ if test "x${have_bison_correct}" = xno; then
(exit 1); exit 1;
fi
if test "x$LEX" == "x:"; then
AC_MSG_ERROR("flex/lex is missing")
fi
# Checks for header files.
AC_CHECK_HEADERS([float.h limits.h stdint.h stdlib.h string.h strings.h sys/timeb.h unistd.h])
Executable → Regular
+4 -1
View File
@@ -122,6 +122,7 @@ static void printusage(const char *cmd) {
printf(" as well as REF_TO in ARRAYs and STRUCTs (a non-standard extension!)\n");
printf(" -a : allow use of non-literals in array size limits (a non-standard extension!)\n");
printf(" -i : allow POUs with no in out and inout parameters (a non-standard extension!)\n");
printf(" -b : allow functions returning VOID (a non-standard extension!)\n");
printf(" -e : disable generation of implicit EN and ENO parameters.\n");
printf(" -c : create conversion functions for enumerated data types\n");
printf(" -O : options for output (code generation) stage. Available options for %s are...\n", cmd);
@@ -145,6 +146,7 @@ int main(int argc, char **argv) {
int path_len;
/* Default values for the command line options... */
runtime_options.allow_void_datatype = false; /* disable: allow declaration of functions returning VOID */
runtime_options.allow_missing_var_in = false; /* disable: allow definition and invocation of POUs with no input, output and in_out parameters! */
runtime_options.disable_implicit_en_eno = false; /* disable: do not generate EN and ENO parameters */
runtime_options.pre_parsing = false; /* disable: allow use of forward references (run pre-parsing phase before the definitive parsing phase that builds the AST) */
@@ -163,7 +165,7 @@ int main(int argc, char **argv) {
/******************************************/
/* Parse command line options... */
/******************************************/
while ((optres = getopt(argc, argv, ":nehvfplsrRaicI:T:O:")) != -1) {
while ((optres = getopt(argc, argv, ":nehvfplsrRabicI:T:O:")) != -1) {
switch(optres) {
case 'h':
printusage(argv[0]);
@@ -179,6 +181,7 @@ int main(int argc, char **argv) {
runtime_options.ref_nonstand_extensions = true; break;
case 'r': runtime_options.ref_standard_extensions = true; break;
case 'a': runtime_options.nonliteral_in_array_size = true; break;
case 'b': runtime_options.allow_void_datatype = true; break;
case 'i': runtime_options.allow_missing_var_in = true; break;
case 'c': runtime_options.conversion_functions = true; break;
case 'n': runtime_options.nested_comments = true; break;
+1
View File
@@ -40,6 +40,7 @@
typedef struct {
/* options specific to stage1_2 */
bool allow_void_datatype; /* Allow declaration of functions returning VOID */
bool allow_missing_var_in; /* Allow definition and invocation of POUs with no input, output and in_out parameters! */
bool disable_implicit_en_eno; /* Disable the generation of implicit EN and ENO parameters on functions and Function Blocks */
bool pre_parsing; /* Support forward references (Run a pre-parsing phase before the defintive parsing phase that builds the AST) */
+3 -1
View File
@@ -1,7 +1,9 @@
include ../common.mk
## Flags for yacc syntax parser generator (bison)
AM_YFLAGS = -d
AM_LFLAGS = -o$(LEX_OUTPUT_ROOT).c
## Flags for lex lexer generator (flex)
AM_LFLAGS = --warn -o$(LEX_OUTPUT_ROOT).c
# Make sure this header file is generated first (by bison), as it is included
# by other C++ code that will also be compiled.
@@ -119,7 +119,7 @@ void *create_enumtype_conversion_functions_c::visit(enumerated_value_list_c *sym
currentTokenList.clear();
list = (list_c *)symbol;
for (int i = 0; i < list->n; i++) {
list->elements[i]->accept(*this);
list->get_element(i)->accept(*this);
currentTokenList.push_back(currentToken);
}
+90 -27
View File
@@ -119,7 +119,7 @@ void yyerror (const char *error_msg);
#define FOR_EACH_ELEMENT(elem, list, code) { \
symbol_c *elem; \
for(int i = 0; i < list->n; i++) { \
elem = list->elements[i]; \
elem = list->get_element(i); \
code; \
} \
}
@@ -373,6 +373,32 @@ typedef struct YYLTYPE {
%type <leaf> prev_declared_derived_function_block_name
%type <leaf> prev_declared_program_type_name
/* Tokens used to help resolve a reduce/reduce conflict */
/* The mentioned conflict only arises due to a non-standard feature added to matiec.
* Namely, the permission to call functions returning VOID as an ST statement.
* e.g.: FUNCTION foo: VOID
* VAR_INPUT i: INT; END_VAR;
* ...
* END_FUNCTION
*
* FUNCTION BAR: BOOL
* VAR b: bool; END_VAR
* foo(i:=42); <--- Calling foo outside an expression. Function invocation is considered an ST statement!!
* END_FUNCTION
*
* The above function invocation may also be reduced to a formal IL function invocation, so we get a
* reduce/reduce conflict to st_statement_list/instruction_list (or something equivalent).
*
* We solve this by having flex determine if it is ST or IL invocation (ST ends with a ';' !!).
* At the start of a function/FB/program body, flex will tell bison whether to expect ST or IL code!
* This is why we need the following two tokens!
*
* NOTE: flex was already determing whther it was parsing ST or IL code as it can only send
* EOL tokens when parsing IL. However, did this silently without telling bison about this.
* Now, it does
*/
%token start_ST_body_token
%token start_IL_body_token
@@ -650,6 +676,9 @@ typedef struct YYLTYPE {
%token TIME_OF_DAY
%token TOD
/* A non-standard extension! */
%token VOID
/******************************************************/
/* Symbols defined in */
/* "Safety Software Technical Specification, */
@@ -1425,6 +1454,7 @@ typedef struct YYLTYPE {
%type <leaf> while_statement
%type <leaf> repeat_statement
%type <leaf> exit_statement
%type <leaf> continue_statement
/* Integrated directly into for_statement */
// %type <leaf> for_list
@@ -1444,6 +1474,7 @@ typedef struct YYLTYPE {
%token END_REPEAT
%token EXIT
%token CONTINUE
%%
@@ -3184,15 +3215,15 @@ structure_element_declaration_list:
structure_element_declaration:
structure_element_name ':' simple_spec_init
{$$ = new structure_element_declaration_c($1, $3, locloc(@$));}
{$$ = new structure_element_declaration_c($1, $3, locloc(@$)); $$->token = $1->token;}
| structure_element_name ':' subrange_spec_init
{$$ = new structure_element_declaration_c($1, $3, locloc(@$));}
{$$ = new structure_element_declaration_c($1, $3, locloc(@$)); $$->token = $1->token;}
| structure_element_name ':' enumerated_spec_init
{$$ = new structure_element_declaration_c($1, $3, locloc(@$));}
{$$ = new structure_element_declaration_c($1, $3, locloc(@$)); $$->token = $1->token;}
| structure_element_name ':' array_spec_init
{$$ = new structure_element_declaration_c($1, $3, locloc(@$));}
{$$ = new structure_element_declaration_c($1, $3, locloc(@$)); $$->token = $1->token;}
| structure_element_name ':' initialized_structure
{$$ = new structure_element_declaration_c($1, $3, locloc(@$));}
{$$ = new structure_element_declaration_c($1, $3, locloc(@$)); $$->token = $1->token;}
| structure_element_name ':' ref_spec_init /* non standard extension: Allow use of struct elements storing REF_TO datatypes (either using REF_TO or a previosuly declared ref type) */
{ $$ = new structure_element_declaration_c($1, $3, locloc(@$));
if (!allow_ref_to_in_derived_datatypes) {
@@ -3506,7 +3537,7 @@ variable:
symbolic_variable
| prev_declared_direct_variable
| eno_identifier
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
;
@@ -3515,15 +3546,15 @@ symbolic_variable:
* prev_declared_variable_name | prev_declared_fb_name | prev_declared_global_var_name
*/
prev_declared_fb_name
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
| prev_declared_global_var_name
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
| prev_declared_variable_name
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
| multi_element_variable
/*
| identifier
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
*/
| symbolic_variable '^'
/* Dereferencing operator defined in IEC 61131-3 v3. However, implemented here differently then how it is defined in the standard! See following note for explanation! */
@@ -3565,7 +3596,7 @@ symbolic_variable:
any_symbolic_variable:
// variable_name -> replaced by any_identifier
any_identifier
{$$ = new symbolic_variable_c($1, locloc(@$));}
{$$ = new symbolic_variable_c($1, locloc(@$)); $$->token = $1->token;}
| any_multi_element_variable
;
@@ -5008,6 +5039,14 @@ function_declaration:
direct_variable_symtable.pop();
library_element_symtable.insert($1, prev_declared_derived_function_name_token);
}
/* | FUNCTION derived_function_name ':' VOID io_OR_function_var_declarations_list function_body END_FUNCTION */
| function_name_declaration ':' VOID io_OR_function_var_declarations_list function_body END_FUNCTION
{$$ = new function_declaration_c($1, new void_type_name_c(locloc(@3)), $4, $5, locloc(@$));
if (!runtime_options.disable_implicit_en_eno) add_en_eno_param_decl_c::add_to($$); /* add EN and ENO declarations, if not already there */
variable_name_symtable.pop();
direct_variable_symtable.pop();
library_element_symtable.insert($1, prev_declared_derived_function_name_token);
}
/* ERROR_CHECK_BEGIN */
| function_name_declaration elementary_type_name io_OR_function_var_declarations_list function_body END_FUNCTION
{$$ = NULL; print_err_msg(locl(@1), locf(@2), "':' missing after function name in function declaration."); yynerrs++;}
@@ -5172,8 +5211,8 @@ var2_init_decl_list:
function_body:
statement_list {$$ = $1;} /* if we leave it for the default action we get a type clash! */
| instruction_list {$$ = $1;} /* if we leave it for the default action we get a type clash! */
start_ST_body_token statement_list {$$ = $2;}
| start_IL_body_token instruction_list {$$ = $2;}
/*
| ladder_diagram
| function_block_diagram
@@ -5246,7 +5285,7 @@ function_block_declaration:
{$$ = NULL; print_err_msg(locl(@2), locf(@3), "no variable(s) declared and body defined in function block declaration."); yynerrs++;}
*/
| FUNCTION_BLOCK derived_function_block_name io_OR_other_var_declarations_list function_block_body END_OF_INPUT
{$$ = NULL; print_err_msg(locf(@1), locl(@2), "no variable(s) declared and body defined in function block declaration."); yynerrs++;}
{$$ = NULL; print_err_msg(locf(@1), locl(@2), "expecting END_FUNCTION_BLOCK before end of file."); yynerrs++;}
| FUNCTION_BLOCK error END_FUNCTION_BLOCK
{$$ = NULL; print_err_msg(locf(@2), locl(@2), "unknown error in function block declaration."); yyerrok;}
/* ERROR_CHECK_END */
@@ -5355,9 +5394,21 @@ non_retentive_var_decls:
function_block_body:
statement_list {$$ = $1;}
| instruction_list {$$ = $1;}
| sequential_function_chart {$$ = $1;}
/* NOTE: start_ST_body_token is a dummy token generated by flex when it determines it is starting to parse a POU body in ST
* start_IL_body_token is a dummy token generated by flex when it determines it is starting to parse a POU body in IL
* These tokens help remove a reduce/reduce conflict in bison, between a formal function invocation in IL, and a
* function invocation used as a statement (a non-standard extension added to matiec)
* e.g: FUNCTION_BLOCK foo
* VAR ... END_VAR
* func_returning_void(in1 := 3
* ); --> only the presence or absence of ';' will determine whether this is a IL or ST
* function invocation. (In standard ST this would be ilegal, in matiec we allow it
* when activated by a command line option)
* END_FUNCTION
*/
start_ST_body_token statement_list {$$ = $2;}
| start_IL_body_token instruction_list {$$ = $2;}
| sequential_function_chart {$$ = $1;}
/*
| ladder_diagram
| function_block_diagram
@@ -5797,17 +5848,17 @@ transition_priority:
transition_condition:
':' eol_list simple_instr_list
{$$ = new transition_condition_c($3, NULL, locloc(@$));}
start_IL_body_token ':' eol_list simple_instr_list
{$$ = new transition_condition_c($4, NULL, locloc(@$));}
| ASSIGN expression ';'
{$$ = new transition_condition_c(NULL, $2, locloc(@$));}
/* ERROR_CHECK_BEGIN */
| eol_list simple_instr_list
{$$ = NULL; print_err_msg(locl(@1), locf(@2), "':' missing before IL condition in transition declaration."); yynerrs++;}
| ':' eol_list error
| start_IL_body_token eol_list simple_instr_list
{$$ = NULL; print_err_msg(locl(@2), locf(@3), "':' missing before IL condition in transition declaration."); yynerrs++;}
| start_IL_body_token ':' eol_list error
{$$ = NULL;
if (is_current_syntax_token()) {print_err_msg(locl(@2), locf(@3), "no instructions defined in IL condition of transition declaration.");}
else {print_err_msg(locf(@3), locl(@3), "invalid instructions in IL condition of transition declaration."); yyclearin;}
if (is_current_syntax_token()) {print_err_msg(locl(@3), locf(@4), "no instructions defined in IL condition of transition declaration.");}
else {print_err_msg(locf(@4), locl(@4), "invalid instructions in IL condition of transition declaration."); yyclearin;}
yyerrok;
}
| ASSIGN ';'
@@ -7856,6 +7907,15 @@ statement:
| subprogram_control_statement
| selection_statement
| iteration_statement
| function_invocation
{ /* This is a non-standard extension (calling a function outside an ST expression!) */
/* Only allow this if command line option has been selected... */
$$ = $1;
if (!runtime_options.allow_void_datatype) {
print_err_msg(locf(@1), locl(@1), "Function invocation in ST code is not allowed outside an expression. To allow this non-standard syntax, activate the apropriate command line option.");
yynerrs++;
}
}
;
@@ -8248,6 +8308,7 @@ iteration_statement:
| while_statement
| repeat_statement
| exit_statement
| continue_statement
;
@@ -8330,7 +8391,7 @@ for_statement:
*/
control_variable:
prev_declared_variable_name
{$$ = new symbolic_variable_c($1,locloc(@$));};
{$$ = new symbolic_variable_c($1,locloc(@$)); $$->token = $1->token;};
// control_variable: identifier {$$ = $1;};
/* Integrated directly into for_statement */
@@ -8391,7 +8452,9 @@ exit_statement:
EXIT {$$ = new exit_statement_c(locloc(@$));}
;
continue_statement:
CONTINUE {$$ = new continue_statement_c(locloc(@$));}
;
File diff suppressed because it is too large Load Diff
View File

Some files were not shown because too many files have changed in this diff Show More