stage3/fill_candidate_datatypes.cc
changeset 449 3c6225521059
parent 448 1bd18fc06911
child 450 eb1b28acec2e
equal deleted inserted replaced
448:1bd18fc06911 449:3c6225521059
    71  * All parameters being passed to the called function MUST be in the parameter list to which f_call points to!
    71  * All parameters being passed to the called function MUST be in the parameter list to which f_call points to!
    72  * This means that, for non formal function calls in IL, de current (default value) must be artificially added to the
    72  * This means that, for non formal function calls in IL, de current (default value) must be artificially added to the
    73  * beginning of the parameter list BEFORE calling handle_function_call().
    73  * beginning of the parameter list BEFORE calling handle_function_call().
    74  */
    74  */
    75 bool fill_candidate_datatypes_c::match_nonformal_call(symbol_c *f_call, symbol_c *f_decl) {
    75 bool fill_candidate_datatypes_c::match_nonformal_call(symbol_c *f_call, symbol_c *f_decl) {
    76 	symbol_c *call_param_value,  *param_type;
    76 	symbol_c *call_param_value,  *param_datatype;
    77 	identifier_c *param_name;
    77 	identifier_c *param_name;
    78 	function_param_iterator_c       fp_iterator(f_decl);
    78 	function_param_iterator_c       fp_iterator(f_decl);
    79 	function_call_param_iterator_c fcp_iterator(f_call);
    79 	function_call_param_iterator_c fcp_iterator(f_call);
    80 	int extensible_parameter_highest_index = -1;
    80 	int extensible_parameter_highest_index = -1;
    81 	unsigned int i;
    81 	unsigned int i;
    90 			/* If there is no other parameter declared, then we are passing too many parameters... */
    90 			/* If there is no other parameter declared, then we are passing too many parameters... */
    91 			if(param_name == NULL) return false;
    91 			if(param_name == NULL) return false;
    92 		} while ((strcmp(param_name->value, "EN") == 0) || (strcmp(param_name->value, "ENO") == 0));
    92 		} while ((strcmp(param_name->value, "EN") == 0) || (strcmp(param_name->value, "ENO") == 0));
    93 
    93 
    94 		/* Get the parameter type */
    94 		/* Get the parameter type */
    95 		param_type = base_type(fp_iterator.param_type());
    95 		param_datatype = base_type(fp_iterator.param_type());
    96 		
    96 		
    97 		/* check whether one of the candidate_data_types of the value being passed is the same as the param_type */
    97 		/* check whether one of the candidate_data_types of the value being passed is the same as the param_type */
    98 		if (search_in_candidate_datatype_list(param_type, call_param_value->candidate_datatypes) < 0)
    98 		if (search_in_candidate_datatype_list(param_datatype, call_param_value->candidate_datatypes) < 0)
    99 			return false; /* return false if param_type not in the list! */
    99 			return false; /* return false if param_type not in the list! */
   100 	}
   100 	}
   101 	/* call is compatible! */
   101 	/* call is compatible! */
   102 	return true;
   102 	return true;
   103 }
   103 }
   105 
   105 
   106 
   106 
   107 /* returns true if compatible function/FB invocation, otherwise returns false */
   107 /* returns true if compatible function/FB invocation, otherwise returns false */
   108 /* Assumes that the candidate_datatype lists of all the parameters being passed haved already been filled in */
   108 /* Assumes that the candidate_datatype lists of all the parameters being passed haved already been filled in */
   109 bool fill_candidate_datatypes_c::match_formal_call(symbol_c *f_call, symbol_c *f_decl) {
   109 bool fill_candidate_datatypes_c::match_formal_call(symbol_c *f_call, symbol_c *f_decl) {
   110 	symbol_c *call_param_value, *call_param_name, *param_type;
   110 	symbol_c *call_param_value, *call_param_name, *param_datatype;
   111 	symbol_c *verify_duplicate_param;
   111 	symbol_c *verify_duplicate_param;
   112 	identifier_c *param_name;
   112 	identifier_c *param_name;
   113 	function_param_iterator_c       fp_iterator(f_decl);
   113 	function_param_iterator_c       fp_iterator(f_decl);
   114 	function_call_param_iterator_c fcp_iterator(f_call);
   114 	function_call_param_iterator_c fcp_iterator(f_call);
   115 	int extensible_parameter_highest_index = -1;
   115 	int extensible_parameter_highest_index = -1;
   116 	identifier_c *extensible_parameter_name;
   116 	identifier_c *extensible_parameter_name;
   117 	unsigned int i;
   117 	unsigned int i;
   118 
   118 
   119 	/* Iterating through the formal parameters of the function call */
   119 	/* Iterating through the formal parameters of the function call */
   120 	while((call_param_name = fcp_iterator.next_f()) != NULL) {
   120 	while((call_param_name = fcp_iterator.next_f()) != NULL) {
   121 /* TODO: check whether direction (IN, OUT, IN_OUT) and assignment types (:= , =>) are compatible !!! */
       
   122 		/* Obtaining the value being passed in the function call */
   121 		/* Obtaining the value being passed in the function call */
   123 		call_param_value = fcp_iterator.get_current_value();
   122 		call_param_value = fcp_iterator.get_current_value();
   124 		/* the following should never occur. If it does, then we have a bug in our code... */
   123 		/* the following should never occur. If it does, then we have a bug in our code... */
   125 		if (NULL == call_param_value) ERROR;
   124 		if (NULL == call_param_value) ERROR;
   126 
   125 
       
   126 		/* Obtaining the assignment direction:  := (assign_in) or => (assign_out) */
       
   127 		function_call_param_iterator_c::assign_direction_t call_param_dir = fcp_iterator.get_assign_direction();
       
   128 
   127 		/* Checking if there are duplicated parameter values */
   129 		/* Checking if there are duplicated parameter values */
   128 		verify_duplicate_param = fcp_iterator.search_f(call_param_name);
   130 		verify_duplicate_param = fcp_iterator.search_f(call_param_name);
   129 		if(verify_duplicate_param != call_param_value)
   131 		if(verify_duplicate_param != call_param_value)
   130 			return false;
   132 			return false;
   131 
   133 
   133 		std::vector <symbol_c *>&call_param_types = call_param_value->candidate_datatypes;
   135 		std::vector <symbol_c *>&call_param_types = call_param_value->candidate_datatypes;
   134 
   136 
   135 		/* Find the corresponding parameter in function declaration */
   137 		/* Find the corresponding parameter in function declaration */
   136 		param_name = fp_iterator.search(call_param_name);
   138 		param_name = fp_iterator.search(call_param_name);
   137 		if(param_name == NULL) return false;
   139 		if(param_name == NULL) return false;
   138 		/* Get the parameter type */
   140 		/* Get the parameter data type */
   139 		param_type = base_type(fp_iterator.param_type());
   141 		param_datatype = base_type(fp_iterator.param_type());
       
   142 		/* Get the parameter direction: IN, OUT, IN_OUT */
       
   143 		function_param_iterator_c::param_direction_t param_dir = fp_iterator.param_direction();
       
   144 
       
   145 		/* check whether direction (IN, OUT, IN_OUT) and assignment types (:= , =>) are compatible !!! */
       
   146 		if          (function_call_param_iterator_c::assign_in  == call_param_dir) {
       
   147 			if ((function_param_iterator_c::direction_in    != param_dir) &&
       
   148 			    (function_param_iterator_c::direction_inout != param_dir))
       
   149 				return false;
       
   150 		} else if   (function_call_param_iterator_c::assign_out == call_param_dir) {
       
   151 			if ((function_param_iterator_c::direction_out   != param_dir))
       
   152 				return false;
       
   153 		} else ERROR;
       
   154 		
   140 		/* check whether one of the candidate_data_types of the value being passed is the same as the param_type */
   155 		/* check whether one of the candidate_data_types of the value being passed is the same as the param_type */
   141 		if (search_in_candidate_datatype_list(param_type, call_param_types) < 0)
   156 		if (search_in_candidate_datatype_list(param_datatype, call_param_types) < 0)
   142 			return false; /* return false if param_type not in the list! */
   157 			return false; /* return false if param_type not in the list! */
   143 	}
   158 	}
   144 	/* call is compatible! */
   159 	/* call is compatible! */
   145 	return true;
   160 	return true;
   146 }
   161 }