diff -r 694127983aa4 -r dd50a82ae8da stage4/generate_c/generate_c_st.cc --- a/stage4/generate_c/generate_c_st.cc Sun Mar 15 20:49:55 2015 +0000 +++ b/stage4/generate_c/generate_c_st.cc Wed Apr 15 23:25:07 2015 +0100 @@ -54,12 +54,6 @@ fparam_output_vg } variablegeneration_t; - typedef enum { - single_cg, - subrange_cg, - none_cg - } casegeneration_t; - private: /* When calling a function block, we must first find it's type, * by searching through the declarations of the variables currently @@ -89,7 +83,6 @@ bool first_subrange_case_list; variablegeneration_t wanted_variablegeneration; - casegeneration_t wanted_casegeneration; public: generate_c_st_c(stage4out_c *s4o_ptr, symbol_c *name, symbol_c *scope, const char *variable_prefix = NULL) @@ -105,7 +98,6 @@ fcall_number = 0; fbname = name; wanted_variablegeneration = expression_vg; - wanted_casegeneration = none_cg; } virtual ~generate_c_st_c(void) { @@ -234,17 +226,7 @@ /* signed_integer DOTDOT signed_integer */ void *visit(subrange_c *symbol) { - switch (wanted_casegeneration) { - case subrange_cg: - s4o.print("__case_expression >= "); - symbol->lower_limit->accept(*this); - s4o.print(" && __case_expression <= "); - symbol->upper_limit->accept(*this); - break; - default: - symbol->lower_limit->accept(*this); - break; - } + symbol->lower_limit->accept(*this); return NULL; } @@ -1223,100 +1205,62 @@ expression_type->accept(*this); s4o.print(" __case_expression = "); symbol->expression->accept(*this); - s4o.print(";\n" + s4o.indent_spaces + "switch (__case_expression) {\n"); - s4o.indent_right(); - wanted_casegeneration = single_cg; - symbol->case_element_list->accept(*this); - wanted_casegeneration = subrange_cg; - s4o.print(s4o.indent_spaces + "default:\n"); - s4o.indent_right(); - first_subrange_case_list = true; + s4o.print(";\n"); symbol->case_element_list->accept(*this); if (symbol->statement_list != NULL) { - if (!first_subrange_case_list) { - s4o.print(s4o.indent_spaces + "else {\n"); - s4o.indent_right(); - } + s4o.print(s4o.indent_spaces + "else {\n"); + s4o.indent_right(); symbol->statement_list->accept(*this); - if (!first_subrange_case_list) { - s4o.indent_left(); - s4o.print(s4o.indent_spaces + "}\n"); - } - } - s4o.print(s4o.indent_spaces + "break;\n"); + s4o.indent_left(); + s4o.print(s4o.indent_spaces + "}\n"); + } s4o.indent_left(); - wanted_casegeneration = none_cg; + s4o.print(s4o.indent_spaces + "}"); + return NULL; +} + + +/* helper symbol for case_statement */ +void *visit(case_element_list_c *symbol) {return print_list(symbol, s4o.indent_spaces+"if ", s4o.indent_spaces+"else if ");} + +void *visit(case_element_c *symbol) { + symbol->case_list->accept(*this); + s4o.print(" {\n"); + s4o.indent_right(); + symbol->statement_list->accept(*this); s4o.indent_left(); s4o.print(s4o.indent_spaces + "}\n"); - s4o.indent_left(); - s4o.print(s4o.indent_spaces + "}"); - return NULL; -} - -/* helper symbol for case_statement */ -void *visit(case_element_list_c *symbol) {return print_list(symbol);} - -void *visit(case_element_c *symbol) { - case_element_iterator_c *case_element_iterator; - symbol_c* element = NULL; - bool first_element = true; - - switch (wanted_casegeneration) { - case single_cg: - case_element_iterator = new case_element_iterator_c(symbol->case_list, case_element_iterator_c::element_single); - for (element = case_element_iterator->next(); element != NULL; element = case_element_iterator->next()) { - if (first_element) first_element = false; - s4o.print(s4o.indent_spaces + "case "); - element->accept(*this); - s4o.print(":\n"); - } - delete case_element_iterator; - break; - - case subrange_cg: - case_element_iterator = new case_element_iterator_c(symbol->case_list, case_element_iterator_c::element_subrange); - for (element = case_element_iterator->next(); element != NULL; element = case_element_iterator->next()) { - if (first_element) { - if (first_subrange_case_list) { - s4o.print(s4o.indent_spaces + "if ("); - first_subrange_case_list = false; - } - else { - s4o.print(s4o.indent_spaces + "else if ("); - } - first_element = false; - } - else { - s4o.print(" && "); - } - element->accept(*this); - } - delete case_element_iterator; - if (!first_element) { - s4o.print(") {\n"); - } - break; - - default: - break; - } - - if (!first_element) { - s4o.indent_right(); - symbol->statement_list->accept(*this); - switch (wanted_casegeneration) { - case single_cg: - s4o.print(s4o.indent_spaces + "break;\n"); - s4o.indent_left(); - break; - case subrange_cg: - s4o.indent_left(); - s4o.print(s4o.indent_spaces + "}\n"); - break; - default: - break; - } - } + return NULL; +} + + +void *visit(case_list_c *symbol) { + s4o.print("("); + for (int i = 0; i < symbol->n; i++) { + /* if not the first element, then add an '||', a '\n', and add some spaces to get nice alignment */ + /* example of generated C code (codition) for + * case XX of + * 10..20,42,15..99: <---- C code is for this line! + * + * else if ((__case_expression >= 10 && __case_expression <= 20) || + * (__case_expression == 42) || + * (__case_expression >= 15 && __case_expression <= 99)) { + */ + if (0 != i) s4o.print(" ||\n" + s4o.indent_spaces + " "); + s4o.print("("); + subrange_c *subrange = dynamic_cast(symbol->elements[i]); + if (NULL == subrange) { + s4o.print("__case_expression == "); + symbol->elements[i]->accept(*this); + } else { + s4o.print("__case_expression >= "); + subrange->lower_limit->accept(*this); + s4o.print(" && __case_expression <= "); + subrange->upper_limit->accept(*this); + } + s4o.print(")"); + } + s4o.print(")"); return NULL; }