Allow use of GLOBAL/EXTERNAL variables as control variable of FOR loop.
--- a/stage4/generate_c/generate_c_st.cc Mon Apr 03 18:30:50 2017 +0100
+++ b/stage4/generate_c/generate_c_st.cc Sun Apr 09 23:43:04 2017 +0100
@@ -1233,19 +1233,26 @@
/* B 3.2.4 Iteration Statements */
/********************************/
void *visit(for_statement_c *symbol) {
- s4o.print("for(");
- symbol->control_variable->accept(*this);
- s4o.print(" = ");
- symbol->beg_expression->accept(*this);
- s4o.print("; ");
+ /* Due to the way the GET/SET_GLOBAL accessor macros access VAR_GLOBAL variables,
+ * these varibles cannot be used within a C for(;;) loop.
+ * We must therefore implemnt the FOR END_FOR loop as a C while() loop
+ */
+ s4o.print("/* FOR ... */\n" + s4o.indent_spaces);
+ /* For the initialization part, we create an assignment_statement_c */
+ /* and have this visitor visit it! */
+ assignment_statement_c ini_assignment(symbol->control_variable, symbol->beg_expression);
+ ini_assignment.accept(*this);
+ //symbol->control_variable->accept(*this); // this does not work for VAR_GLOBAL variables
+ //s4o.print(" = ");
+ //symbol->beg_expression->accept(*this);
+
+ /* comparison // check for end of loop */
+ s4o.print(";\n" + s4o.indent_spaces + "while( ");
if (symbol->by_expression == NULL) {
- /* increment by 1 */
+ /* increment by 1 */
symbol->control_variable->accept(*this);
s4o.print(" <= ");
symbol->end_expression->accept(*this);
- s4o.print("; ");
- symbol->control_variable->accept(*this);
- s4o.print("++");
} else {
/* increment by user defined value */
/* The user defined increment value may be negative, in which case
@@ -1265,19 +1272,47 @@
symbol->control_variable->accept(*this);
s4o.print(" >= (");
symbol->end_expression->accept(*this);
- s4o.print(")); ");
- symbol->control_variable->accept(*this);
- s4o.print(" += (");
- symbol->by_expression->accept(*this);
- s4o.print(")");
- }
- s4o.print(")");
+ s4o.print(")) ");
+ }
+ s4o.print(" ) {\n");
- s4o.print(" {\n");
+ /* the body part */
s4o.indent_right();
symbol->statement_list->accept(*this);
+
+ /* increment part */
+ s4o.print(s4o.indent_spaces + "/* BY ... (of FOR loop) */\n");
+ s4o.print(s4o.indent_spaces);
+ if (symbol->by_expression == NULL) {
+ /* increment by 1 */
+ /* For the increment part, we create an add_expression_c and assignment_statement_c */
+ /* and have this visitor vist the latter! */
+ integer_c integer_oneval("1");
+ add_expression_c add_expression(symbol->control_variable, &integer_oneval);
+ assignment_statement_c inc_assignment(symbol->control_variable, &add_expression);
+ integer_oneval.const_value._int64 .set(1); // set the stage3 anottation we need
+ integer_oneval.const_value._uint64.set(1); // set the stage3 anottation we need
+ integer_oneval.datatype = symbol->control_variable->datatype; // set the stage3 anottation we need
+ add_expression.datatype = symbol->control_variable->datatype; // set the stage3 anottation we need
+ inc_assignment.accept(*this);
+ //symbol->control_variable->accept(*this); // this does not work for VAR_GLOBAL variables
+ //s4o.print("++");
+ } else {
+ /* increment by user defined value */
+ /* For the increment part, we create an add_expression_c and assignment_statement_c */
+ /* and have this visitor vist the latter! */
+ add_expression_c add_expression(symbol->control_variable, symbol->by_expression);
+ assignment_statement_c inc_assignment(symbol->control_variable, &add_expression);
+ add_expression.datatype = symbol->control_variable->datatype; // set the stage3 anottation we need
+ inc_assignment.accept(*this);
+ //symbol->control_variable->accept(*this); // this does not work for VAR_GLOBAL variables
+ //s4o.print(" += (");
+ //symbol->by_expression->accept(*this);
+ //s4o.print(")");
+ }
+
s4o.indent_left();
- s4o.print(s4o.indent_spaces); s4o.print("}");
+ s4o.print(";\n" + s4o.indent_spaces + "} /* END_FOR */");
return NULL;
}