stage4/generate_c/generate_c_typedecl.cc
changeset 98 d0cdf1d00b74
parent 70 e1f0ebd2d9ec
child 121 9e8ce092e169
equal deleted inserted replaced
97:55ffcf693d6d 98:d0cdf1d00b74
    46 
    46 
    47 
    47 
    48 
    48 
    49 class generate_c_typedecl_c: public generate_c_base_c {
    49 class generate_c_typedecl_c: public generate_c_base_c {
    50 
    50 
       
    51   private:
       
    52     symbol_c* current_type_name;
       
    53     search_base_type_c search_base_type;
       
    54 
    51   public:
    55   public:
    52     generate_c_typedecl_c(stage4out_c *s4o_ptr): generate_c_base_c(s4o_ptr) {}
    56     generate_c_typedecl_c(stage4out_c *s4o_ptr): generate_c_base_c(s4o_ptr) {
       
    57       current_typedefinition = none_td;
       
    58       current_basetypedeclaration = none_bd;
       
    59     }
    53     ~generate_c_typedecl_c(void) {}
    60     ~generate_c_typedecl_c(void) {}
    54 
    61 
       
    62     typedef enum {
       
    63       none_td,
       
    64       subrange_td,
       
    65       array_td
       
    66     } typedefinition_t;
       
    67 
       
    68     typedefinition_t current_typedefinition;
       
    69 
       
    70     typedef enum {
       
    71       none_bd,
       
    72       subrangebasetype_bd,
       
    73       subrangebasetypeexploration_bd,
       
    74       subrangetest_bd,
       
    75       arraybasetype_bd,
       
    76       arraysubrange_bd,
       
    77       arraytranslateindex_bd
       
    78     } basetypedeclaration_t;
       
    79     
       
    80     basetypedeclaration_t current_basetypedeclaration;
       
    81 
       
    82     int extract_integer(symbol_c *integer) {
       
    83       return atoi(((integer_c *)integer)->value);
       
    84     }
       
    85 
       
    86     void print_integer(unsigned int integer) {
       
    87       char str[10];
       
    88       sprintf(str, "%d", integer);
       
    89       s4o.print(str);
       
    90     }
    55 
    91 
    56 /***************************/
    92 /***************************/
    57 /* B 0 - Programming Model */
    93 /* B 0 - Programming Model */
    58 /***************************/
    94 /***************************/
    59   /* leave for derived classes... */
    95   /* leave for derived classes... */
   108   /* originally empty... */
   144   /* originally empty... */
   109 
   145 
   110 /********************************/
   146 /********************************/
   111 /* B 1.3.3 - Derived data types */
   147 /* B 1.3.3 - Derived data types */
   112 /********************************/
   148 /********************************/
       
   149 /*  subrange_type_name ':' subrange_spec_init */
       
   150 void *visit(subrange_type_declaration_c *symbol) {
       
   151   TRACE("subrange_type_declaration_c");  
       
   152   /* add this type declaration to the type symbol table... */
       
   153   type_symtable.insert(symbol->subrange_type_name, symbol->subrange_spec_init);
       
   154   
       
   155   s4o.print("typedef ");
       
   156   current_basetypedeclaration = subrangebasetype_bd;
       
   157   symbol->subrange_spec_init->accept(*this);
       
   158   current_basetypedeclaration = none_bd;
       
   159   s4o.print(" ");
       
   160   symbol->subrange_type_name->accept(*this);
       
   161   s4o.print(";\n\n");
       
   162   
       
   163   current_basetypedeclaration = subrangebasetypeexploration_bd;
       
   164   symbol->subrange_spec_init->accept(*this);
       
   165   current_basetypedeclaration = none_bd;
       
   166   
       
   167   current_type_name = symbol->subrange_type_name;
       
   168   
       
   169   current_basetypedeclaration = subrangetest_bd;
       
   170   symbol->subrange_spec_init->accept(*this);
       
   171   current_basetypedeclaration = none_bd;
       
   172   
       
   173   return NULL;
       
   174 }
       
   175 
       
   176 /* subrange_specification ASSIGN signed_integer */
   113 void *visit(subrange_spec_init_c *symbol) {
   177 void *visit(subrange_spec_init_c *symbol) {
   114   TRACE("subrange_spec_init_c");
   178   TRACE("subrange_spec_init_c");
   115   // TODO...
   179   current_typedefinition = subrange_td;
   116   ERROR;
   180   symbol->subrange_specification->accept(*this);
       
   181   current_typedefinition = none_td;
       
   182   return NULL;
       
   183 }
       
   184 
       
   185 /*  integer_type_name '(' subrange')' */
       
   186 void *visit(subrange_specification_c *symbol) {
       
   187   switch (current_basetypedeclaration) {
       
   188     case subrangebasetype_bd:
       
   189       symbol->integer_type_name->accept(*this);
       
   190       break;
       
   191     case subrangebasetypeexploration_bd:
       
   192       search_base_type.explore_type(symbol->integer_type_name);
       
   193       break;
       
   194     case subrangetest_bd:
       
   195       if (symbol->subrange != NULL) {
       
   196         current_type_name->accept(*this);
       
   197         s4o.print(" __CHECK_");
       
   198         current_type_name->accept(*this);
       
   199         s4o.print("(");
       
   200         current_type_name->accept(*this);
       
   201         s4o.print(" value) {\n");
       
   202         s4o.indent_right();
       
   203         
       
   204         if (search_base_type.base_is_subrange()) {
       
   205           s4o.print(s4o.indent_spaces + "value = __CHECK_");
       
   206           symbol->integer_type_name->accept(*this);
       
   207           s4o.print("(value);\n");
       
   208         }
       
   209         
       
   210         symbol->subrange->accept(*this);
       
   211         
       
   212         s4o.indent_left();
       
   213         s4o.print("}\n");
       
   214       }
       
   215       else {
       
   216         s4o.print("#define __CHECK_");
       
   217         current_type_name->accept(*this);
       
   218         s4o.print(" __CHECK_");
       
   219         symbol->integer_type_name->accept(*this);
       
   220         s4o.print("\n");
       
   221       } 
       
   222       break;
       
   223     default:
       
   224       break;
       
   225   }
       
   226   return NULL;
       
   227 }
       
   228 
       
   229 /*  signed_integer DOTDOT signed_integer */
       
   230 void *visit(subrange_c *symbol) {
       
   231   int dimension;
       
   232   switch (current_typedefinition) {
       
   233     case array_td:
       
   234       if (current_basetypedeclaration == arraysubrange_bd) {
       
   235         s4o.print("[");
       
   236         dimension = extract_integer(symbol->upper_limit) - extract_integer(symbol->lower_limit) + 1;
       
   237         print_integer(dimension);
       
   238         s4o.print("]");
       
   239       }
       
   240       else
       
   241         symbol->lower_limit->accept(*this);
       
   242       break;
       
   243     case subrange_td:
       
   244       s4o.print(s4o.indent_spaces + "if (value < ");
       
   245       symbol->lower_limit->accept(*this);
       
   246       s4o.print(")\n");
       
   247       s4o.indent_right();
       
   248       s4o.print(s4o.indent_spaces + "return ");
       
   249       symbol->lower_limit->accept(*this);
       
   250       s4o.print(";\n");
       
   251       s4o.indent_left();
       
   252       s4o.print(s4o.indent_spaces + "else if (value > ");
       
   253       symbol->upper_limit->accept(*this);
       
   254       s4o.print(")\n");
       
   255       s4o.indent_right();
       
   256       s4o.print(s4o.indent_spaces + "return ");
       
   257       symbol->upper_limit->accept(*this);
       
   258       s4o.print(";\n");
       
   259       s4o.indent_left();
       
   260       s4o.print(s4o.indent_spaces + "else\n");
       
   261       s4o.indent_right();
       
   262       s4o.print(s4o.indent_spaces + "return value;\n");
       
   263       s4o.indent_left();
       
   264     default:
       
   265       break;
       
   266   }
       
   267   return NULL;
       
   268 }
       
   269 
       
   270 /*  enumerated_type_name ':' enumerated_spec_init */
       
   271 void *visit(enumerated_type_declaration_c *symbol) {
       
   272   TRACE("enumerated_type_declaration_c");
       
   273   /* add this type declaration to the type symbol table... */
       
   274   type_symtable.insert(symbol->enumerated_type_name, symbol->enumerated_spec_init);
       
   275   
       
   276   s4o.print("typedef enum {\n");
       
   277   s4o.indent_right();
       
   278   symbol->enumerated_spec_init->accept(*this);
       
   279   s4o.indent_left();
       
   280   s4o.print("} ");
       
   281   symbol->enumerated_type_name->accept(*this);
       
   282   s4o.print(";\n");
   117   return NULL;
   283   return NULL;
   118 }
   284 }
   119 
   285 
   120 void *visit(enumerated_spec_init_c *symbol) {
   286 void *visit(enumerated_spec_init_c *symbol) {
   121   TRACE("enumerated_spec_init_c");
   287   TRACE("enumerated_spec_init_c");
   122   // TODO...
   288   symbol->enumerated_specification->accept(*this);
   123   ERROR;
   289   return NULL;
       
   290 }
       
   291 
       
   292 /* helper symbol for enumerated_specification->enumerated_spec_init */
       
   293 /* enumerated_value_list ',' enumerated_value */
       
   294 void *visit(enumerated_value_list_c *symbol) {
       
   295   print_list(symbol, s4o.indent_spaces, ",\n"+s4o.indent_spaces, "\n");
       
   296   return NULL;
       
   297 }
       
   298 
       
   299 /* enumerated_type_name '#' identifier */
       
   300 void *visit(enumerated_value_c *symbol) {
       
   301   symbol->value->accept(*this);
       
   302   return NULL;
       
   303 }
       
   304 
       
   305 /*  identifier ':' array_spec_init */
       
   306 void *visit(array_type_declaration_c *symbol) {
       
   307   TRACE("array_type_declaration_c");
       
   308   /* add this type declaration to the type symbol table... */
       
   309   type_symtable.insert(symbol->identifier, symbol->array_spec_init);
       
   310   
       
   311   s4o.print("typedef ");
       
   312   current_basetypedeclaration = arraybasetype_bd;
       
   313   symbol->array_spec_init->accept(*this);
       
   314   current_basetypedeclaration = none_bd;
       
   315   s4o.print(" ");
       
   316   symbol->identifier->accept(*this);
       
   317   current_basetypedeclaration = arraysubrange_bd;
       
   318   symbol->array_spec_init->accept(*this);
       
   319   current_basetypedeclaration = none_bd;
       
   320   s4o.print(";\n");
       
   321   
       
   322   search_base_type.explore_type(symbol->array_spec_init);
       
   323   if (search_base_type.base_is_subrange()) {
       
   324     s4o.print("#define __CHECK_");
       
   325     symbol->identifier->accept(*this);
       
   326     s4o.print(" __CHECK_");
       
   327     current_basetypedeclaration = arraybasetype_bd;
       
   328     symbol->array_spec_init->accept(*this);
       
   329     current_basetypedeclaration = none_bd;
       
   330     s4o.print("\n");
       
   331   }
       
   332   
       
   333   current_type_name = symbol->identifier;
       
   334   current_basetypedeclaration = arraytranslateindex_bd;
       
   335   symbol->array_spec_init->accept(*this);
       
   336   current_basetypedeclaration = none_bd;
       
   337   s4o.print("\n");
       
   338   
       
   339   return NULL;
       
   340 }
       
   341 
       
   342 /* array_specification [ASSIGN array_initialization} */
       
   343 /* array_initialization may be NULL ! */
       
   344 void *visit(array_spec_init_c *symbol) {
       
   345   TRACE("array_spec_init_c");
       
   346   current_typedefinition = array_td;
       
   347   symbol->array_specification->accept(*this);
       
   348   current_typedefinition = none_td;
       
   349   return NULL;
       
   350 }
       
   351 
       
   352 /* ARRAY '[' array_subrange_list ']' OF non_generic_type_name */
       
   353 void *visit(array_specification_c *symbol) {
       
   354   switch (current_basetypedeclaration) {
       
   355     case arraybasetype_bd:
       
   356       symbol->non_generic_type_name->accept(*this);
       
   357       break;
       
   358     case arraysubrange_bd:
       
   359     case arraytranslateindex_bd:
       
   360       symbol->array_subrange_list->accept(*this);
       
   361       break;
       
   362     default:
       
   363       break;
       
   364   }
       
   365   return NULL;
       
   366 }
       
   367 
       
   368 /* helper symbol for array_specification */
       
   369 /* array_subrange_list ',' subrange */
       
   370 void *visit(array_subrange_list_c *symbol) {
       
   371   if (current_basetypedeclaration == arraytranslateindex_bd) {
       
   372     for (int i = 0; i < symbol->n; i++) {
       
   373       s4o.print("#define __");
       
   374       current_type_name->accept(*this);
       
   375       s4o.print("_TRANSIDX");
       
   376       print_integer(i);
       
   377       s4o.print("(index) (index) - ");
       
   378       symbol->elements[i]->accept(*this);
       
   379       s4o.print("\n");
       
   380     }
       
   381   }
       
   382   else
       
   383     print_list(symbol);
   124   return NULL;
   384   return NULL;
   125 }
   385 }
   126 
   386 
   127 /*  TYPE type_declaration_list END_TYPE */
   387 /*  TYPE type_declaration_list END_TYPE */
   128 void *visit(data_type_declaration_c *symbol) {
   388 void *visit(data_type_declaration_c *symbol) {
   133 }
   393 }
   134 
   394 
   135 /* helper symbol for data_type_declaration */
   395 /* helper symbol for data_type_declaration */
   136 void *visit(type_declaration_list_c *symbol) {
   396 void *visit(type_declaration_list_c *symbol) {
   137   TRACE("type_declaration_list_c");
   397   TRACE("type_declaration_list_c");
   138   return print_list(symbol);
   398   return print_list(symbol, "", "\n");
   139 }
   399 }
   140 
   400 
   141 /*  simple_type_name ':' simple_spec_init */
   401 /*  simple_type_name ':' simple_spec_init */
   142 void *visit(simple_type_declaration_c *symbol) {
   402 void *visit(simple_type_declaration_c *symbol) {
   143   TRACE("simple_type_declaration_c");
   403   TRACE("simple_type_declaration_c");