stage3/fill_candidate_datatypes.cc
changeset 720 f637ac331a68
parent 719 19595fce59f0
child 724 d19877568878
equal deleted inserted replaced
719:19595fce59f0 720:f637ac331a68
    86 /* Add to the global_enumerated_value_symtable the global enum value constants, i.e. the enum constants used in the enumerated
    86 /* Add to the global_enumerated_value_symtable the global enum value constants, i.e. the enum constants used in the enumerated
    87  * datatypes that are defined inside a TYPE ... END_TYPE declaration.
    87  * datatypes that are defined inside a TYPE ... END_TYPE declaration.
    88  */
    88  */
    89 
    89 
    90  symbol_c null_globalenumvalue_symbol; /* cannot be static, so it may be used in the template!! */
    90  symbol_c null_globalenumvalue_symbol; /* cannot be static, so it may be used in the template!! */
    91  static symtable_c<symbol_c *, &null_globalenumvalue_symbol> global_enumerated_value_symtable;
    91  static dsymtable_c<symbol_c *, &null_globalenumvalue_symbol> global_enumerated_value_symtable;
    92  
    92  
    93  
    93  
    94 class populate_globalenumvalue_symtable_c: public iterator_visitor_c {
    94 class populate_globalenumvalue_symtable_c: public iterator_visitor_c {
    95   private:
    95   private:
    96     symbol_c *current_enumerated_type;
    96     symbol_c *current_enumerated_type;
   137      *       compiler error message).
   137      *       compiler error message).
   138      *       For this reason, the follosing check is commented out.
   138      *       For this reason, the follosing check is commented out.
   139      */
   139      */
   140     /* if (value_type == current_enumerated_type) ERROR; */
   140     /* if (value_type == current_enumerated_type) ERROR; */
   141 
   141 
   142     if (value_type == global_enumerated_value_symtable.end_value())
   142     global_enumerated_value_symtable.insert(symbol->value, current_enumerated_type);
   143 	/* This identifier has not yet been used in any previous declaration of an enumeration data type.
       
   144 	 * so we add it to the symbol table.
       
   145 	 */
       
   146       global_enumerated_value_symtable.insert(symbol->value, current_enumerated_type);
       
   147     else if (value_type != NULL)
       
   148 	/* This identifier has already been used in a previous declaration of an enumeration data type.
       
   149 	 * so we set the symbol in symbol table pointing to NULL.
       
   150 	 */
       
   151       global_enumerated_value_symtable.set(symbol->value, NULL);
       
   152     
       
   153     return NULL;
   143     return NULL;
   154   }
   144   }
   155 
   145 
   156   /**************************************/
   146   /**************************************/
   157   /* B.1.5 - Program organization units */
   147   /* B.1.5 - Program organization units */
   185  *  Values in (A) are added to the enumerated_value_symtable in absyntaxt_utils.cc.
   175  *  Values in (A) are added to the enumerated_value_symtable in absyntaxt_utils.cc.
   186  *  Values in (B) are only in scope inside the POU with the VAR END_VAR declaration.
   176  *  Values in (B) are only in scope inside the POU with the VAR END_VAR declaration.
   187  *
   177  *
   188  * This class will add the enum values in (B) to the local_enumerated_value_symtable.
   178  * This class will add the enum values in (B) to the local_enumerated_value_symtable.
   189  *
   179  *
   190  * If a locally defined enum value is identical to another locally defined enum_value, the
   180  * If a locally defined enum value is identical to another locally defined enum_value, a 
   191  *  corresponding entry in local_enumerated_value_symtable is set to NULL.
   181  *  duplicate entry is created.
   192  *  However, if a locally defined enum value is identical to another globally defined enum_value, the
   182  *  However, if a locally defined enum value is identical to another globally defined enum_value, the
   193  *  corresponding entry in local_enumerated_value_symtable is set to the local datatype (and not NULL).
   183  *  corresponding entry in local_enumerated_value_symtable is also set to the local datatype.
   194  *  This is because anonynous locally feined enum datatypes are anonymous, and its enum values cannot therefore
   184  *  This is because anonynous locally feined enum datatypes are anonymous, and its enum values cannot therefore
   195  *  be disambiguated using EnumType#enum_value (since the enum type does not have a name, it is anonymous!).
   185  *  be disambiguated using EnumType#enum_value (since the enum type does not have a name, it is anonymous!).
   196  *  For this reason we implement the semantics where locally defined enum values, when in scope, will 'cover'
   186  *  For this reason we implement the semantics where locally defined enum values, when in scope, will 'cover'
   197  *  the globally defined enum value with the same name/identifier.
   187  *  the globally defined enum value with the same name/identifier.
   198  *  For example:
   188  *  For example:
   209  *     GlobalEnumVar := GlobalEnumT#xxx1;
   199  *     GlobalEnumVar := GlobalEnumT#xxx1;
   210  *     END_FUNCTION_BLOCK
   200  *     END_FUNCTION_BLOCK
   211  */
   201  */
   212  
   202  
   213  symbol_c null_localenumvalue_symbol; /* cannot be static, so it may be used in the template!! */
   203  symbol_c null_localenumvalue_symbol; /* cannot be static, so it may be used in the template!! */
   214  static symtable_c<symbol_c *, &null_localenumvalue_symbol> local_enumerated_value_symtable;
   204  static dsymtable_c<symbol_c *, &null_localenumvalue_symbol> local_enumerated_value_symtable;
   215 
   205 
   216 
   206 
   217 class populate_enumvalue_symtable_c: public iterator_visitor_c {
   207 class populate_enumvalue_symtable_c: public iterator_visitor_c {
   218   private:
   208   private:
   219     symbol_c *current_enumerated_type;
   209     symbol_c *current_enumerated_type;
   249     /* if the enumerated_value_c is not inside a enumerated_spec_init_c (e.g. used as the inital value of a variable), we simply return */
   239     /* if the enumerated_value_c is not inside a enumerated_spec_init_c (e.g. used as the inital value of a variable), we simply return */
   250     if (current_enumerated_type == NULL) return NULL;  
   240     if (current_enumerated_type == NULL) return NULL;  
   251     /* this is really an ERROR! The initial value may use the syntax NUM_TYPE#enum_value, but in that case we should have return'd in the above statement !! */
   241     /* this is really an ERROR! The initial value may use the syntax NUM_TYPE#enum_value, but in that case we should have return'd in the above statement !! */
   252     if (symbol->type != NULL) ERROR;  
   242     if (symbol->type != NULL) ERROR;  
   253 
   243 
   254     // symbol_c *global_value_type = global_enumerated_value_symtable.find_value(symbol->value);
       
   255     symbol_c *local_value_type  = local_enumerated_value_symtable.find_value(symbol->value);
   244     symbol_c *local_value_type  = local_enumerated_value_symtable.find_value(symbol->value);
   256     if (local_value_type == local_enumerated_value_symtable.end_value())
   245     
   257       /* This identifier has not yet been used in any previous local declaration of an enumeration data type, so we add it to the local symbol table. */
   246     /* add it to the local symbol table. */
   258       local_enumerated_value_symtable.insert(symbol->value, current_enumerated_type);
   247     local_enumerated_value_symtable.insert(symbol->value, current_enumerated_type);
   259     else 
       
   260       /* This identifier has already been used in a previous declaration of an enumeration data type. so we set the symbol in symbol table pointing to NULL. */
       
   261       local_enumerated_value_symtable.set(symbol->value, NULL);
       
   262     return NULL;
   248     return NULL;
   263   }
   249   }
   264 }; // class populate_enumvalue_symtable_c
   250 }; // class populate_enumvalue_symtable_c
   265 
   251 
   266 static populate_enumvalue_symtable_c populate_enumvalue_symtable;
   252 static populate_enumvalue_symtable_c populate_enumvalue_symtable;
   526 	 * spurious error messages.
   512 	 * spurious error messages.
   527 	 * Even if the parameters to the function call are invalid, doing this is still safe, as the 
   513 	 * Even if the parameters to the function call are invalid, doing this is still safe, as the 
   528 	 * expressions inside the function call will themselves have erros and will  guarantee that 
   514 	 * expressions inside the function call will themselves have erros and will  guarantee that 
   529 	 * compilation is aborted in stage3 (in print_datatypes_error_c).
   515 	 * compilation is aborted in stage3 (in print_datatypes_error_c).
   530 	 */
   516 	 */
   531 	if (function_symtable.multiplicity(fcall_data.function_name) == 1) {
   517 	if (function_symtable.count(fcall_data.function_name) == 1) {
   532 		f_decl = function_symtable.get_value(lower);
   518 		f_decl = function_symtable.get_value(lower);
   533 		returned_parameter_type = base_type(f_decl->type_name);
   519 		returned_parameter_type = base_type(f_decl->type_name);
   534 		if (add_datatype_to_candidate_list(fcall, returned_parameter_type))
   520 		if (add_datatype_to_candidate_list(fcall, returned_parameter_type))
   535 			/* we only add it to the function declaration list if this entry was not already present in the candidate datatype list! */
   521 			/* we only add it to the function declaration list if this entry was not already present in the candidate datatype list! */
   536 			fcall_data.candidate_functions.push_back(f_decl);
   522 			fcall_data.candidate_functions.push_back(f_decl);
   918 	symbol_c *enumerated_type;
   904 	symbol_c *enumerated_type;
   919 
   905 
   920 	if (NULL != symbol->type)
   906 	if (NULL != symbol->type)
   921 		enumerated_type = symbol->type; /* TODO: check whether the value really belongs to that datatype!! */
   907 		enumerated_type = symbol->type; /* TODO: check whether the value really belongs to that datatype!! */
   922 	else {
   908 	else {
   923 		global_enumerated_type = global_enumerated_value_symtable.find_value(symbol->value);
   909 		symbol_c *global_enumerated_type = global_enumerated_value_symtable.find_value  (symbol->value);
   924 		local_enumerated_type  =  local_enumerated_value_symtable.find_value(symbol->value);
   910 		symbol_c * local_enumerated_type =  local_enumerated_value_symtable.find_value  (symbol->value);
   925 		if      (( local_enumerated_type ==  local_enumerated_value_symtable.end_value()) && (global_enumerated_type == global_enumerated_value_symtable.end_value()))
   911 		int       global_multiplicity    = global_enumerated_value_symtable.count(symbol->value);
       
   912 		int        local_multiplicity    =  local_enumerated_value_symtable.count(symbol->value);
       
   913 
       
   914 		if      (( local_multiplicity == 0) && (global_multiplicity == 0))
   926 		  enumerated_type = NULL; // not found!
   915 		  enumerated_type = NULL; // not found!
   927 		else if (( local_enumerated_type !=  local_enumerated_value_symtable.end_value()) && (local_enumerated_type == NULL))
   916 		else if (  local_multiplicity  > 1)
   928 			enumerated_type = NULL; // Duplicate, so it is ambiguous!
   917 			enumerated_type = NULL; // Local duplicate, so it is ambiguous!
   929 		else if (( local_enumerated_type !=  local_enumerated_value_symtable.end_value()))
   918 		else if (  local_multiplicity == 1)
   930 			enumerated_type = local_enumerated_type;
   919 			enumerated_type = local_enumerated_type;
   931 		else if ((global_enumerated_type != global_enumerated_value_symtable.end_value()) && (global_enumerated_type == NULL))
   920 		else if ( global_multiplicity  > 1)
   932 			enumerated_type = NULL; // Duplicate, so it is ambiguous!
   921 			enumerated_type = NULL; // Global duplicate, so it is ambiguous!
   933 		else if ((global_enumerated_type != global_enumerated_value_symtable.end_value()))
   922 		else if ( global_multiplicity == 1)
   934 			enumerated_type = global_enumerated_type;
   923 			enumerated_type = global_enumerated_type;
   935 		else ERROR;
   924 		else ERROR;
   936 	}
   925 	}
   937 	enumerated_type = base_type(enumerated_type);
   926 	enumerated_type = base_type(enumerated_type);
   938 	if (NULL != enumerated_type)
   927 	if (NULL != enumerated_type)