stage3/narrow_candidate_datatypes.cc
changeset 870 9c6c588fd708
parent 854 13d0b67de111
child 873 dea39ef02847
equal deleted inserted replaced
822:a7d9e0b8636b 870:9c6c588fd708
   320  */
   320  */
   321 void *narrow_candidate_datatypes_c::narrow_implicit_il_fb_call(symbol_c *il_instruction, const char *param_name, symbol_c *&called_fb_declaration) {
   321 void *narrow_candidate_datatypes_c::narrow_implicit_il_fb_call(symbol_c *il_instruction, const char *param_name, symbol_c *&called_fb_declaration) {
   322 
   322 
   323 	/* set the datatype of the il_operand, this is, the FB being called! */
   323 	/* set the datatype of the il_operand, this is, the FB being called! */
   324 	if (NULL != il_operand) {
   324 	if (NULL != il_operand) {
   325 		/* only set it if it is in the candidate datatypes list! */  
   325 		set_datatype(called_fb_declaration, il_operand); /* only set it if it is in the candidate datatypes list! */  
   326 		set_datatype(called_fb_declaration, il_operand);
       
   327 		il_operand->accept(*this);
   326 		il_operand->accept(*this);
   328 	}
   327 	}
   329 	symbol_c *fb_decl = il_operand->datatype;
       
   330 
   328 
   331 	if (0 == fake_prev_il_instruction->prev_il_instruction.size()) {
   329 	if (0 == fake_prev_il_instruction->prev_il_instruction.size()) {
   332 		/* This IL implicit FB call (e.g. CLK ton_var) is not preceded by another IL instruction
   330 		/* This IL implicit FB call (e.g. CLK ton_var) is not preceded by another IL instruction
   333 		 * (or list of instructions) that will set the IL current/default value.
   331 		 * (or list of instructions) that will set the IL current/default value.
   334 		 * We cannot proceed verifying type compatibility of something that does not exist.
   332 		 * We cannot proceed verifying type compatibility of something that does not exist.
   335 		 */
   333 		 */
   336 		return NULL;
   334 		return NULL;
   337 	}
   335 	}
   338 
   336 
       
   337 	symbol_c *fb_decl = (NULL == il_operand)? NULL : il_operand->datatype;
       
   338 	
   339 	if (NULL == fb_decl) {
   339 	if (NULL == fb_decl) {
   340 		/* the il_operand is a not FB instance */
   340 		/* the il_operand is a not FB instance, or it simply does not even exist, */
   341 		/* so we simply pass on the required datatype to the prev_il_instructions */
   341 		/* so we simply pass on the required datatype to the prev_il_instructions */
   342 		/* The invalid FB invocation will be caught in the print_datatypes_error_c by analysing NULL value in il_operand->datatype! */
   342 		/* The invalid FB invocation will be caught in the print_datatypes_error_c by analysing NULL value in il_operand->datatype! */
   343 		set_datatype_in_prev_il_instructions(il_instruction->datatype, fake_prev_il_instruction);
   343 		set_datatype_in_prev_il_instructions(il_instruction->datatype, fake_prev_il_instruction);
   344 		return NULL;
   344 		return NULL;
   345 	}
   345 	}
   647 
   647 
   648 
   648 
   649 /*********************/
   649 /*********************/
   650 /* B 1.4 - Variables */
   650 /* B 1.4 - Variables */
   651 /*********************/
   651 /*********************/
   652 
   652 // SYM_REF1(symbolic_variable_c, var_name)
       
   653 void *narrow_candidate_datatypes_c::visit(symbolic_variable_c *symbol) {
       
   654 	symbol->var_name->datatype = symbol->datatype;
       
   655 	return NULL;
       
   656 }
   653 /********************************************/
   657 /********************************************/
   654 /* B 1.4.1 - Directly Represented Variables */
   658 /* B 1.4.1 - Directly Represented Variables */
   655 /********************************************/
   659 /********************************************/
   656 
   660 
   657 /*************************************/
   661 /*************************************/
   660 /*  subscripted_variable '[' subscript_list ']' */
   664 /*  subscripted_variable '[' subscript_list ']' */
   661 // SYM_REF2(array_variable_c, subscripted_variable, subscript_list)
   665 // SYM_REF2(array_variable_c, subscripted_variable, subscript_list)
   662 void *narrow_candidate_datatypes_c::visit(array_variable_c *symbol) {
   666 void *narrow_candidate_datatypes_c::visit(array_variable_c *symbol) {
   663 	/* we need to check the data types of the expressions used for the subscripts... */
   667 	/* we need to check the data types of the expressions used for the subscripts... */
   664 	symbol->subscript_list->accept(*this);
   668 	symbol->subscript_list->accept(*this);
       
   669 
       
   670 	/* Set the datatype of the subscripted variable and visit it recursively. For the reason why we do this,                                                 */
       
   671 	/* Please read the comments in the array_variable_c and structured_variable_c visitors in the fill_candidate_datatypes.cc file! */
       
   672 	symbol->subscripted_variable->accept(*this); // visit recursively
       
   673 
       
   674 	if (symbol->subscripted_variable->candidate_datatypes.size() == 1)
       
   675 	  symbol->subscripted_variable->datatype = symbol->subscripted_variable->candidate_datatypes[0]; // set the datatype
       
   676 
   665 	return NULL;
   677 	return NULL;
   666 }
   678 }
   667 
   679 
   668 
   680 
   669 /* subscript_list ',' subscript */
   681 /* subscript_list ',' subscript */
   678 	}
   690 	}
   679 	return NULL;  
   691 	return NULL;  
   680 }
   692 }
   681 
   693 
   682 
   694 
       
   695 
       
   696 /*  record_variable '.' field_selector */
       
   697 /*  WARNING: input and/or output variables of function blocks
       
   698  *           may be accessed as fields of a structured variable!
       
   699  *           Code handling a structured_variable_c must take
       
   700  *           this into account!
       
   701  */
       
   702 // SYM_REF2(structured_variable_c, record_variable, field_selector)
       
   703 void *narrow_candidate_datatypes_c::visit(structured_variable_c *symbol) {
       
   704 	/* Set the datatype of the record_variable and visit it recursively. For the reason why we do this,                                                      */
       
   705 	/* Please read the comments in the array_variable_c and structured_variable_c visitors in the fill_candidate_datatypes.cc file! */
       
   706 	symbol->record_variable->accept(*this); // visit recursively
       
   707 
       
   708 	if (symbol->record_variable->candidate_datatypes.size() == 1)
       
   709 	  symbol->record_variable->datatype = symbol->record_variable->candidate_datatypes[0]; // set the datatype
       
   710 
       
   711 	return NULL;
       
   712 }
   683 
   713 
   684 
   714 
   685 /******************************************/
   715 /******************************************/
   686 /* B 1.4.3 - Declaration & Initialisation */
   716 /* B 1.4.3 - Declaration & Initialisation */
   687 /******************************************/
   717 /******************************************/
   971  * | il_call_operator prev_declared_fb_name '(' ')'
  1001  * | il_call_operator prev_declared_fb_name '(' ')'
   972  * | il_call_operator prev_declared_fb_name '(' eol_list ')'
  1002  * | il_call_operator prev_declared_fb_name '(' eol_list ')'
   973  * | il_call_operator prev_declared_fb_name '(' il_operand_list ')'
  1003  * | il_call_operator prev_declared_fb_name '(' il_operand_list ')'
   974  * | il_call_operator prev_declared_fb_name '(' eol_list il_param_list ')'
  1004  * | il_call_operator prev_declared_fb_name '(' eol_list il_param_list ')'
   975  */
  1005  */
   976 /* NOTE: The parameter 'called_fb_declaration'is used to pass data between stage 3 and stage4 (although currently it is not used in stage 4 */
  1006 /* NOTE: The parameter 'called_fb_declaration'is used to pass data between stage 3 and stage4 */
   977 // SYM_REF4(il_fb_call_c, il_call_operator, fb_name, il_operand_list, il_param_list, symbol_c *called_fb_declaration)
  1007 // SYM_REF4(il_fb_call_c, il_call_operator, fb_name, il_operand_list, il_param_list, symbol_c *called_fb_declaration)
   978 void *narrow_candidate_datatypes_c::visit(il_fb_call_c *symbol) {
  1008 void *narrow_candidate_datatypes_c::visit(il_fb_call_c *symbol) {
   979 	symbol_c *fb_decl = symbol->called_fb_declaration;
  1009 	symbol_c *fb_decl = symbol->called_fb_declaration;
   980 	
  1010 	
   981 	/* Although a call to a non-declared FB is a semantic error, this is currently caught by stage 2! */
  1011 	/* Although a call to a non-declared FB is a semantic error, this is currently caught by stage 2! */
  1054 
  1084 
  1055 
  1085 
  1056 /*******************/
  1086 /*******************/
  1057 /* B 2.2 Operators */
  1087 /* B 2.2 Operators */
  1058 /*******************/
  1088 /*******************/
       
  1089 /* Sets the datatype of the il_operand, and calls it recursively!
       
  1090  * 
       
  1091  * NOTE 1: the il_operand __may__ be pointing to a parenthesized list of IL instructions. 
       
  1092  * e.g.  LD 33
       
  1093  *       AND ( 45
       
  1094  *            OR 56
       
  1095  *            )
       
  1096  *       When we handle the first 'AND' IL_operator, the il_operand will point to an simple_instr_list_c.
       
  1097  *       In this case, when we call il_operand->accept(*this);, the prev_il_instruction pointer will be overwritten!
       
  1098  *
       
  1099  *       So, if yoy wish to set the prev_il_instruction->datatype = symbol->datatype;
       
  1100  *       do it __before__ calling set_il_operand_datatype() (which in turn calls il_operand->accept(*this)) !!
       
  1101  */
       
  1102 void *narrow_candidate_datatypes_c::set_il_operand_datatype(symbol_c *il_operand, symbol_c *datatype) {
       
  1103 	if (NULL == il_operand) return NULL; /* if no IL operand => error in the source code!! */
       
  1104 
       
  1105 	/* If il_operand already has a non-NULL datatype (remember, narrow algorithm runs twice over IL lists!),
       
  1106 	 * but narrow algorithm has not yet been able to determine what datatype it should take? This is strange,
       
  1107 	 * and most probably an error!
       
  1108 	 */
       
  1109 	if ((NULL != il_operand->datatype) && (NULL == datatype)) ERROR;
       
  1110 
       
  1111 	/* If the il_operand's datatype has already been set previously, and
       
  1112 	 * the narrow algorithm has already determined the datatype the il_operand should take!
       
  1113 	 *   ...we just make sure that the new datatype is the same as the current il_operand's datatype
       
  1114 	 */
       
  1115 	if ((NULL != il_operand->datatype)  && (NULL != datatype)) {
       
  1116 		/* Both datatypes are an invalid_type_name_c. This implies they are the same!! */
       
  1117 		if ((!get_datatype_info_c::is_type_valid(datatype)) && ((!get_datatype_info_c::is_type_valid(il_operand->datatype)))) 
       
  1118 			return NULL;;
       
  1119 		/* OK, so both the datatypes are valid, but are they equal? */
       
  1120 		if ( !get_datatype_info_c::is_type_equal(il_operand->datatype, datatype)) 
       
  1121 			ERROR; 
       
  1122 		/* The datatypes are the same. We have nothing to do, so we simply return! */
       
  1123 		return NULL;
       
  1124 	}
       
  1125 
       
  1126 	/* Set the il_operand's datatype. Note that the new 'datatype' may even be NULL!!! */
       
  1127 	il_operand->datatype = datatype;
       
  1128 	/* Even if we are not able to determine the il_operand's datatype ('datatype' is NULL), we still visit it recursively,
       
  1129 	 * to give a chance of any complex expressions embedded in the il_operand (e.g. expressions inside array subscripts!) 
       
  1130 	 * to be narrowed too.
       
  1131 	 */
       
  1132 	il_operand->accept(*this);
       
  1133 	return NULL;
       
  1134 }
       
  1135 
       
  1136 
       
  1137 
       
  1138 
  1059 void *narrow_candidate_datatypes_c::narrow_binary_operator(const struct widen_entry widen_table[], symbol_c *symbol, bool *deprecated_operation) {
  1139 void *narrow_candidate_datatypes_c::narrow_binary_operator(const struct widen_entry widen_table[], symbol_c *symbol, bool *deprecated_operation) {
  1060 	symbol_c *prev_instruction_type, *operand_type;
  1140 	symbol_c *prev_instruction_type, *operand_type;
  1061 	int count = 0;
  1141 	int count = 0;
  1062 
  1142 
  1063 	if (NULL == symbol->datatype)
       
  1064 		/* next IL instructions were unable to determine the datatype this instruction should produce */
       
  1065 		return NULL;
       
  1066 
       
  1067         if (NULL != deprecated_operation)
  1143         if (NULL != deprecated_operation)
  1068 		*deprecated_operation = false;
  1144 		*deprecated_operation = false;
  1069 
  1145 
  1070 	/* NOTE 1: the il_operand __may__ be pointing to a parenthesized list of IL instructions. 
  1146 	if (NULL == il_operand) return NULL; /* if no IL operand => error in the source code!! */
       
  1147 
       
  1148 	 /* NOTE 1: the il_operand __may__ be pointing to a parenthesized list of IL instructions. 
  1071 	 * e.g.  LD 33
  1149 	 * e.g.  LD 33
  1072 	 *       AND ( 45
  1150 	 *       AND ( 45
  1073 	 *            OR 56
  1151 	 *            OR 56
  1074 	 *            )
  1152 	 *            )
  1075 	 *       When we handle the first 'AND' IL_operator, the il_operand will point to an simple_instr_list_c.
  1153 	 *       When we handle the first 'AND' IL_operator, the il_operand will point to an simple_instr_list_c.
  1080 	 *
  1158 	 *
  1081 	 * NOTE 2: We do not need to call prev_il_instruction->accept(*this), as the object to which prev_il_instruction
  1159 	 * NOTE 2: We do not need to call prev_il_instruction->accept(*this), as the object to which prev_il_instruction
  1082 	 *         is pointing to will be later narrowed by the call from the for() loop of the instruction_list_c
  1160 	 *         is pointing to will be later narrowed by the call from the for() loop of the instruction_list_c
  1083 	 *         (or simple_instr_list_c), which iterates backwards.
  1161 	 *         (or simple_instr_list_c), which iterates backwards.
  1084 	 */
  1162 	 */
  1085 	for(unsigned int i = 0; i < fake_prev_il_instruction->candidate_datatypes.size(); i++) {
  1163 	if (NULL != symbol->datatype) { // next IL instructions were able to determine the datatype this instruction should produce
  1086 		for(unsigned int j = 0; j < il_operand->candidate_datatypes.size(); j++) {
  1164 		for(unsigned int i = 0; i < fake_prev_il_instruction->candidate_datatypes.size(); i++) {
  1087 			prev_instruction_type = fake_prev_il_instruction->candidate_datatypes[i];
  1165 			for(unsigned int j = 0; j < il_operand->candidate_datatypes.size(); j++) {
  1088 			operand_type = il_operand->candidate_datatypes[j];
  1166 				prev_instruction_type = fake_prev_il_instruction->candidate_datatypes[i];
  1089 			if (is_widening_compatible(widen_table, prev_instruction_type, operand_type, symbol->datatype, deprecated_operation)) {
  1167 				operand_type = il_operand->candidate_datatypes[j];
  1090 				/* set the desired datatype of the previous il instruction */
  1168 				if (is_widening_compatible(widen_table, prev_instruction_type, operand_type, symbol->datatype, deprecated_operation)) {
  1091 				set_datatype_in_prev_il_instructions(prev_instruction_type, fake_prev_il_instruction);
  1169 					/* set the desired datatype of the previous il instruction */
  1092 				/* set the datatype for the operand */
  1170 					set_datatype_in_prev_il_instructions(prev_instruction_type, fake_prev_il_instruction);
  1093 				il_operand->datatype = operand_type;
  1171 					/* set the datatype for the operand */
  1094 				il_operand->accept(*this);
  1172 					set_il_operand_datatype(il_operand, operand_type);
  1095 				
  1173 					
  1096 				/* NOTE: DO NOT search any further! Return immediately!
  1174 					/* NOTE: DO NOT search any further! Return immediately!
  1097 				 * Since we support SAFE*** datatypes, multiple entries in the widen_table may be compatible.
  1175 					 * Since we support SAFE*** datatypes, multiple entries in the widen_table may be compatible.
  1098 				 * If we try to set more than one distinct datatype on the same symbol, then the datatype will be set to
  1176 					 * If we try to set more than one distinct datatype on the same symbol, then the datatype will be set to
  1099 				 * an invalid_datatype, which is NOT what we want!
  1177 					 * an invalid_datatype, which is NOT what we want!
  1100 				 */
  1178 					 */
  1101 				return NULL;
  1179 					return NULL;
       
  1180 				}
  1102 			}
  1181 			}
  1103 		}
  1182 		}
  1104 	}
  1183 	}
  1105 	return NULL;
  1184 	/* We were not able to determine the required datatype, but we still give the il_operand a chance to be narrowed! */
  1106 }
  1185 	set_il_operand_datatype(il_operand, NULL);
  1107 
  1186 	return NULL;
  1108 
  1187 }
  1109 
  1188 
  1110 
  1189 
  1111 
  1190 
  1112 void *narrow_candidate_datatypes_c::handle_il_instruction(symbol_c *symbol) {
  1191 
  1113 	if (NULL == symbol->datatype)
  1192 /* Narrow IL operators whose execution is conditional on the boolean value in the accumulator.
  1114 		/* next IL instructions were unable to determine the datatype this instruction should produce */
  1193  * Basically, narrow the JMPC, JMPCN, RETC, RETCN, CALC, and CALCN operators!
  1115 		return NULL;
  1194  * Also does part of the S and R operator narrowing!!!
  1116 	/* NOTE 1: the il_operand __may__ be pointing to a parenthesized list of IL instructions. 
  1195  */
  1117 	 * e.g.  LD 33
  1196 void *narrow_candidate_datatypes_c::narrow_conditional_operator(symbol_c *symbol) {
  1118 	 *       AND ( 45
  1197 	/* if the next IL instructions needs us to provide a datatype other than a BOOL or a SAFEBOOL, 
  1119 	 *            OR 56
  1198 	 * then we have an internal compiler error - most likely in fill_candidate_datatypes_c 
  1120 	 *            )
  1199 	 */
  1121 	 *       When we handle the first 'AND' IL_operator, the il_operand will point to an simple_instr_list_c.
  1200 	// I (mario) am confident the fill/narrow algorithms are working correctly, so for now we can disable the assertions!
  1122 	 *       In this case, when we call il_operand->accept(*this);, the prev_il_instruction pointer will be overwritten!
  1201 	//if ((NULL != symbol->datatype) && (!get_datatype_info_c::is_BOOL_compatible(symbol->datatype))) ERROR;
  1123 	 *
  1202 	//if (symbol->candidate_datatypes.size() > 2) ERROR; /* may contain, at most, a BOOL and a SAFEBOOL */
  1124 	 *       We must therefore set the prev_il_instruction->datatype = symbol->datatype;
  1203 
  1125 	 *       __before__ calling il_operand->accept(*this) !!
  1204 	/* NOTE: If there is no IL instruction following this S, R, CALC, CALCN, JMPC, JMPCN, RETC, or RETCN instruction,
  1126 	 *
  1205 	 *       we must still provide a bool_type_name_c datatype (if possible, i.e. if it exists in the candidate datatype list).
  1127 	 * NOTE 2: We do not need to call prev_il_instruction->accept(*this), as the object to which prev_il_instruction
  1206 	 *       If it is not possible, we set it to NULL
  1128 	 *         is pointing to will be later narrowed by the call from the for() loop of the instruction_list_c
  1207 	 * 
  1129 	 *         (or simple_instr_list_c), which iterates backwards.
  1208 	 * NOTE: Note that this algorithm we are implementing is slightly wrong. 
  1130 	 */
  1209 	 *        (a) It ignores that a SAFEBOOL may be needed instead of a BOOL datatype. 
  1131 	/* set the desired datatype of the previous il instruction */
  1210 	 *        (b) It also ignores that this method gets to be called twice on the same 
       
  1211 	 *            object (the narrow algorithm runs through the IL list twice in order to
       
  1212 	 *            handle forward JMPs), so the assumption that we must immediately set our
       
  1213 	 *            own datatype if we get called with a NULL symbol->datatype is incorrect 
       
  1214 	 *           (it may be that the second time it is called it will be with the correct datatype!).
       
  1215 	 * 
       
  1216 	 *       These two issues (a) and (b) together means that we should only really be setting our own
       
  1217 	 *       datatype if we are certain that the following IL instructions will never set it for us
       
  1218 	 *       - basically if the following IL instruction is a LD, or a JMP to a LD, or a JMP to a JMP to a LD,
       
  1219 	 *        etc..., or a conditional JMP whose both branches go to LD, etc...!!!
       
  1220 	 *       
       
  1221 	 *       At the moment, it seems to me that we would need to write a visitor class to do this for us!
       
  1222 	 *       I currently have other things on my mind at the moment, so I will leave this for later...
       
  1223 	 *       For the moment we just set it to BOOL, and ignore the support of SAFEBOOL!
       
  1224 	 */
       
  1225 	if (NULL == symbol->datatype) set_datatype(&get_datatype_info_c::bool_type_name /* datatype*/, symbol /* symbol */);
       
  1226 	if (NULL == symbol->datatype) ERROR; // the BOOL is not on the candidate_datatypes! Strange... Probably a bug in fill_candidate_datatype_c
       
  1227 
       
  1228 	/* set the required datatype of the previous IL instruction, i.e. a bool_type_name_c! */
  1132 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
  1229 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
  1133 	  
  1230 	return NULL;
       
  1231 }
       
  1232 
       
  1233 
       
  1234 
       
  1235 void *narrow_candidate_datatypes_c::narrow_S_and_R_operator(symbol_c *symbol, const char *param_name, symbol_c *called_fb_declaration) {
       
  1236 	if (NULL != called_fb_declaration) 
       
  1237 	  /* FB call semantics */  
       
  1238 	  return narrow_implicit_il_fb_call(symbol, param_name, called_fb_declaration); 
       
  1239 	
       
  1240 	/* Set/Reset semantics */  
       
  1241 	narrow_conditional_operator(symbol);
       
  1242 	/* set the datatype for the il_operand */
       
  1243 	if ((NULL != il_operand) && (il_operand->candidate_datatypes.size() > 0))
       
  1244 		set_il_operand_datatype(il_operand, il_operand->candidate_datatypes[0]);
       
  1245 	return NULL;
       
  1246 }
       
  1247 
       
  1248 
       
  1249 
       
  1250 void *narrow_candidate_datatypes_c::narrow_store_operator(symbol_c *symbol) {
       
  1251 	if (symbol->candidate_datatypes.size() == 1) {
       
  1252 		symbol->datatype = symbol->candidate_datatypes[0];
       
  1253 		/* set the desired datatype of the previous il instruction */
       
  1254 		set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
       
  1255 		/* In the case of the ST operator, we must set the datatype of the il_instruction_c object that points to this ST_operator_c ourselves,
       
  1256 		 * since the following il_instruction_c objects have not done it, as is normal/standard for other instructions!
       
  1257 		 */
       
  1258 		current_il_instruction->datatype = symbol->datatype;
       
  1259 	}
       
  1260 	
  1134 	/* set the datatype for the operand */
  1261 	/* set the datatype for the operand */
  1135 	il_operand->datatype = symbol->datatype;
  1262 	set_il_operand_datatype(il_operand, symbol->datatype);
  1136 	il_operand->accept(*this);
  1263 	return NULL;
  1137 	return NULL;
  1264 }
  1138 }
  1265 
  1139 
  1266 
  1140 
  1267 
  1141 
  1268 void *narrow_candidate_datatypes_c::visit(  LD_operator_c *symbol)  {return set_il_operand_datatype(il_operand, symbol->datatype);}
  1142 
  1269 void *narrow_candidate_datatypes_c::visit( LDN_operator_c *symbol)  {return set_il_operand_datatype(il_operand, symbol->datatype);}
  1143 void *narrow_candidate_datatypes_c::visit(LD_operator_c *symbol)   {
  1270 
  1144 	if (NULL == symbol->datatype)
  1271 void *narrow_candidate_datatypes_c::visit(  ST_operator_c *symbol)  {return narrow_store_operator(symbol);}
  1145 		/* next IL instructions were unable to determine the datatype this instruction should produce */
  1272 void *narrow_candidate_datatypes_c::visit( STN_operator_c *symbol)  {return narrow_store_operator(symbol);}
  1146 		return NULL;
  1273 
  1147 	/* set the datatype for the operand */
  1274 
  1148 	il_operand->datatype = symbol->datatype;
  1275 /* NOTE: the standard allows syntax in which the NOT operator is followed by an optional <il_operand>
  1149 	il_operand->accept(*this);
  1276  *              NOT [<il_operand>]
  1150 	return NULL;
  1277  *       However, it does not define the semantic of the NOT operation when the <il_operand> is specified.
  1151 }
  1278  *       We therefore consider it an error if an il_operand is specified!
  1152 
  1279  *       This error will be detected in print_datatypes_error_c!!
  1153 
  1280  */
  1154 void *narrow_candidate_datatypes_c::visit(LDN_operator_c *symbol)  {
  1281 /* This operator does not change the data type, it simply inverts the bits in the ANT_BIT data types! */
  1155 	if (NULL == symbol->datatype)
  1282 /* So, we merely set the desired datatype of the previous il instruction */
  1156 		/* next IL instructions were unable to determine the datatype this instruction should produce */
  1283 void *narrow_candidate_datatypes_c::visit( NOT_operator_c *symbol)  {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);return NULL;}
  1157 		return NULL;
  1284 
  1158 	/* set the datatype for the operand */
  1285 void *narrow_candidate_datatypes_c::visit(   S_operator_c *symbol)  {return narrow_S_and_R_operator   (symbol, "S",   symbol->called_fb_declaration);}
  1159 	il_operand->datatype = symbol->datatype;
  1286 void *narrow_candidate_datatypes_c::visit(   R_operator_c *symbol)  {return narrow_S_and_R_operator   (symbol, "R",   symbol->called_fb_declaration);}
  1160 	il_operand->accept(*this);
       
  1161 	return NULL;
       
  1162 }
       
  1163 
       
  1164 void *narrow_candidate_datatypes_c::visit(ST_operator_c *symbol) {
       
  1165 	if (symbol->candidate_datatypes.size() != 1)
       
  1166 		return NULL;
       
  1167 	symbol->datatype = symbol->candidate_datatypes[0];
       
  1168 	/* set the datatype for the operand */
       
  1169 	il_operand->datatype = symbol->datatype;
       
  1170 	il_operand->accept(*this);
       
  1171 	/* set the desired datatype of the previous il instruction */
       
  1172 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
       
  1173 	/* In the case of the ST operator, we must set the datatype of the il_instruction_c object that points to this ST_operator_c ourselves,
       
  1174 	 * since the following il_instruction_c objects have not done it, as is normal/standard for other instructions!
       
  1175 	 */
       
  1176 	current_il_instruction->datatype = symbol->datatype;
       
  1177 	return NULL;
       
  1178 }
       
  1179 
       
  1180 void *narrow_candidate_datatypes_c::visit(STN_operator_c *symbol) {
       
  1181 	if (symbol->candidate_datatypes.size() != 1)
       
  1182 		return NULL;
       
  1183 	symbol->datatype = symbol->candidate_datatypes[0];
       
  1184 	/* set the datatype for the operand */
       
  1185 	il_operand->datatype = symbol->datatype;
       
  1186 	il_operand->accept(*this);
       
  1187 	/* set the desired datatype of the previous il instruction */
       
  1188 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
       
  1189 	return NULL;
       
  1190 }
       
  1191 
       
  1192 void *narrow_candidate_datatypes_c::visit(NOT_operator_c *symbol) {
       
  1193 	/* NOTE: the standard allows syntax in which the NOT operator is followed by an optional <il_operand>
       
  1194 	 *              NOT [<il_operand>]
       
  1195 	 *       However, it does not define the semantic of the NOT operation when the <il_operand> is specified.
       
  1196 	 *       We therefore consider it an error if an il_operand is specified!
       
  1197 	 */
       
  1198 	/* We do not change the data type, we simply invert the bits in bit types! */
       
  1199 	/* So, we set the desired datatype of the previous il instruction */
       
  1200 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
       
  1201 	return NULL;
       
  1202 }
       
  1203 
       
  1204 void *narrow_candidate_datatypes_c::visit(S_operator_c *symbol)  {
       
  1205   /* TODO: what if this is a FB call? */
       
  1206 	return handle_il_instruction(symbol);
       
  1207 }
       
  1208 void *narrow_candidate_datatypes_c::visit(R_operator_c *symbol)  {
       
  1209   /* TODO: what if this is a FB call? */
       
  1210 	return handle_il_instruction(symbol);
       
  1211 }
       
  1212 
       
  1213 
  1287 
  1214 void *narrow_candidate_datatypes_c::visit(  S1_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "S1",  symbol->called_fb_declaration);}
  1288 void *narrow_candidate_datatypes_c::visit(  S1_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "S1",  symbol->called_fb_declaration);}
  1215 void *narrow_candidate_datatypes_c::visit(  R1_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "R1",  symbol->called_fb_declaration);}
  1289 void *narrow_candidate_datatypes_c::visit(  R1_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "R1",  symbol->called_fb_declaration);}
  1216 void *narrow_candidate_datatypes_c::visit( CLK_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "CLK", symbol->called_fb_declaration);}
  1290 void *narrow_candidate_datatypes_c::visit( CLK_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "CLK", symbol->called_fb_declaration);}
  1217 void *narrow_candidate_datatypes_c::visit(  CU_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "CU",  symbol->called_fb_declaration);}
  1291 void *narrow_candidate_datatypes_c::visit(  CU_operator_c *symbol)  {return narrow_implicit_il_fb_call(symbol, "CU",  symbol->called_fb_declaration);}
  1237 void *narrow_candidate_datatypes_c::visit(  LT_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1311 void *narrow_candidate_datatypes_c::visit(  LT_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1238 void *narrow_candidate_datatypes_c::visit(  LE_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1312 void *narrow_candidate_datatypes_c::visit(  LE_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1239 void *narrow_candidate_datatypes_c::visit(  NE_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1313 void *narrow_candidate_datatypes_c::visit(  NE_operator_c *symbol)  {return narrow_binary_operator(widen_CMP_table, symbol);}
  1240 
  1314 
  1241 
  1315 
  1242 
  1316 /* visitors to CAL_operator_c, CALC_operator_c and CALCN_operator_c are called from visit(il_fb_call_c *) {symbol->il_call_operator->accept(*this)} */
  1243 
       
  1244 void *narrow_candidate_datatypes_c::narrow_conditional_flow_control_IL_instruction(symbol_c *symbol) {
       
  1245 	/* if the next IL instructions needs us to provide a datatype other than a bool, 
       
  1246 	 * then we have an internal compiler error - most likely in fill_candidate_datatypes_c 
       
  1247 	 */
       
  1248 	if ((NULL != symbol->datatype) && (!get_datatype_info_c::is_BOOL_compatible(symbol->datatype))) ERROR;
       
  1249 	if (symbol->candidate_datatypes.size() > 1) ERROR;
       
  1250 
       
  1251 	/* NOTE: If there is no IL instruction following this CALC, CALCN, JMPC, JMPC, ..., instruction,
       
  1252 	 *       we must still provide a bool_type_name_c datatype (if possible, i.e. if it exists in the candidate datatype list).
       
  1253 	 *       If it is not possible, we set it to NULL
       
  1254 	 */
       
  1255 	if (symbol->candidate_datatypes.size() == 0)    symbol->datatype = NULL;
       
  1256 	else    symbol->datatype = symbol->candidate_datatypes[0]; /* i.e. a bool_type_name_c! */
       
  1257 	if ((NULL != symbol->datatype) && (!get_datatype_info_c::is_BOOL_compatible(symbol->datatype))) ERROR;
       
  1258 
       
  1259 	/* set the required datatype of the previous IL instruction, i.e. a bool_type_name_c! */
       
  1260 	set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction);
       
  1261 	return NULL;
       
  1262 }
       
  1263 
       
  1264 
       
  1265 // SYM_REF0(CAL_operator_c)
       
  1266 // SYM_REF0(CALC_operator_c)
       
  1267 // SYM_REF0(CALCN_operator_c)
       
  1268 /* called from visit(il_fb_call_c *) {symbol->il_call_operator->accpet(*this)} */
       
  1269 /* NOTE: The CAL, JMP and RET instructions simply set the desired datatype of the previous il instruction since they do not change the value in the current/default IL variable */
  1317 /* NOTE: The CAL, JMP and RET instructions simply set the desired datatype of the previous il instruction since they do not change the value in the current/default IL variable */
  1270 /* called from il_fb_call_c (symbol->il_call_operator->accpet(*this) ) */
       
  1271 void *narrow_candidate_datatypes_c::visit(  CAL_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1318 void *narrow_candidate_datatypes_c::visit(  CAL_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1272 void *narrow_candidate_datatypes_c::visit(  RET_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1319 void *narrow_candidate_datatypes_c::visit(  RET_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1273 void *narrow_candidate_datatypes_c::visit(  JMP_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1320 void *narrow_candidate_datatypes_c::visit(  JMP_operator_c *symbol) {set_datatype_in_prev_il_instructions(symbol->datatype, fake_prev_il_instruction); return NULL;}
  1274 void *narrow_candidate_datatypes_c::visit( CALC_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1321 void *narrow_candidate_datatypes_c::visit( CALC_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1275 void *narrow_candidate_datatypes_c::visit(CALCN_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1322 void *narrow_candidate_datatypes_c::visit(CALCN_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1276 void *narrow_candidate_datatypes_c::visit( RETC_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1323 void *narrow_candidate_datatypes_c::visit( RETC_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1277 void *narrow_candidate_datatypes_c::visit(RETCN_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1324 void *narrow_candidate_datatypes_c::visit(RETCN_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1278 void *narrow_candidate_datatypes_c::visit( JMPC_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1325 void *narrow_candidate_datatypes_c::visit( JMPC_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1279 void *narrow_candidate_datatypes_c::visit(JMPCN_operator_c *symbol) {return narrow_conditional_flow_control_IL_instruction(symbol);}
  1326 void *narrow_candidate_datatypes_c::visit(JMPCN_operator_c *symbol) {return narrow_conditional_operator(symbol);}
  1280 
  1327 
  1281 /* Symbol class handled together with function call checks */
  1328 /* Symbol class handled together with function call checks */
  1282 // void *visit(il_assign_operator_c *symbol, variable_name);
  1329 // void *visit(il_assign_operator_c *symbol, variable_name);
  1283 /* Symbol class handled together with function call checks */
  1330 /* Symbol class handled together with function call checks */
  1284 // void *visit(il_assign_operator_c *symbol, option, variable_name);
  1331 // void *visit(il_assign_operator_c *symbol, option, variable_name);
  1311 			r_type = r_expr->candidate_datatypes[j];
  1358 			r_type = r_expr->candidate_datatypes[j];
  1312 			if        (is_widening_compatible(widen_table, l_type, r_type, symbol->datatype, deprecated_operation)) {
  1359 			if        (is_widening_compatible(widen_table, l_type, r_type, symbol->datatype, deprecated_operation)) {
  1313 				l_expr->datatype = l_type;
  1360 				l_expr->datatype = l_type;
  1314 				r_expr->datatype = r_type;
  1361 				r_expr->datatype = r_type;
  1315 				count ++;
  1362 				count ++;
  1316 			} else if ((l_type == r_type) && search_base_type_c::type_is_enumerated(l_type) && get_datatype_info_c::is_BOOL_compatible(symbol->datatype)) {
  1363 			} else if ((l_type == r_type) && get_datatype_info_c::is_enumerated(l_type) && get_datatype_info_c::is_BOOL_compatible(symbol->datatype)) {
  1317 				if (NULL != deprecated_operation)  *deprecated_operation = false;
  1364 				if (NULL != deprecated_operation)  *deprecated_operation = false;
  1318 				l_expr->datatype = l_type;
  1365 				l_expr->datatype = l_type;
  1319 				r_expr->datatype = r_type;
  1366 				r_expr->datatype = r_type;
  1320 				count ++;
  1367 				count ++;
  1321 			}
  1368 			}
  1467 /* CASE expression OF case_element_list ELSE statement_list END_CASE */
  1514 /* CASE expression OF case_element_list ELSE statement_list END_CASE */
  1468 // SYM_REF3(case_statement_c, expression, case_element_list, statement_list)
  1515 // SYM_REF3(case_statement_c, expression, case_element_list, statement_list)
  1469 void *narrow_candidate_datatypes_c::visit(case_statement_c *symbol) {
  1516 void *narrow_candidate_datatypes_c::visit(case_statement_c *symbol) {
  1470 	for (unsigned int i = 0; i < symbol->expression->candidate_datatypes.size(); i++) {
  1517 	for (unsigned int i = 0; i < symbol->expression->candidate_datatypes.size(); i++) {
  1471 		if ((get_datatype_info_c::is_ANY_INT(symbol->expression->candidate_datatypes[i]))
  1518 		if ((get_datatype_info_c::is_ANY_INT(symbol->expression->candidate_datatypes[i]))
  1472 				 || (search_base_type_c::type_is_enumerated(symbol->expression->candidate_datatypes[i])))
  1519 				 || (get_datatype_info_c::is_enumerated(symbol->expression->candidate_datatypes[i])))
  1473 			symbol->expression->datatype = symbol->expression->candidate_datatypes[i];
  1520 			symbol->expression->datatype = symbol->expression->candidate_datatypes[i];
  1474 	}
  1521 	}
  1475 	symbol->expression->accept(*this);
  1522 	symbol->expression->accept(*this);
  1476 	if (NULL != symbol->statement_list)
  1523 	if (NULL != symbol->statement_list)
  1477 		symbol->statement_list->accept(*this);
  1524 		symbol->statement_list->accept(*this);