예제 #1
0
 static void RestoreSymbols(SymbolInfo si, PascalABCCompiler.TreeRealization.wrapped_definition_node wdn, string name)
 {
 	if (wdn.is_synonim)
 		si.sym_info = wdn.PCUReader.CreateTypeSynonim(wdn.offset, name);
 	else
 	if (si.scope is ClassScope)
         si.sym_info = wdn.PCUReader.CreateInterfaceInClassMember(wdn.offset, name);
     else
         si.sym_info = wdn.PCUReader.CreateImplementationMember(wdn.offset, false);
 }
예제 #2
0
 public static void RestoreSymbols(SymbolInfo si, string name)
 {
     while (si != null)
     {
         if (si.sym_info != null)
         if (si.sym_info.semantic_node_type == PascalABCCompiler.TreeRealization.semantic_node_type.wrap_def)
         {
             PascalABCCompiler.TreeRealization.wrapped_definition_node wdn = (PascalABCCompiler.TreeRealization.wrapped_definition_node)si.sym_info;
             RestoreSymbols(si, wdn, name);
         }
         si = si.Next;
     }
 }
예제 #3
0
 public static void RestoreSymbolsInterfaceMember(SymbolInfo si, string name)
 {
     while (si != null)
     {
         if (si.sym_info!=null)
         if (si.sym_info.semantic_node_type == PascalABCCompiler.TreeRealization.semantic_node_type.wrap_def)
         {
             PascalABCCompiler.TreeRealization.wrapped_definition_node wdn = (PascalABCCompiler.TreeRealization.wrapped_definition_node)si.sym_info;
             si.sym_info = wdn.PCUReader.CreateInterfaceMember(wdn.offset, name);
         }
         si = si.Next;
     }
 }
예제 #4
0
 public void reset()
 {
     _cmn = null;
     _ctn = null;
     _func_stack.clear();
     var_defs.Clear();
     _main_procedure = null;
     _last_created_function = null;
     _cycles_stack.clear();
     _num_of_for_cycles = 0;
     _fal = SemanticTree.field_access_level.fal_private;
     rec_num = 1;
     var_defs_stack.Clear();
     type_stack.Clear();
     clear_special_local_vars();
     _scope_stack.Clear();
 }
 private addressed_expression address_expression_reciving(SyntaxTree.ident id_right, SymbolInfo si,
     expression_node en)
 {
     if (si != null && si.sym_info != null &&
         si.sym_info.semantic_node_type == semantic_node_type.indefinite_definition_node)
     {
         return new indefinite_reference(si.sym_info as indefinite_definition_node, get_location(id_right));
     }
 	definition_node dn = null;
 	if (!internal_is_assign)
         dn = context.check_name_node_type(id_right.name, si, get_location(id_right),
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node);
     else
         dn = context.check_name_node_type(id_right.name, si, get_location(id_right),
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node, general_node_type.constant_definition);
     if (dn.general_node_type == general_node_type.constant_definition)
     {
         AddError(get_location(id_right), "CAN_NOT_ASSIGN_TO_CONSTANT_OBJECT");
     }
     switch (dn.general_node_type)
     {
         case general_node_type.variable_node:
             {
                 return create_class_field_reference(en, dn, id_right);
             }
         case general_node_type.property_node:
             {
                 property_node pn = (property_node)dn;
                 if (pn.polymorphic_state == SemanticTree.polymorphic_state.ps_static)
                 {
                     AddError(new CanNotReferenceToStaticPropertyWithExpression(pn, get_location(id_right), pn.comprehensive_type));
                 }
                 try_convert_typed_expression_to_function_call(ref en);
                 non_static_property_reference pr = new non_static_property_reference(pn, en, get_location(id_right));
                 return pr;
             }
         case general_node_type.event_node:
             {
                 if (dn.semantic_node_type == semantic_node_type.compiled_event)
                 {
                     compiled_event ce = (compiled_event)dn;
                     if (ce.is_static)
                     {
                         //throw new NonStaticAndStaticEvevnt();
                     }
                     nonstatic_event_reference ser = new nonstatic_event_reference(en, ce, get_location(id_right));
                     return ser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_event)
                 {
                     common_event ce = (common_event)dn;
                     if (ce.is_static)
                     {
                         //throw new NonStaticAndStaticEvevnt();
                     }
                     nonstatic_event_reference ser = new nonstatic_event_reference(en, ce, get_location(id_right));
                     return ser;
                 }
                 break;
             }
     	default : return null;
     }
     throw new CompilerInternalError("Undefined expression to address reciving");
 }
        internal expression_node convert_typed_expression_to_function_call(typed_expression te)
        {
            delegated_methods dm = te.type as delegated_methods;
            if (dm == null)
            {
                return te;
            }
            base_function_call bfc = dm.empty_param_method;
            if (bfc == null)
            {
                return te;
            }
            if (bfc.type == null) 
            	return te;
            function_node fn = bfc.simple_function_node;
            common_namespace_function_node cnfn = fn as common_namespace_function_node;
            if ((fn.parameters.Count == 1 || cnfn != null && fn.parameters.Count == 2 && cnfn.ConnectedToType != null)
                && (fn.parameters[fn.parameters.Count - 1].is_params || fn.parameters[fn.parameters.Count - 1].default_value != null))
            {
                fn = convertion_data_and_alghoritms.select_function(bfc.parameters, new SymbolInfo(fn), bfc.location);
                if (fn.polymorphic_state == SemanticTree.polymorphic_state.ps_static || fn is common_namespace_function_node || fn is basic_function_node)
                    bfc = convertion_data_and_alghoritms.create_simple_function_call(fn, bfc.location, bfc.parameters.ToArray()) as base_function_call;
                else
                {
                    expression_node obj = null;
                    if (bfc is common_method_call)
                        obj = (bfc as common_method_call).obj;
                    else if (bfc is compiled_function_call)
                        obj = (bfc as compiled_function_call).obj;
                    bfc = convertion_data_and_alghoritms.create_method_call(fn, bfc.location, obj, bfc.parameters.ToArray()) as base_function_call;

                }   
            }
            else
            {
                function_node[] empty_param_methods = dm.empty_param_methods;
                SymbolInfo si = new SymbolInfo(empty_param_methods[0]);
                SymbolInfo root_si = si;
                for (int i = 1; i < empty_param_methods.Length; i++)
                {
                    si.Next = new SymbolInfo(empty_param_methods[i]);
                    si = si.Next;
                }
                compiled_function_node cfn = fn as compiled_function_node;
                if ((fn.parameters.Count == 1 || cfn != null && fn.parameters.Count == 2 && cfn.ConnectedToType != null)
                    && (fn.parameters[fn.parameters.Count - 1].is_params || fn.parameters[fn.parameters.Count - 1].default_value != null))
                {
                    fn = convertion_data_and_alghoritms.select_function(bfc.parameters, root_si, bfc.location);
                    bfc = create_static_method_call_with_params(fn, bfc.location, fn.return_value_type, true, bfc.parameters);
                }
                else if (fn.parameters.Count == 1 && cfn != null && cfn.ConnectedToType != null)
                {
                    fn = convertion_data_and_alghoritms.select_function(bfc.parameters, root_si, bfc.location);
                    bfc = create_static_method_call_with_params(fn, bfc.location, fn.return_value_type, true, bfc.parameters);
                }
            }
            return bfc;
        }
 private addressed_expression create_addressed_with_type_expression(type_node tn, SyntaxTree.ident id_right,
     SymbolInfo si_right)
 {
     definition_node dn = null;
     if (!internal_is_assign)
     dn = context.check_name_node_type(id_right.name, si_right, get_location(id_right),
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node);
     else
         dn = context.check_name_node_type(id_right.name, si_right, get_location(id_right),
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node,general_node_type.constant_definition);
     if (dn.general_node_type == general_node_type.constant_definition)
         AddError(get_location(id_right), "CAN_NOT_ASSIGN_TO_CONSTANT_OBJECT");
     switch (dn.general_node_type)
     {
         case general_node_type.variable_node:
             {
                 return create_class_static_field_reference(tn, dn, id_right);
             }
         case general_node_type.property_node:
             {
                 property_node pn = (property_node)dn;
                 if (pn.polymorphic_state != SemanticTree.polymorphic_state.ps_static)
                 {
                     AddError(new CanNotReferenceToNonStaticPropertyWithType(pn, get_location(id_right), tn));
                 }
                 static_property_reference pr = new static_property_reference(pn, get_location(id_right));
                 return pr;
             }
         case general_node_type.event_node:
             {
                 if (dn.semantic_node_type == semantic_node_type.compiled_event)
                 {
                     compiled_event ce = (compiled_event)dn;
                     if (!ce.is_static)
                     {
                         //throw new NonStaticAndStaticEvevnt();
                     }
                     static_event_reference ser = new static_event_reference(ce, get_location(id_right));
                     return ser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_event)
                 {
                     common_event ce = (common_event)dn;
                     if (!ce.is_static)
                     {
                         //throw new NonStaticAndStaticEvevnt();
                     }
                     static_event_reference ser = new static_event_reference(ce, get_location(id_right));
                     return ser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_namespace_event)
                 {
                     common_namespace_event cne = dn as common_namespace_event;
                     static_event_reference ser = new static_event_reference(cne, get_location(id_right));
                     return ser;
                 }
                 break;
             }
     		default : return null;
     }
     throw new CompilerInternalError("Invalid right type expression");
 }
        private expression_node make_dec_call(SymbolInfo si, SyntaxTree.expression_list parameters, location loc)
        {
        	if (parameters == null) throw new NoFunctionWithSameParametresNum(loc,false,si.sym_info as function_node);
        	if (parameters.expressions.Count == 1 || parameters.expressions.Count == 2)
        	{
        		expression_node param0 = convert_strong(parameters.expressions[0]);
        		if (!param0.is_addressed)
        		{
        			bool is_pascal_array_ref = false;
                    if (param0.semantic_node_type == semantic_node_type.common_method_call)
                    {
                        common_method_call cmc = (common_method_call)param0;
                        internal_interface ii = cmc.obj.type.get_internal_interface(internal_interface_kind.bounded_array_interface);
                        if (ii != null)
                        {
                            if (cmc.function_node.name == compiler_string_consts.get_val_pascal_array_name)
                            {
                                bounded_array_interface bai = (bounded_array_interface)ii;
                                class_field cf = bai.int_array;
                                expression_node left = new class_field_reference(cf, cmc.obj, cmc.location);
                                expression_node right = cmc.parameters[0];
                                //right = convert_type(right, SystemLibrary.SystemLibrary.integer_type);
                                right = convertion_data_and_alghoritms.convert_type(right, (ii as bounded_array_interface).ordinal_type_interface.elems_type);
                                right = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibrary.int_sub, cmc.location, right,
                                    new int_const_node(bai.ordinal_type_interface.ordinal_type_to_int(bai.ordinal_type_interface.lower_value), cmc.location));
                                param0 = new simple_array_indexing(left, right, cmc.type, cmc.location);
                                is_pascal_array_ref = true;

                            }
                        }
                        if (!is_pascal_array_ref)
                        {
							throw new ThisExpressionCanNotBePassedAsVarParameter(param0);
                    	}
        				
        			}
                    else if (param0 is compiled_function_call)
                    {
                    	compiled_function_call cfc = param0 as compiled_function_call;
                    	if ((cfc.function_node.return_value_type == SystemLibrary.SystemLibrary.char_type && cfc.function_node.cont_type == SystemLibrary.SystemLibrary.string_type
                    	      && cfc.function_node == cfc.function_node.cont_type.default_property_node.get_function))
                    	{
                    		expressions_list exl = new expressions_list();
                            exl.AddElement(cfc.obj);
                            exl.AddElement(cfc.parameters[0]);
                            basic_function_call bfc2 = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
                            bfc2.parameters.AddElement(param0);
                            expression_node _param1 = null;
                            if (parameters.expressions.Count == 2) 
        					{
        						_param1 = convert_strong(parameters.expressions[1]);
        					}
                            if (_param1 != null)
                            	bfc2.parameters.AddElement(convertion_data_and_alghoritms.convert_type(_param1,SystemLibrary.SystemLibrary.integer_type));
                            else
                            	bfc2.parameters.AddElement(new int_const_node(1,null));
                            expressions_list el = new expressions_list();
                            el.AddElement(convertion_data_and_alghoritms.convert_type(bfc2,SystemLibrary.SystemLibrary.ushort_type));
                            function_node chr_func = convertion_data_and_alghoritms.select_function(el, SystemLibrary.SystemLibInitializer.ChrUnicodeFunction.SymbolInfo, loc);
                            exl.AddElement(convertion_data_and_alghoritms.create_simple_function_call(chr_func, loc, el.ToArray()));
                            function_node fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.StringDefaultPropertySetProcedure.SymbolInfo, loc);
                            expression_node ret = convertion_data_and_alghoritms.create_simple_function_call(fn, loc, exl.ToArray());
                            return ret;
                    	}
                    	else
                    	{
                    		throw new ThisExpressionCanNotBePassedAsVarParameter(param0);
                    	}
                    }
                    else throw new ThisExpressionCanNotBePassedAsVarParameter(param0);
        		}
        		else
        			check_on_loop_variable(param0);
        		expression_node param1 = null;
        		int type_flag = 0;
        		bool is_uint=false;
        		bool is_enum=false;
        		if (parameters.expressions.Count == 2) 
        		{
        			param1 = convert_strong(parameters.expressions[1]);
        			param1 = convertion_data_and_alghoritms.convert_type(param1,SystemLibrary.SystemLibrary.integer_type);
        		}
        		basic_function_call ass = null;
        		basic_function_call bfc = null;
        		if (param0.type == SystemLibrary.SystemLibrary.integer_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.int_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.char_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.char_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.byte_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.byte_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.sbyte_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.sbyte_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.short_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.short_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.ushort_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.ushort_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.uint_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.uint_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.uint_sub as basic_function_node,loc);
        			type_flag = 2;
        			is_uint = true;
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.int64_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.long_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.long_sub as basic_function_node,loc);
        			type_flag = 1;
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.uint64_type)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.ulong_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.ulong_sub as basic_function_node,loc);
        			type_flag = 2;
        		}
        		else if (param0.type == SystemLibrary.SystemLibrary.bool_type)
        		{
        			if (param1 == null)
        			{
        				ass = new basic_function_call(SystemLibrary.SystemLibrary.bool_assign as basic_function_node,loc);
        				bfc = new basic_function_call(SystemLibrary.SystemLibrary.bool_not as basic_function_node,loc);
        				type_flag = 4;
        			}
        			else
        			{
        				basic_function_call mod_expr = new basic_function_call(SystemLibrary.SystemLibrary.int_mod as basic_function_node,loc);
        				mod_expr.parameters.AddElement(convertion_data_and_alghoritms.convert_type(param1,SystemLibrary.SystemLibrary.integer_type));
        				mod_expr.parameters.AddElement(new int_const_node(2,loc));
        				basic_function_call condition = new basic_function_call(SystemLibrary.SystemLibrary.int_eq as basic_function_node,loc);
        				condition.parameters.AddElement(mod_expr);
        				condition.parameters.AddElement(new int_const_node(0,loc));
        				basic_function_call not_expr = new basic_function_call(SystemLibrary.SystemLibrary.bool_not as basic_function_node,loc);
        				not_expr.parameters.AddElement(param0);
        				question_colon_expression qce = new question_colon_expression(condition, param0, not_expr, loc);
        				ass = new basic_function_call(SystemLibrary.SystemLibrary.bool_assign as basic_function_node,loc);
        				ass.parameters.AddElement(param0);
        				ass.parameters.AddElement(qce);
        				type_flag = 5;
        			}
        		}
        		else if (param0.type.type_special_kind == PascalABCCompiler.SemanticTree.type_special_kind.diap_type || param0.type.IsEnum)
        		{
        			ass = new basic_function_call(SystemLibrary.SystemLibrary.int_assign as basic_function_node,loc);
        			bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_sub as basic_function_node,loc);
        			if (param0.type.type_special_kind == PascalABCCompiler.SemanticTree.type_special_kind.diap_type)
        			{
        				type_node bt = param0.type.base_type;
        				if (bt == SystemLibrary.SystemLibrary.int64_type) type_flag = 1;
        				else if (bt == SystemLibrary.SystemLibrary.uint64_type) type_flag = 2;
        				else if (bt == SystemLibrary.SystemLibrary.uint_type) 
        				{
        					type_flag =2;
        					is_uint = true;
        				}
        				else if (bt.IsEnum) is_enum = true;
        			}
        			else if (param0.type.IsEnum) is_enum = true;
        		}
        		else throw new NoFunctionWithSameArguments(loc,false);
                if (type_flag != 5)
                {
                    if (param1 != null)
                        switch (type_flag)
                        {
                            case 0: param1 = convertion_data_and_alghoritms.convert_type(param1, SystemLibrary.SystemLibrary.integer_type); break;
                            case 3:
                            case 1: param1 = convertion_data_and_alghoritms.convert_type(param1, SystemLibrary.SystemLibrary.int64_type); break;
                            case 2: param1 = convertion_data_and_alghoritms.convert_type(param1, SystemLibrary.SystemLibrary.uint64_type); break;
                        }
                    //bfc.parameters.AddElement(param0);
                    if (param0.type != SystemLibrary.SystemLibrary.char_type && !is_enum && param0.type != SystemLibrary.SystemLibrary.bool_type)
                        switch (type_flag)
                        {
                            case 0: bfc.parameters.AddElement(convertion_data_and_alghoritms.convert_type(param0, SystemLibrary.SystemLibrary.integer_type)); break;
                            case 3:
                            case 1: bfc.parameters.AddElement(convertion_data_and_alghoritms.convert_type(param0, SystemLibrary.SystemLibrary.int64_type)); break;
                            case 2: bfc.parameters.AddElement(convertion_data_and_alghoritms.convert_type(param0, SystemLibrary.SystemLibrary.uint64_type)); break;
                        }
                    else bfc.parameters.AddElement(param0);
                    if (param1 == null)
                    {
                        if (type_flag == 0 || type_flag == 3)
                            bfc.parameters.AddElement(new int_const_node(1, null));
                        else if (type_flag == 1)
                            bfc.parameters.AddElement(new long_const_node(1, null));
                        else if (type_flag == 2)
                            bfc.parameters.AddElement(new ulong_const_node(1, null));
                    }
                    else bfc.parameters.AddElement(param1);
                    ass.parameters.AddElement(param0);
                    if (is_uint)
                        ass.parameters.AddElement(convertion_data_and_alghoritms.convert_type(bfc, SystemLibrary.SystemLibrary.uint_type));
                    else
                        ass.parameters.AddElement(bfc);
                }
        		return ass;
        	}
        	
        	throw new NoFunctionWithSameParametresNum(loc,false,si.sym_info as function_node);
        }
        private expression_node make_dispose_call(SymbolInfo si, SyntaxTree.expression_list parameters, location loc)
        {
            if (parameters == null)
            {
                AddError(new NoFunctionWithSameParametresNum(loc, false, si.sym_info as function_node));
                return null;
            }
            if (parameters.expressions.Count == 1)
            {
                expression_node param0 = convert_strong(parameters.expressions[0]);
                if (!param0.type.IsPointer || param0.type == SystemLibrary.SystemLibrary.pointer_type)
                    AddError(new NoFunctionWithSameArguments(loc, true));
                if (!param0.is_addressed)
                {
                    bool is_pascal_array_ref = false;
                    if (param0.semantic_node_type == semantic_node_type.common_method_call)
                    {
                        common_method_call cmc = (common_method_call)param0;
                        internal_interface ii = cmc.obj.type.get_internal_interface(internal_interface_kind.bounded_array_interface);
                        if (ii != null)
                        {
                            if (cmc.function_node.name == compiler_string_consts.get_val_pascal_array_name)
                            {
                                bounded_array_interface bai = (bounded_array_interface)ii;
                                class_field cf = bai.int_array;
                                expression_node left = new class_field_reference(cf, cmc.obj, cmc.location);
                                expression_node right = cmc.parameters[0];
                                //right = convert_type(right, SystemLibrary.SystemLibrary.integer_type);
                                right = convertion_data_and_alghoritms.convert_type(right, (ii as bounded_array_interface).ordinal_type_interface.elems_type);
                                right = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibrary.int_sub, cmc.location, right,
                                    new int_const_node(bai.ordinal_type_interface.ordinal_type_to_int(bai.ordinal_type_interface.lower_value), cmc.location));
                                param0 = new simple_array_indexing(left, right, cmc.type, cmc.location);
                                is_pascal_array_ref = true;
                            }
                        }
                        if (!is_pascal_array_ref)
                        {
                            AddError(new ThisExpressionCanNotBePassedAsVarParameter(param0));
                            return null;
                        }

                    }
                    else
                    {
                        AddError(new ThisExpressionCanNotBePassedAsVarParameter(param0));
                        return null;
                    }
                }
                function_node fn = si.sym_info as function_node;
                common_namespace_function_call cnfc = new common_namespace_function_call(fn as common_namespace_function_node, loc);
                cnfc.parameters.AddElement(param0);
                return cnfc;

            }
            else
            {
                AddError(new NoFunctionWithSameParametresNum(loc, false, si.sym_info as function_node));
                return null;
            }
        }
 //ssyy
 //Удаляет конструкторы предков в списке si
 private void delete_inherited_constructors(ref SymbolInfo si, type_node tn)
 {
     SymbolInfo last_sym = null;
     SymbolInfo cur_sym = si;
     while (cur_sym != null)
     {
         type_node comph_type = null;
         bool is_ctor = false;
         common_method_node mnode = cur_sym.sym_info as common_method_node;
         if (mnode != null)
         {
             comph_type = mnode.cont_type;
             is_ctor = mnode.is_constructor;
         }
         else
         {
             compiled_function_node tnode = cur_sym.sym_info as compiled_function_node;
             if (tnode != null)
             {
                 comph_type = tnode.cont_type;
                 is_ctor = tnode.method_info.IsConstructor;
             }
         }
         //Итак, comph_type - класс, содержащий si.sym_info;
         //is_ctor - является ли оно конструктором
         if (is_ctor && comph_type != tn)
         {
             //Удаляем
             if (last_sym == null)
             {
                 si = si.Next;
             }
             else
             {
                 last_sym.Next = cur_sym.Next;
             }
         }
         else
         {
             last_sym = cur_sym;
         }
         cur_sym = cur_sym.Next;
     }
 }
 private expression_node ident_value_reciving(SymbolInfo si, SyntaxTree.ident _ident)
 {
     //SymbolInfo si=blocks.find(_ident.name);
     location lloc = get_location(_ident);
     definition_node dn = context.check_name_node_type(_ident.name, si, get_location(_ident), general_node_type.variable_node,
         general_node_type.function_node, general_node_type.property_node, general_node_type.constant_definition,
         general_node_type.event_node);
     switch (dn.general_node_type)
     {
         case general_node_type.constant_definition:
             {
                 constant_definition_node cdn = (constant_definition_node)dn;
                 if (cdn.const_value is array_const || cdn.const_value is record_constant || cdn.const_value is common_namespace_function_call_as_constant)
                 {
                 	return create_constant_reference(cdn,lloc);
                 }
                 if (cdn.const_value == null)
                     AddError(new UndefinedNameReference(cdn.name,get_location(_ident)));
                 constant_node cn = cdn.const_value.get_constant_copy(get_location(_ident));
                 if (cn != null) return cn;
                 return cdn.const_value;
             }
         case general_node_type.variable_node:
             {
                 local_variable lv = dn as local_variable;
                 if (lv != null && (lv.function is common_method_node))
                 {
                     //self variable
                     if ((lv.function as common_method_node).self_variable == lv)
                         //return new this_node((lv.function as common_method_node).cont_type, lloc);
                         return new this_node(lv.type, lloc);
                     //return GetCurrentObjectReference((lv.function as common_method_node).cont_type.Scope, lloc);
                 }
                 return create_variable_reference(dn, lloc);
             }
         case general_node_type.function_node:
             {
                 //return convertion_data_and_alghoritms.create_full_function_call(new expressions_list(),
                 //	si,lloc,blocks.converted_type,blocks.top_function,false);
                 if (!(si.sym_info is common_in_function_function_node))
                     return make_delegate_wrapper(null, si, lloc, ((si.sym_info is common_method_node) && ((common_method_node)si.sym_info).IsStatic));
                 return convertion_data_and_alghoritms.create_full_function_call(new expressions_list(),
                 	si,lloc,context.converted_type,context.top_function,false);
             }
         case general_node_type.property_node:
             {
                 property_node pn = (property_node)dn;
                 function_node fn = pn.get_function;
                 if (fn == null)
                 {
                     AddError(new ThisPropertyCanNotBeReaded(pn, lloc));
                 }
                 if (pn.polymorphic_state == SemanticTree.polymorphic_state.ps_static)
                 {
                     return create_static_method_call(fn, lloc, pn.comprehensive_type, false);
                 }
                 check_property_no_params(pn, lloc);
                 //this_node thisnode = new this_node(context.converted_type, lloc);
                 if (pn.comprehensive_type.Scope == null && pn is compiled_property_node)
                 	(pn.comprehensive_type as compiled_type_node).init_scope();
                 return create_not_static_method_call(fn, GetCurrentObjectReference(pn.comprehensive_type.Scope, fn, lloc), lloc, false);
             }
         case general_node_type.event_node:
             {
                 if (dn.semantic_node_type == semantic_node_type.compiled_event)
                 {
                     compiled_event ce = (compiled_event)dn;
                     if (ce.is_static)
                     {
                         static_event_reference ser = new static_event_reference(ce, get_location(_ident));
                         return ser;
                     }
                     nonstatic_event_reference nser = new nonstatic_event_reference(
                         new this_node(context.converted_type, lloc), ce, lloc);
                     return nser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_event)
                 {
                     common_event ce = (common_event)dn;
                     if (ce.is_static)
                     {
                         static_event_reference ser = new static_event_reference(ce, get_location(_ident));
                         return ser;
                     }
                     nonstatic_event_reference nser = new nonstatic_event_reference(
                         new this_node(context.converted_type, lloc), ce, lloc);
                     return nser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_namespace_event)
                 {
                     common_namespace_event cne = (common_namespace_event)dn;
                     if (_compiled_unit.namespaces.IndexOf(cne.namespace_node) != -1)
                     {
                         static_event_reference ser = new static_event_reference(cne, get_location(_ident));
                         return ser;
                     }
                     else
                         AddError(get_location(_ident), "EVENT_{0}_MUST_BE_IN_LEFT_PART", cne.name);
                 }
                 break;
             }
     }
     return null;
 }
 private addressed_expression ident_address_reciving(SymbolInfo si, SyntaxTree.ident _ident)
 {
     location lloc = get_location(_ident);
     definition_node dn = null;
     if (!internal_is_assign)
         dn = context.check_name_node_type(_ident.name, si, lloc,
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node);
     else
         dn = context.check_name_node_type(_ident.name, si, lloc,
         general_node_type.variable_node, general_node_type.property_node, general_node_type.event_node, general_node_type.constant_definition);
     if (dn.general_node_type == general_node_type.constant_definition)
         AddError(get_location(_ident), "CAN_NOT_ASSIGN_TO_CONSTANT_OBJECT");
     switch (dn.general_node_type)
     {
         case general_node_type.variable_node:
             {
                 local_variable lv = dn as local_variable;
                 if (lv != null && (lv.function is common_method_node))
                 {
                     //self variable
                     if ((lv.function as common_method_node).self_variable == lv)
                         AddError(lloc, "VARIABLE_{0}_READONLY", lv.name);
                 }
                 return create_variable_reference(dn, lloc);
             }
         case general_node_type.property_node:
             {
                 property_node pn = (property_node)dn;
                 if (pn.polymorphic_state == SemanticTree.polymorphic_state.ps_static)
                 {
                     static_property_reference spr = new static_property_reference(pn, lloc);
                     return spr;
                 }
                 //this_node thisnode=new this_node(context.converted_type,lloc);
                 if (pn.comprehensive_type.Scope == null && pn is compiled_property_node)
                 	(pn.comprehensive_type as compiled_type_node).init_scope();
                 non_static_property_reference nspr = new non_static_property_reference(pn, GetCurrentObjectReference(pn.comprehensive_type.Scope, pn, lloc), lloc);
                 return nspr;
             }
         case general_node_type.event_node:
             {
                 if (dn.semantic_node_type == semantic_node_type.compiled_event)
                 {
                     compiled_event ce = (compiled_event)dn;
                     if (ce.is_static)
                     {
                         static_event_reference ser = new static_event_reference(ce, get_location(_ident));
                         return ser;
                     }
                     nonstatic_event_reference nser = new nonstatic_event_reference(
                         GetCurrentObjectReference(ce.comprehensive_type.Scope, ce, lloc), ce, lloc);
                     return nser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_event)
                 {
                 	common_event ce = (common_event)dn;
                 	if (ce.is_static)
                     {
                         static_event_reference ser = new static_event_reference(ce, get_location(_ident));
                         return ser;
                     }
                     nonstatic_event_reference nser = new nonstatic_event_reference(
                         GetCurrentObjectReference(ce.comprehensive_type.Scope, ce, lloc), ce, lloc);
                     return nser;
                 }
                 else if (dn.semantic_node_type == semantic_node_type.common_namespace_event)
                 {
                     common_namespace_event cne = (common_namespace_event)dn;
                     static_event_reference ser = new static_event_reference(cne, get_location(_ident));
                     return ser;
                 }
                 break;
             }
     }
     return null;
 }
        private base_function_call_list create_possible_delegates_list(expression_node obj, SymbolInfo si, location loc, bool is_static)
        {
            if (si == null)
            {
                return new base_function_call_list();
            }
            function_node_list fnl = new function_node_list();
            while (si != null)
            {
                function_node fn = si.sym_info as function_node;
                if (si.sym_info is compiled_property_node)
                {
                    fn = (si.sym_info as compiled_property_node).get_function; 
                }
                else if (si.sym_info is common_property_node)
                {
                    fn = (si.sym_info as common_property_node).get_function;
                }
                if (convertion_data_and_alghoritms.find_eq_method_in_list(fn, fnl) == null)
                {
                    if (!(obj != null && fn.polymorphic_state == SemanticTree.polymorphic_state.ps_static && !fn.is_extension_method))
                    {
                        if (fn.is_extension_method)
                        {
                            if (obj != null && (fn.parameters[0].type == obj.type || type_table.compare_types(fn.parameters[0].type, obj.type) == type_compare.greater_type))
                                fnl.AddElementFirst(fn);
                            else
                                fnl.AddElement(fn);
                        }
                        else
                            fnl.AddElement(fn);
                    }
                }
                else
                {

                }
                si = si.Next;
            }
            return convert_functions_to_calls(obj, fnl, loc, is_static);
        }
 private bool FunctionExsistsInSymbolInfo(function_node fn, SymbolInfo si)
 {
     while (si != null)
     {
         if (si.sym_info is function_node)
             if (convertion_data_and_alghoritms.function_eq_params(fn, si.sym_info as function_node))
                 return true;
         si = si.Next;
     }
     return false;
 }
예제 #15
0
		public common_function_node create_function(string name,location def_loc)
		{
			check_function_name(name,def_loc);
			common_function_node cfn=null;
			switch (converting_block())
			{
				case block_type.function_block:
				{
                    common_function_node top_func = _func_stack.top();
                    SymbolTable.Scope scope = convertion_data_and_alghoritms.symbol_table.CreateScope(top_func.scope);
					common_in_function_function_node ciffn;
					ciffn=new common_in_function_function_node(name,def_loc,top_func,scope);
					top_func.functions_nodes_list.AddElement(ciffn);
					_last_created_function=new SymbolInfo(ciffn);
					top_func.scope.AddSymbol(name,_last_created_function);
					cfn=ciffn;
					break;
				}
				case block_type.type_block:
				{
					common_method_node cmmn;
                    SymbolTable.Scope scope = convertion_data_and_alghoritms.symbol_table.CreateClassMethodScope(_cmn.scope, _ctn.Scope);
                    //TODO:сделать static и virtual.
                    //TODO: interface and implementation scopes.
					cmmn=new common_method_node(name,def_loc,_ctn,SemanticTree.polymorphic_state.ps_common,_fal,scope);
					_last_created_function=new SymbolInfo(cmmn);
					_ctn.Scope.AddSymbol(name,_last_created_function);
					_ctn.methods.AddElement(cmmn);

                    local_variable lv = new local_variable(compiler_string_consts.self_word, _ctn, cmmn, def_loc);
                    cmmn.scope.AddSymbol(compiler_string_consts.self_word, new SymbolInfo(lv));
                    cmmn.self_variable = lv;
                    cmmn.var_definition_nodes_list.AddElement(lv);

					cfn=cmmn;
					break;
				}
				case block_type.namespace_block:
				{
					common_namespace_function_node cnfnn;
                    SymbolTable.Scope scope = convertion_data_and_alghoritms.symbol_table.CreateScope(_cmn.scope);
					cnfnn=new common_namespace_function_node(name,def_loc,_cmn,scope);
					_cmn.functions.AddElement(cnfnn);
					_last_created_function=new SymbolInfo(cnfnn);
					_cmn.scope.AddSymbol(name,_last_created_function);
					cfn=cnfnn;
					break;
				}
			}
			_func_stack.push(cfn);
			return cfn;
		}
        internal void visit_method_call(SyntaxTree.method_call _method_call)
        {
            // frninja 01/03/16 - for iterator capturing (yield)
            if (_method_call.dereferencing_value is yield_unknown_ident)
            {
                var nodeToVisit = new method_call(ProcessUnknownIdent(_method_call.dereferencing_value as yield_unknown_ident), _method_call.parameters);
                visit(nodeToVisit);
                return;
            }
            // end frninja

            //lroman
            if (_method_call.dereferencing_value is closure_substituting_node)
            {
                var nodeToVisit =
                    new method_call(((closure_substituting_node) _method_call.dereferencing_value).substitution,
                                    _method_call.parameters);
                visit(nodeToVisit);
                return;
            }

            bool proc_wait = procedure_wait;
			bool lambdas_are_in_parameters = false; //lroman//

            var syntax_nodes_parameters = _method_call.parameters == null
                                              ? new List<expression>()
                                              : _method_call.parameters.expressions;
            if (procedure_wait)
            {
                procedure_wait = false;
            }
            //throw new ArgumentNullException("test");

            motivation mot = motivation_keeper.motivation;

            expression_node expr_node = null;
            expressions_list exprs = new expressions_list();

            SyntaxTree.ident id = null;

            SymbolInfo si = null;

            type_node to_type = null;

            SyntaxTree.addressed_value deref_value = _method_call.dereferencing_value;
            int templ_args_count = 0;
            //bool needs_generic_type_search = false;
            SyntaxTree.ident_with_templateparams iwt = deref_value as SyntaxTree.ident_with_templateparams;
            if (iwt != null)
            {
                deref_value = iwt.name;
                templ_args_count = iwt.template_params.params_list.Count;
                //needs_generic_type_search = _method_call.parameters.expressions.Count == 1;
            }

            SyntaxTree.inherited_ident inh_id = deref_value as SyntaxTree.inherited_ident;
            if (inh_id != null)
            {
                inherited_ident_processing = true;
                si = find_in_base(inh_id);
                if (si != null) 
            	if (si.sym_info is common_method_node)
            	{
            		if ((si.sym_info as common_method_node).polymorphic_state == SemanticTree.polymorphic_state.ps_virtual_abstract)
                        AddError(get_location(inh_id), "CANNOT_CALL_ABSTRACT_METHOD");
            	}
            	else
            	if (si.sym_info is compiled_function_node)
            	{
            		if ((si.sym_info as compiled_function_node).polymorphic_state == SemanticTree.polymorphic_state.ps_virtual_abstract)
                        AddError(get_location(inh_id), "CANNOT_CALL_ABSTRACT_METHOD");
            	}
                id = inh_id;
            }
            else
            {
                id = deref_value as SyntaxTree.ident;
                if (id != null)
                {
                    if (templ_args_count != 0)
                    {
                        //Ищем generics
                        si = context.find(id.name + compiler_string_consts.generic_params_infix + templ_args_count.ToString());
                        if (si != null)
                        {
                            si = new SymbolInfo(get_generic_instance(si, iwt.template_params.params_list));
                            iwt = null;
                        }
                    }
                    if (si == null)
                    {
                        SyntaxTree.operator_name_ident oni = id as SyntaxTree.operator_name_ident;
                        if (oni != null)
                        {
                            si = context.find(name_reflector.get_name(oni.operator_type));
                        }
                        else
                        {
                            si = context.find(id.name);
                            if (templ_args_count != 0)
                            {
                                SymbolInfo conv = ConvertTypeToInstance(si, iwt.template_params.params_list, get_location(id));
                                if (conv != null)
                                {
                                    si = conv;
                                    iwt = null;
                                }
                            }
                        }
                    }
                }
                else
                {
                    SyntaxTree.dot_node _dot_node = deref_value as SyntaxTree.dot_node;
                    if (_dot_node != null)
                    {
						bool skip_first_parameter = false; //lroman//
                        bool has_extension_overload = false;
                        semantic_node sn = convert_semantic_strong(_dot_node.left);

                        //SyntaxTree.ident id_right = ConvertOperatorNameToIdent(_dot_node.right as SyntaxTree.ident);
                        SyntaxTree.ident id_right = _dot_node.right as SyntaxTree.ident;
                        switch (sn.general_node_type)
                        {
                            case general_node_type.expression:
                                {
                                    expression_node exp = (expression_node)sn;
                                    if (exp is typed_expression)
                                        try_convert_typed_expression_to_function_call(ref exp);
                                    SyntaxTree.operator_name_ident oni_right = id_right as SyntaxTree.operator_name_ident;
                                    if (oni_right != null)
                                    {
                                        si = exp.type.find_in_type(name_reflector.get_name(oni_right.operator_type), context.CurrentScope);
                                    }
                                    else
                                    {
                                        si = exp.type.find_in_type(id_right.name, context.CurrentScope);
                                        if (si != null && si.sym_info != null && si.sym_info.semantic_node_type == semantic_node_type.wrap_def)
                                            BasePCUReader.RestoreSymbols(si, id_right.name);
                                    }

                                    
                                    //definition_node ddn=check_name_node_type(id_right.name,si,get_location(id_right),
                                    //	general_node_type.function_node,general_node_type.variable_node);

                                    location subloc = get_location(id_right);

                                    if (si == null)
                                    {
                                        AddError(new UndefinedNameReference(id_right.name, subloc));
                                    }

                                    if (si.sym_info.general_node_type != general_node_type.function_node)
                                    {
                                        if (si.sym_info.general_node_type == general_node_type.type_node)
                                        {
                                            to_type = ((type_node)(si.sym_info));
                                        }
                                        else
                                        {
                                            dot_node_as_expression_dot_ident(exp, id_right, motivation.expression_evaluation, _dot_node.left);
                                            exp = ret.get_expression();
                                            internal_interface ii = exp.type.get_internal_interface(internal_interface_kind.delegate_interface);
                                            if (ii == null)
                                            {
                                                AddError(subloc, "EXPECTED_DELEGATE");
                                            }
                                            delegate_internal_interface dii = ii as delegate_internal_interface;
                                            si = new SymbolInfo(dii.invoke_method);
                                        }
                                    }

                                    if (to_type != null)
                                    {
                                        if ((_method_call.parameters == null) || (_method_call.parameters.expressions.Count != 1))
                                        {
                                            AddError(get_location(_method_call), "ONLY_ONE_PARAMETER_OF_TYPE_CONVERSION_ALLOWED" );
                                        }
                                    }
                                    SymbolInfo tmp_si = si;
                                    while (si != null)
                                    {
                                        if (si.sym_info is common_namespace_function_node)
                                        {
                                            common_namespace_function_node cnfn = si.sym_info as common_namespace_function_node;
                                            if (cnfn.ConnectedToType != null && !cnfn.IsOperator)
                                            {
                                                exprs.AddElementFirst(exp);
                                                skip_first_parameter = true;
                                                break;
                                            }
                                        }
                                        if (si.sym_info is compiled_function_node)
                                        {
                                            compiled_function_node cfn = si.sym_info as compiled_function_node;
                                            if (cfn.ConnectedToType != null)
                                            {
                                                exprs.AddElementFirst(exp);
                                                skip_first_parameter = true;
                                                if (cfn.is_generic_function)
                                                {
                                                    //generic_convertions.DeduceFunction(cfn, exprs);
                                                    //si.sym_info = cfn.get_instance(new List<type_node>(new type_node[] { exp.type }), true, get_location(_method_call));
                                                }
                                                break;
                                            }

                                        }
                                        si = si.Next;
                                    }
                                    
                                    si = tmp_si;
                                    if (skip_first_parameter)
                                    {
                                        SymbolInfo new_si = null;
                                        bool has_obj_methods = false;
                                        List<SymbolInfo> si_list = new List<SymbolInfo>();
                                        while (si != null)
                                        {
                                            if (si.sym_info is common_namespace_function_node)
                                            {
                                                common_namespace_function_node cnfn = si.sym_info as common_namespace_function_node;
                                                if (cnfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static || cnfn.ConnectedToType != null)
                                                    si_list.Add(si);
                                                if (cnfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static && cnfn.ConnectedToType == null)
                                                    has_obj_methods = true;
                                            }
                                            else if (si.sym_info is compiled_function_node)
                                            {
                                                compiled_function_node cfn = si.sym_info as compiled_function_node;
                                                if (cfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static || cfn.ConnectedToType != null)
                                                    si_list.Add(si);
                                                if (cfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static && cfn.ConnectedToType == null)
                                                    has_obj_methods = true;
                                            }
                                            else if (si.sym_info is common_method_node)
                                            {
                                                common_method_node cfn = si.sym_info as common_method_node;
                                                if (cfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static)
                                                    si_list.Add(si);
                                                if (cfn.polymorphic_state != SemanticTree.polymorphic_state.ps_static)
                                                    has_obj_methods = true;
                                            }
                                            si = si.Next;
                                        }
                                        for (int i = 0; i < si_list.Count; i++)
                                        {
                                            if (new_si == null)
                                            {
                                                new_si = si_list[i];
                                                si = new_si;
                                            }
                                            else
                                            {
                                                si.Next = si_list[i];
                                                si = si.Next;
                                            }
                                        }
                                        if (si != null)
                                            si.Next = null;
                                        si = new_si;
                                    }
                                    if (_method_call.parameters != null)
                                    {
                                    	foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                        {
                                            #region Отмечаем флаг в лямбдах, говорящий о том, что в первый раз будем их "обходить" для вывода типов
                                            //lroman//
                                            if (en is SyntaxTree.function_lambda_definition)
                                            {
                                                lambdas_are_in_parameters = true;
                                                ((SyntaxTree.function_lambda_definition)en).lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                            }
                                            //lroman//
                                            #endregion
                                            var cen = convert_strong(en);
                                            exprs.AddElement(cen);
                                        }
                                    }

                                    expression_node subexpr1 = null;

                                    if (to_type != null)
                                    {
                                        subexpr1 = convertion_data_and_alghoritms.explicit_convert_type(exprs[0], to_type);
                                    }
                                    else
                                    {
                                        if (iwt != null)
                                        {
                                            si = get_generic_functions(si, true, subloc);
                                            si = get_function_instances(si, iwt.template_params.params_list, id_right.name, subloc, si.Next == null);
                                        }
										#region Если встретились лямбды в фактических параметрах, то выбираем нужную функцию из перегруженных, выводим типы, отмечаем флаг в лямбдах, говорящий о том, что мы их реально обходим
                                        //lroman//
                                        if (lambdas_are_in_parameters)
                                        {
                                            LambdaHelper.processingLambdaParametersForTypeInference++;
                                            // SSM 21.05.14 - попытка обработать перегруженные функции с параметрами-лямбдами с различными возвращаемыми значениями
                                            function_node_list spf = null;
                                            try
                                            {
                                                ThrowCompilationError = false;
                                                function_node ffn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                                if (ffn == null)
                                                {
                                                    if (skip_first_parameter)
                                                    {
                                                        expressions_list ex_list = new expressions_list();
                                                        ex_list.AddRange(exprs);
                                                        ex_list.remove_at(0);
                                                        ffn = convertion_data_and_alghoritms.select_function(ex_list, si, subloc, syntax_nodes_parameters);
                                                        if (ffn == null)
                                                        {
                                                            ThrowCompilationError = true;
                                                            throw LastError();
                                                        }
                                                        RemoveLastError();
                                                        skip_first_parameter = false;
                                                        exprs = ex_list;
                                                        ThrowCompilationError = true;
                                                    }
                                                    else
                                                    {
                                                        ThrowCompilationError = true;
                                                        throw LastError();
                                                    }
                                                        
                                                }
                                                ThrowCompilationError = true;
                                                int exprCounter = 0;
                                                if (skip_first_parameter)
                                                {
                                                    exprCounter++;
                                                }
                                                foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                                {
                                                    if (!(en is SyntaxTree.function_lambda_definition))
                                                    {
                                                        exprCounter++;
                                                        continue;
                                                    }
                                                    else
                                                    {
                                                        var enLambda = (SyntaxTree.function_lambda_definition)en;
                                                        LambdaHelper.InferTypesFromVarStmt(ffn.parameters[exprCounter].type, enLambda, this);
                                                        enLambda.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing;
                                                        exprs[exprCounter] = convert_strong(en);
                                                        enLambda.lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                                        exprCounter++;
                                                    }
                                                }
                                            }
                                            catch (SeveralFunctionsCanBeCalled sf)
                                            {
                                                spf = sf.set_of_possible_functions; // Возможны несколько перегруженных версий - надо выводить дальше в надежде что какие-то уйдут и останется одна
                                            }

                                            Exception lastmultex = null;
                                            if (spf != null) // пытаемся инстанцировать одну за другой и ошибки гасим try
                                            {   // exprs - глобальная, поэтому надо копировать
                                                int spfnum = -1; // первый номер правильно инстанцированной. Если потом встретился второй, то тоже ошибка
                                                                 // SSM 4.08.15. Сейчас меняю эту логику. Если будет много кандидатов, но ровно один с совпадающим типом возвращаемого значения, то его и надо выбирать.
                                                                 // не забыть, что аналогичный код есть в create_constructor_call!!!!!!!
                                                int GoodVersionsCount = 0;
                                                int GoodVersionsCountWithSameResType = 0;
                                                for (int i = 0; i < spf.Count; i++) // цикл по версиям
                                                {
                                                    function_node fnn = spf[i];
                                                    try
                                                    {
                                                        int exprCounter = 0;
                                                        if (skip_first_parameter)
                                                        {
                                                            exprCounter++;
                                                        }

                                                        expressions_list exprs1 = new expressions_list();
                                                        exprs1.AddRange(exprs); // сделали копию

                                                        foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                                        {
                                                            if (!(en is SyntaxTree.function_lambda_definition))
                                                            {
                                                                exprCounter++;
                                                                continue;
                                                            }
                                                            else
                                                            {
                                                                var fld = en as SyntaxTree.function_lambda_definition;

                                                                var lambdaName = fld.lambda_name;                           //lroman Сохранять имя необходимо
                                                                var fl = fld.lambda_visit_mode;

                                                                // запомнили типы параметров лямбды - SSM
                                                                object[] realparamstype = new object[fld.formal_parameters.params_list.Count]; // здесь хранятся выведенные типы лямбд или null если типы явно заданы
                                                                for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                                {
                                                                    var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                                    if (laminftypeK == null)
                                                                        realparamstype[k] = null;
                                                                    else realparamstype[k] = laminftypeK.real_type;
                                                                }

                                                                // запоминаем реальный тип возвращаемого значения если он не указан явно (это должен быть any_type или null если он указан явно) - он может измениться при следующем вызове, поэтому мы его восстановим
                                                                var restype = fld.return_type as SyntaxTree.lambda_inferred_type;
                                                                object realrestype = null;
                                                                if (restype != null)
                                                                    realrestype = restype.real_type;
                                                                LambdaHelper.InferTypesFromVarStmt(fnn.parameters[exprCounter].type, fld, this);
                                                                fld.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing; //lroman
                                                                fld.lambda_name = LambdaHelper.GetAuxiliaryLambdaName(lambdaName); // поправляю имя. Думаю, назад возвращать не надо. ПРОВЕРИТЬ!

                                                                //contextChanger.SaveContextAndUpToNearestDefSect();
                                                                try
                                                                {
                                                                    exprs1[exprCounter] = convert_strong(en);

                                                                    type_node resexprtype = fld.RealSemTypeOfResExpr as type_node;
                                                                    type_node resformaltype = fld.RealSemTypeOfResult as type_node;
                                                                    var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                                    if (bbb)
                                                                    {
                                                                        GoodVersionsCountWithSameResType += 1;
                                                                        spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                                    }

                                                                    /*compiled_type_node tt;
                                                                    tt = fnn.parameters[exprCounter].type as compiled_type_node;
                                                                    if (tt != null && tt.compiled_type.FullName.ToLower().StartsWith("system.func"))
                                                                    {
                                                                        resformaltype = tt.instance_params[tt.instance_params.Count - 1]; // Последний параметр в записи Func<T,T1,...TN> - тип возвращаемого значения
                                                                        var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                                        if (bbb)
                                                                        {
                                                                            GoodVersionsCountWithSameResType += 1;
                                                                            spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                                        }
                                                                    }*/
                                                                }
                                                                catch
                                                                {
                                                                    throw;
                                                                }
                                                                finally
                                                                {
                                                                    LambdaHelper.RemoveLambdaInfoFromCompilationContext(context, en as function_lambda_definition);
                                                                    // восстанавливаем сохраненный тип возвращаемого значения
                                                                    if (restype != null)
                                                                        restype.real_type = realrestype;
                                                                    // восстанавливаем сохраненные типы параметров лямбды, которые не были заданы явно
                                                                    for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                                    {
                                                                        var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                                        if (laminftypeK != null)
                                                                            laminftypeK.real_type = realparamstype[k];
                                                                    }

                                                                    fld.lambda_name = lambdaName; //lroman Восстанавливаем имена
                                                                    fld.lambda_visit_mode = fl;
                                                                }

                                                                //contextChanger.RestoreCurrentContext();
                                                                exprCounter++;
                                                            }
                                                        }
                                                        /*if (spfnum >= 0) // два удачных инстанцирования - плохо. Может, одно - с более близким типом возвращаемого значения, тогда это плохо - надо доделать, но пока так
                                                        {
                                                            spfnum = -2;
                                                            break;
                                                        }*/

                                                        if (GoodVersionsCountWithSameResType == 0)
                                                            spfnum = i; // здесь запоминаем индекс только если нет подошедших, совпадающих по типу возвращаемого значения
                                                        GoodVersionsCount += 1;
                                                        for (int j = 0; j < exprs.Count; j++) // копируем назад если всё хорошо
                                                            exprs[j] = exprs1[j];
                                                    }
                                                    catch (Exception e)
                                                    {
                                                        // если сюда попали, значит, не вывели типы в лямбде и надо эту инстанцию пропускать
                                                        //contextChanger.RestoreCurrentContext();
                                                        lastmultex = e;
                                                    }
                                                } // конец цикла по версиям
                                                if (GoodVersionsCount > 1 && GoodVersionsCountWithSameResType != 1) // подошло много, но не было ровно одной с совпадающим типом возвращаемого значения
                                                    throw new SeveralFunctionsCanBeCalled(subloc, spf);
                                                if (GoodVersionsCount == 0) // было много, но ни одна не подошла из-за лямбд
                                                {
                                                    throw lastmultex;
                                                    //throw new NoFunctionWithSameArguments(subloc2, false);
                                                }

                                                int kk = 0;
                                                if (skip_first_parameter)
                                                    kk++;
                                                foreach (SyntaxTree.expression en in _method_call.parameters.expressions) //lroman окончательно подставить типы в лямбды
                                                {
                                                    if (!(en is SyntaxTree.function_lambda_definition))
                                                    {
                                                        kk++;
                                                        continue;
                                                    }
                                                    else
                                                    {
                                                        LambdaHelper.InferTypesFromVarStmt(spf[spfnum].parameters[kk].type, en as SyntaxTree.function_lambda_definition, this);
                                                        exprs[kk] = convert_strong(en);
                                                        kk++;
                                                    }
                                                }
                                            }
                                            // SSM 21.05.14 end
                                            LambdaHelper.processingLambdaParametersForTypeInference--;
                                        }
                                        //lroman//
                                        #endregion

                                        function_node fn = null;
                                        if (!skip_first_parameter || si.Next == null)
                                            fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                        else
                                        {
                                            try
                                            {
                                                ThrowCompilationError = false;
                                                fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                                if (fn == null && skip_first_parameter)
                                                {
                                                    if (si.Next == null)
                                                    {
                                                        ThrowCompilationError = true;
                                                        throw LastError();
                                                    }
                                                    RemoveLastError();
                                                    skip_first_parameter = false;
                                                    si = tmp_si;
                                                    exprs.remove_at(0);
                                                    fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                                    if (fn == null)
                                                    {
                                                        ThrowCompilationError = true;
                                                        throw LastError();
                                                    }
//                                                    else
//                                                        RemoveLastError(); // ошибка уже убрана чуть выше
                                                }
                                            }
                                            catch (Exception ex)
                                            {
                                                ThrowCompilationError = true;
                                                if (skip_first_parameter)
                                                {
                                                    si = tmp_si;
                                                    exprs.remove_at(0);
                                                    fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                                }
                                                else
                                                    throw ex;
                                            }
                                            ThrowCompilationError = true;
                                        }
                                        SemanticTree.IGenericInstance igi = fn as SemanticTree.IGenericInstance;
                                        if (igi != null)
                                        {
                                            //проверяем на соответствие ограничителям
                                            int num_err;
                                            //CompilationErrorWithLocation err = generic_parameter_eliminations.check_type_list(
                                        }
                                        base_function_call bfc = create_not_static_method_call(fn, exp, get_location(id_right), proc_wait);
                                        bfc.parameters.AddRange(exprs);
                                        subexpr1 = bfc;
                                    }

                                    switch (mot)
                                    {
                                        case motivation.expression_evaluation:
                                            {
                                                return_value(subexpr1);
                                                return;
                                            }
                                        case motivation.semantic_node_reciving:
                                            {
                                                return_semantic_value(subexpr1);
                                                return;
                                            }
                                        default:
                                            {
                                                AddError(subexpr1.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                                return;
                                            }
                                    }

                                }
                            case general_node_type.namespace_node:
                                {
                                    namespace_node nsn = (namespace_node)sn;
                                    if (templ_args_count != 0)
                                    {
                                        //Ищем generics
                                        si = context.find(id_right.name + compiler_string_consts.generic_params_infix + templ_args_count.ToString());
                                        if (si != null)
                                        {
                                            si = new SymbolInfo(get_generic_instance(si, iwt.template_params.params_list));
                                            iwt = null;
                                        }
                                    }
                                    if (si == null)
                                    {
                                        SyntaxTree.operator_name_ident oni_right = id_right as SyntaxTree.operator_name_ident;
                                        if (oni_right != null)
                                        {
                                            si = nsn.find(name_reflector.get_name(oni_right.operator_type));
                                        }
                                        else
                                        {
                                            si = nsn.find(id_right.name);
                                            if (templ_args_count != 0)
                                            {
                                                SymbolInfo conv = ConvertTypeToInstance(si, iwt.template_params.params_list, get_location(id_right));
                                                if (conv != null)
                                                {
                                                    si = conv;
                                                    iwt = null;
                                                }
                                            }
                                        }
                                    }
                                    id = id_right;
                                    break;
                                }
                            case general_node_type.unit_node:
                                {
                                    unit_node un = (unit_node)sn;
                                    SyntaxTree.operator_name_ident oni_right = id_right as SyntaxTree.operator_name_ident;
                                    if (oni_right != null)
                                    {
                                        si = un.find_only_in_namespace(name_reflector.get_name(oni_right.operator_type));
                                    }
                                    else
                                    {
                                        si = un.find_only_in_namespace(id_right.name);
                                    }
                                    id = id_right;
                                    break;
                                }
                            case general_node_type.type_node:
                                {
                                    type_node tn = (type_node)sn;
                                    /*if (tn == SystemLibrary.SystemLibrary.void_type)
                                    {
                                        throw new VoidNotValid(get_location(id_right));
                                    }*/
                                    check_for_type_allowed(tn,get_location(id_right));
                                    SyntaxTree.operator_name_ident oni_right = id_right as SyntaxTree.operator_name_ident;
                                    if (oni_right != null)
                                    {
                                        si = tn.find_in_type(name_reflector.get_name(oni_right.operator_type), context.CurrentScope);
                                    }
                                    else
                                    {
                                        si = tn.find_in_type(id_right.name, context.CurrentScope);//CurrentScope
                                        delete_inherited_constructors(ref si, tn);
                                        delete_extension_methods(ref si, tn); // SSM 2.2.2016 Пока временно закомментировал - в старом коде этого не было. Из-за этого не работает System.Linq.Enumerable.Select
                                    }

                                    //definition_node ddn2=check_name_node_type(id_right.name,si,get_location(id_right),
                                    //    general_node_type.function_node);

                                    expression_node exp = null;
                                    location subloc = get_location(id_right);

                                    if (si == null)
                                    {
                                        AddError( new UndefinedNameReference(id_right.name, subloc));
                                    }

                                    if (si.sym_info.general_node_type != general_node_type.function_node)
                                    {
                                        if (si.sym_info.general_node_type == general_node_type.type_node)
                                        {
                                            to_type = ((type_node)(si.sym_info));
                                        }
                                        else
                                        {
                                            dot_node_as_type_ident(tn, id_right, motivation.expression_evaluation);
                                            exp = ret.get_expression();
                                            internal_interface ii = exp.type.get_internal_interface(internal_interface_kind.delegate_interface);
                                            if (ii == null)
                                            {
                                                AddError(subloc, "EXPECTED_DELEGATE");
                                            }
                                            delegate_internal_interface dii = ii as delegate_internal_interface;
                                            si = new SymbolInfo(dii.invoke_method);
                                        }
                                    }

                                    if (to_type != null)
                                    {
                                        if ((_method_call.parameters == null) || (_method_call.parameters.expressions.Count != 1))
                                        {
                                            AddError(get_location(_method_call), "ONLY_ONE_PARAMETER_OF_TYPE_CONVERSION_ALLOWED" );
                                        }
                                    }

                                    if (_method_call.parameters != null)
                                    {
                                        foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                        {
                                            #region Отмечаем флаг в лямбдах, говорящий о том, что в первый раз будем их "обходить" для вывода типов
                                            //lroman//
                                            if (en is SyntaxTree.function_lambda_definition)
                                            {
                                                lambdas_are_in_parameters = true;
                                                ((SyntaxTree.function_lambda_definition)en).lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                            }
                                            //lroman//
                                            #endregion
                                            exprs.AddElement(convert_strong(en));
                                        }
                                    }

                                    expression_node subexpr2 = null;

                                    if (to_type != null)
                                    {
                                        subexpr2 = convertion_data_and_alghoritms.explicit_convert_type(exprs[0], to_type);
                                    }
                                    else
                                    {
                                        if (iwt != null)
                                        {
                                            si = get_generic_functions(si, true, subloc);
                                            si = get_function_instances(si, iwt.template_params.params_list, id_right.name, subloc, si.Next == null);
                                        }
                                        #region Если встретились лямбды в фактических параметрах, то выбираем нужную функцию из перегруженных, выводим типы, отмечаем флаг в лямбдах, говорящий о том, что мы их реально обходим
                                        //lroman//
                                        if (lambdas_are_in_parameters)
                                        {
                                            LambdaHelper.processingLambdaParametersForTypeInference++;
                                            // SSM 21.05.14 - попытка обработать перегруженные функции с параметрами-лямбдами с различными возвращаемыми значениями
                                            function_node_list spf = null;
                                            try
                                            {
                                                function_node ffn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                                int exprCounter = 0;
                                                if (skip_first_parameter)
                                                {
                                                    exprCounter++;
                                                }
                                                foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                                {
                                                    if (!(en is SyntaxTree.function_lambda_definition))
                                                    {
                                                        exprCounter++;
                                                        continue;
                                                    }
                                                    else
                                                    {
                                                        var enLambda = (SyntaxTree.function_lambda_definition)en;
                                                        LambdaHelper.InferTypesFromVarStmt(ffn.parameters[exprCounter].type, enLambda, this);
                                                        enLambda.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing;
                                                        exprs[exprCounter] = convert_strong(en);
                                                        enLambda.lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                                        exprCounter++;
                                                    }
                                                }
                                            }
                                            catch (SeveralFunctionsCanBeCalled sf)
                                            {
                                                spf = sf.set_of_possible_functions; // Возможны несколько перегруженных версий - надо выводить дальше в надежде что какие-то уйдут и останется одна
                                            }

                                            Exception lastmultex = null;
                                            if (spf != null) // пытаемся инстанцировать одну за другой и ошибки гасим try
                                            {   // exprs - глобальная, поэтому надо копировать
                                                int spfnum = -1; // первый номер правильно инстанцированной. Если потом встретился второй, то тоже ошибка
                                                                 // SSM 4.08.15. Сейчас меняю эту логику. Если будет много кандидатов, но ровно один с совпадающим типом возвращаемого значения, то его и надо выбирать.
                                                                 // не забыть, что аналогичный код есть в create_constructor_call!!!!!!!
                                                int GoodVersionsCount = 0;
                                                int GoodVersionsCountWithSameResType = 0;
                                                for (int i = 0; i < spf.Count; i++) // цикл по версиям
                                                {
                                                    function_node fnn = spf[i];
                                                    try
                                                    {
                                                        int exprCounter = 0;
                                                        if (skip_first_parameter)
                                                        {
                                                            exprCounter++;
                                                        }

                                                        expressions_list exprs1 = new expressions_list();
                                                        exprs1.AddRange(exprs); // сделали копию

                                                        foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                                        {
                                                            if (!(en is SyntaxTree.function_lambda_definition))
                                                            {
                                                                exprCounter++;
                                                                continue;
                                                            }
                                                            else
                                                            {
                                                                var fld = en as SyntaxTree.function_lambda_definition;

                                                                var lambdaName = fld.lambda_name;                           //lroman Сохранять имя необходимо
                                                                var fl = fld.lambda_visit_mode;

                                                                // запомнили типы параметров лямбды - SSM
                                                                object[] realparamstype = new object[fld.formal_parameters.params_list.Count]; // здесь хранятся выведенные типы лямбд или null если типы явно заданы
                                                                for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                                {
                                                                    var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                                    if (laminftypeK == null)
                                                                        realparamstype[k] = null;
                                                                    else realparamstype[k] = laminftypeK.real_type;
                                                                }

                                                                // запоминаем реальный тип возвращаемого значения если он не указан явно (это должен быть any_type или null если он указан явно) - он может измениться при следующем вызове, поэтому мы его восстановим
                                                                var restype = fld.return_type as SyntaxTree.lambda_inferred_type;
                                                                object realrestype = null;
                                                                if (restype != null)
                                                                    realrestype = restype.real_type;
                                                                LambdaHelper.InferTypesFromVarStmt(fnn.parameters[exprCounter].type, fld, this);
                                                                fld.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing; //lroman
                                                                fld.lambda_name = LambdaHelper.GetAuxiliaryLambdaName(lambdaName); // поправляю имя. Думаю, назад возвращать не надо. ПРОВЕРИТЬ!

                                                                //contextChanger.SaveContextAndUpToNearestDefSect();
                                                                try
                                                                {
                                                                    exprs1[exprCounter] = convert_strong(en);

                                                                    type_node resexprtype = fld.RealSemTypeOfResExpr as type_node;
                                                                    type_node resformaltype = fld.RealSemTypeOfResult as type_node;
                                                                    var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                                    if (bbb)
                                                                    {
                                                                        GoodVersionsCountWithSameResType += 1;
                                                                        spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                                    }

                                                                    /*compiled_type_node tt;
                                                                    tt = fnn.parameters[exprCounter].type as compiled_type_node;
                                                                    if (tt != null && tt.compiled_type.FullName.ToLower().StartsWith("system.func"))
                                                                    {
                                                                        resformaltype = tt.instance_params[tt.instance_params.Count - 1]; // Последний параметр в записи Func<T,T1,...TN> - тип возвращаемого значения
                                                                        var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                                        if (bbb)
                                                                        {
                                                                            GoodVersionsCountWithSameResType += 1;
                                                                            spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                                        }
                                                                    }*/
                                                                }
                                                                catch
                                                                {
                                                                    throw;
                                                                }
                                                                finally
                                                                {
                                                                    LambdaHelper.RemoveLambdaInfoFromCompilationContext(context, en as function_lambda_definition);
                                                                    // восстанавливаем сохраненный тип возвращаемого значения
                                                                    if (restype != null)
                                                                        restype.real_type = realrestype;
                                                                    // восстанавливаем сохраненные типы параметров лямбды, которые не были заданы явно
                                                                    for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                                    {
                                                                        var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                                        if (laminftypeK != null)
                                                                            laminftypeK.real_type = realparamstype[k];
                                                                    }

                                                                    fld.lambda_name = lambdaName; //lroman Восстанавливаем имена
                                                                    fld.lambda_visit_mode = fl;
                                                                }

                                                                //contextChanger.RestoreCurrentContext();
                                                                exprCounter++;
                                                            }
                                                        }
                                                        /*if (spfnum >= 0) // два удачных инстанцирования - плохо. Может, одно - с более близким типом возвращаемого значения, тогда это плохо - надо доделать, но пока так
                                                        {
                                                            spfnum = -2;
                                                            break;
                                                        }*/

                                                        if (GoodVersionsCountWithSameResType == 0)
                                                            spfnum = i; // здесь запоминаем индекс только если нет подошедших, совпадающих по типу возвращаемого значения
                                                        GoodVersionsCount += 1;
                                                        for (int j = 0; j < exprs.Count; j++) // копируем назад если всё хорошо
                                                            exprs[j] = exprs1[j];
                                                    }
                                                    catch (Exception e)
                                                    {
                                                        // если сюда попали, значит, не вывели типы в лямбде и надо эту инстанцию пропускать
                                                        //contextChanger.RestoreCurrentContext();
                                                        lastmultex = e;
                                                    }
                                                } // конец цикла по версиям
                                                if (GoodVersionsCount > 1 && GoodVersionsCountWithSameResType != 1) // подошло много, но не было ровно одной с совпадающим типом возвращаемого значения
                                                    throw new SeveralFunctionsCanBeCalled(subloc, spf);
                                                if (GoodVersionsCount == 0) // было много, но ни одна не подошла из-за лямбд
                                                {
                                                    throw lastmultex;
                                                    //throw new NoFunctionWithSameArguments(subloc2, false);
                                                }

                                                int kk = 0;
                                                if (skip_first_parameter)
                                                    kk++;
                                                foreach (SyntaxTree.expression en in _method_call.parameters.expressions) //lroman окончательно подставить типы в лямбды
                                                {
                                                    if (!(en is SyntaxTree.function_lambda_definition))
                                                    {
                                                        kk++;
                                                        continue;
                                                    }
                                                    else
                                                    {
                                                        LambdaHelper.InferTypesFromVarStmt(spf[spfnum].parameters[kk].type, en as SyntaxTree.function_lambda_definition, this);
                                                        exprs[kk] = convert_strong(en);
                                                        kk++;
                                                    }
                                                }
                                            }
                                            // SSM 21.05.14 end
                                            LambdaHelper.processingLambdaParametersForTypeInference--;
                                        }
                                        //lroman//
                                        #endregion

                                        function_node fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                        if (!debug && fn == SystemLibrary.SystemLibrary.assert_method)
                                        {
//                                        	return_value(new empty_statement(null));
//                                        	return;
                                        }
                                        /*if ((proc_wait==false)&&(fn.return_value_type==null))
                                        {
                                            throw new FunctionExpectedProcedureMeet(fn,get_location(id_right));
                                        }*/

                                        base_function_call bfc2 = null;
                                        if (exp == null)
                                        {
                                            bfc2 = create_static_method_call(fn, subloc, tn, proc_wait);
                                        }
                                        else
                                        {
                                            bfc2 = create_not_static_method_call(fn, exp, subloc, proc_wait);
                                        }
                                        bfc2.parameters.AddRange(exprs);
                                        subexpr2 = bfc2;
                                    }

                                    switch (mot)
                                    {
                                        case motivation.expression_evaluation:
                                            {
                                                return_value(subexpr2);
                                                return;
                                            }
                                        case motivation.semantic_node_reciving:
                                            {
                                                return_semantic_value(subexpr2);
                                                return;
                                            }
                                        default:
                                            {
                                                AddError(subexpr2.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                                return;
                                            }
                                    }
                                }
                        }
                    }
                    else
                    {
                        SyntaxTree.expression expr = deref_value as SyntaxTree.expression;
                        if (expr != null)
                        {
                            //throw new CompilerInternalError("Not supported");
                            expression_node exp_int = convert_strong(expr);
                            location sloc = get_location(expr);
                            internal_interface ii = exp_int.type.get_internal_interface(internal_interface_kind.delegate_interface);
                            if (ii == null)
                            {
                                AddError(sloc, "EXPECTED_DELEGATE");
                            }
                            delegate_internal_interface dii = (delegate_internal_interface)ii;
                            si = new SymbolInfo(dii.invoke_method);

                            if (_method_call.parameters != null)
                            {
                                foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                {
                                    #region Отмечаем флаг в лямбдах, говорящий о том, что в первый раз будем их "обходить" для вывода типов
                                    //lroman//
                                    if (en is SyntaxTree.function_lambda_definition)
                                    {
                                        lambdas_are_in_parameters = true;
                                        ((SyntaxTree.function_lambda_definition)en).lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                    }
                                    //lroman//
                                    #endregion
                                    exprs.AddElement(convert_strong(en));
                                }
                            }
                            location subloc = sloc;
                            #region Если встретились лямбды в фактических параметрах, то выбираем нужную функцию из перегруженных, выводим типы, отмечаем флаг в лямбдах, говорящий о том, что мы их реально обходим
                            //lroman//
                            if (lambdas_are_in_parameters)
                            {
                                LambdaHelper.processingLambdaParametersForTypeInference++;
                                // SSM 21.05.14 - попытка обработать перегруженные функции с параметрами-лямбдами с различными возвращаемыми значениями
                                function_node_list spf = null;
                                try
                                {
                                    function_node ffn = convertion_data_and_alghoritms.select_function(exprs, si, subloc, syntax_nodes_parameters);
                                    int exprCounter = 0;
                                    
                                    foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                    {
                                        if (!(en is SyntaxTree.function_lambda_definition))
                                        {
                                            exprCounter++;
                                            continue;
                                        }
                                        else
                                        {
                                            var enLambda = (SyntaxTree.function_lambda_definition)en;
                                            LambdaHelper.InferTypesFromVarStmt(ffn.parameters[exprCounter].type, enLambda, this);
                                            enLambda.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing;
                                            exprs[exprCounter] = convert_strong(en);
                                            enLambda.lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                            exprCounter++;
                                        }
                                    }
                                }
                                catch (SeveralFunctionsCanBeCalled sf)
                                {
                                    spf = sf.set_of_possible_functions; // Возможны несколько перегруженных версий - надо выводить дальше в надежде что какие-то уйдут и останется одна
                                }

                                Exception lastmultex = null;
                                if (spf != null) // пытаемся инстанцировать одну за другой и ошибки гасим try
                                {   // exprs - глобальная, поэтому надо копировать
                                    int spfnum = -1; // первый номер правильно инстанцированной. Если потом встретился второй, то тоже ошибка
                                                     // SSM 4.08.15. Сейчас меняю эту логику. Если будет много кандидатов, но ровно один с совпадающим типом возвращаемого значения, то его и надо выбирать.
                                                     // не забыть, что аналогичный код есть в create_constructor_call!!!!!!!
                                    int GoodVersionsCount = 0;
                                    int GoodVersionsCountWithSameResType = 0;
                                    for (int i = 0; i < spf.Count; i++) // цикл по версиям
                                    {
                                        function_node fnn = spf[i];
                                        try
                                        {
                                            int exprCounter = 0;
                                            

                                            expressions_list exprs1 = new expressions_list();
                                            exprs1.AddRange(exprs); // сделали копию

                                            foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                            {
                                                if (!(en is SyntaxTree.function_lambda_definition))
                                                {
                                                    exprCounter++;
                                                    continue;
                                                }
                                                else
                                                {
                                                    var fld = en as SyntaxTree.function_lambda_definition;

                                                    var lambdaName = fld.lambda_name;                           //lroman Сохранять имя необходимо
                                                    var fl = fld.lambda_visit_mode;

                                                    // запомнили типы параметров лямбды - SSM
                                                    object[] realparamstype = new object[fld.formal_parameters.params_list.Count]; // здесь хранятся выведенные типы лямбд или null если типы явно заданы
                                                    for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                    {
                                                        var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                        if (laminftypeK == null)
                                                            realparamstype[k] = null;
                                                        else realparamstype[k] = laminftypeK.real_type;
                                                    }

                                                    // запоминаем реальный тип возвращаемого значения если он не указан явно (это должен быть any_type или null если он указан явно) - он может измениться при следующем вызове, поэтому мы его восстановим
                                                    var restype = fld.return_type as SyntaxTree.lambda_inferred_type;
                                                    object realrestype = null;
                                                    if (restype != null)
                                                        realrestype = restype.real_type;
                                                    LambdaHelper.InferTypesFromVarStmt(fnn.parameters[exprCounter].type, fld, this);
                                                    fld.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing; //lroman
                                                    fld.lambda_name = LambdaHelper.GetAuxiliaryLambdaName(lambdaName); // поправляю имя. Думаю, назад возвращать не надо. ПРОВЕРИТЬ!

                                                    //contextChanger.SaveContextAndUpToNearestDefSect();
                                                    try
                                                    {
                                                        exprs1[exprCounter] = convert_strong(en);

                                                        type_node resexprtype = fld.RealSemTypeOfResExpr as type_node;
                                                        type_node resformaltype = fld.RealSemTypeOfResult as type_node;
                                                        var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                        if (bbb)
                                                        {
                                                            GoodVersionsCountWithSameResType += 1;
                                                            spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                        }

                                                        /*compiled_type_node tt;
                                                        tt = fnn.parameters[exprCounter].type as compiled_type_node;
                                                        if (tt != null && tt.compiled_type.FullName.ToLower().StartsWith("system.func"))
                                                        {
                                                            resformaltype = tt.instance_params[tt.instance_params.Count - 1]; // Последний параметр в записи Func<T,T1,...TN> - тип возвращаемого значения
                                                            var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                            if (bbb)
                                                            {
                                                                GoodVersionsCountWithSameResType += 1;
                                                                spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                            }
                                                        }*/
                                                    }
                                                    catch
                                                    {
                                                        throw;
                                                    }
                                                    finally
                                                    {
                                                        LambdaHelper.RemoveLambdaInfoFromCompilationContext(context, en as function_lambda_definition);
                                                        // восстанавливаем сохраненный тип возвращаемого значения
                                                        if (restype != null)
                                                            restype.real_type = realrestype;
                                                        // восстанавливаем сохраненные типы параметров лямбды, которые не были заданы явно
                                                        for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                        {
                                                            var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                            if (laminftypeK != null)
                                                                laminftypeK.real_type = realparamstype[k];
                                                        }

                                                        fld.lambda_name = lambdaName; //lroman Восстанавливаем имена
                                                        fld.lambda_visit_mode = fl;
                                                    }

                                                    //contextChanger.RestoreCurrentContext();
                                                    exprCounter++;
                                                }
                                            }
                                            /*if (spfnum >= 0) // два удачных инстанцирования - плохо. Может, одно - с более близким типом возвращаемого значения, тогда это плохо - надо доделать, но пока так
                                            {
                                                spfnum = -2;
                                                break;
                                            }*/

                                            if (GoodVersionsCountWithSameResType == 0)
                                                spfnum = i; // здесь запоминаем индекс только если нет подошедших, совпадающих по типу возвращаемого значения
                                            GoodVersionsCount += 1;
                                            for (int j = 0; j < exprs.Count; j++) // копируем назад если всё хорошо
                                                exprs[j] = exprs1[j];
                                        }
                                        catch (Exception e)
                                        {
                                            // если сюда попали, значит, не вывели типы в лямбде и надо эту инстанцию пропускать
                                            //contextChanger.RestoreCurrentContext();
                                            lastmultex = e;
                                        }
                                    } // конец цикла по версиям
                                    if (GoodVersionsCount > 1 && GoodVersionsCountWithSameResType != 1) // подошло много, но не было ровно одной с совпадающим типом возвращаемого значения
                                        throw new SeveralFunctionsCanBeCalled(subloc, spf);
                                    if (GoodVersionsCount == 0) // было много, но ни одна не подошла из-за лямбд
                                    {
                                        throw lastmultex;
                                        //throw new NoFunctionWithSameArguments(subloc2, false);
                                    }

                                    int kk = 0;
                                    
                                    foreach (SyntaxTree.expression en in _method_call.parameters.expressions) //lroman окончательно подставить типы в лямбды
                                    {
                                        if (!(en is SyntaxTree.function_lambda_definition))
                                        {
                                            kk++;
                                            continue;
                                        }
                                        else
                                        {
                                            LambdaHelper.InferTypesFromVarStmt(spf[spfnum].parameters[kk].type, en as SyntaxTree.function_lambda_definition, this);
                                            exprs[kk] = convert_strong(en);
                                            kk++;
                                        }
                                    }
                                }
                                // SSM 21.05.14 end
                                LambdaHelper.processingLambdaParametersForTypeInference--;
                            }
                            //lroman//
                            #endregion

                            function_node del_func = convertion_data_and_alghoritms.select_function(exprs, si, sloc, syntax_nodes_parameters);
                            base_function_call bbfc = create_not_static_method_call(del_func, exp_int, sloc, proc_wait);
                            bbfc.parameters.AddRange(exprs);

                            switch (mot)
                            {
                                case motivation.expression_evaluation:
                                    {
                                        return_value(bbfc);
                                        return;
                                    }
                                case motivation.semantic_node_reciving:
                                    {
                                        return_semantic_value(bbfc);
                                        return;
                                    }
                                default:
                                    {
                                        AddError(bbfc.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                        return;
                                    }
                            }
                        }
                        else
                        {
                            throw new CompilerInternalError("Unexpected method name kind");
                        }
                    }
                }
            }

            //definition_node dn=check_name_node_type(id.name,si,get_location(_method_call),general_node_type.function_node);

            expression_node exp2 = null;
            location subloc2 = get_location(id);

            List<TreeConverter.SymbolInfo> sibak = new List<TreeConverter.SymbolInfo>();
            TreeConverter.SymbolInfo ssi=si;
            while (ssi != null)
            {
                ssi = ssi.Next;
                sibak.Add(ssi);
            }


            if (si == null)
            {
                AddError(new UndefinedNameReference(id.name, subloc2));
            }
			is_format_allowed = false;
            if (SystemUnitAssigned)
                if (SystemLibrary.SystemLibInitializer.read_procedure.Equal(si) || SystemLibrary.SystemLibInitializer.readln_procedure.Equal(si))
                {
                    
            		expression_node bfcint = make_read_call(si, _method_call.parameters, subloc2);
                    if (!proc_wait)
                        AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name);
                    switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
                }
            else if (SystemLibrary.SystemLibInitializer.write_procedure.Equal(si) || SystemLibrary.SystemLibInitializer.writeln_procedure.Equal(si) || SystemLibrary.SystemLibInitializer.StrProcedure.Equal(si))
            {
            	is_format_allowed = true;
            }
            else if (SystemLibrary.SystemLibInitializer.ArrayCopyFunction.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 1)
            	{
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		if (param0.type.type_special_kind == SemanticTree.type_special_kind.array_kind)
            		{
            			location loc = get_location(_method_call);
            			expression_node en = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.ArrayCopyFunction.sym_info as function_node,loc,param0);
                    	function_node fn = convertion_data_and_alghoritms.get_empty_conversion(en.type, param0.type, false);
                    	en = convertion_data_and_alghoritms.create_simple_function_call(fn, loc, en);
                    	return_value(en);
                    	return;
            		}
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.SetLengthProcedure.Equal(si) || SystemLibrary.SystemLibrary.resize_func == si.sym_info as function_node)
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count >= 2)
            	{
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		if (!param0.is_addressed)
            			AddError(new ThisExpressionCanNotBePassedAsVarParameter(param0));
            		if (param0.type.type_special_kind == SemanticTree.type_special_kind.short_string)
            		{
            			expression_node param1 = convert_strong(_method_call.parameters.expressions[1]);
            			param1 = convertion_data_and_alghoritms.convert_type(param1,SystemLibrary.SystemLibrary.integer_type);
                        base_function_call cnfn = null; 
                        if (SystemLibrary.SystemLibInitializer.SetLengthForShortStringProcedure.sym_info is common_namespace_function_node)
                            cnfn = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.SetLengthForShortStringProcedure.sym_info as common_namespace_function_node, get_location(_method_call));
            			else
                            cnfn = new compiled_static_method_call(SystemLibrary.SystemLibInitializer.SetLengthForShortStringProcedure.sym_info as compiled_function_node, get_location(_method_call));
                        cnfn.parameters.AddElement(param0);
            			cnfn.parameters.AddElement(param1);
            			cnfn.parameters.AddElement(new int_const_node((param0.type as short_string_type_node).Length,null));
            			switch (mot)
                    	{
                        	case motivation.expression_evaluation:
                            {
                                return_value(cnfn);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(cnfn);
                                return;
                            }
                        	default:
                            {
                                AddError(cnfn.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    	}
            		}
            		else if (param0.type.type_special_kind == SemanticTree.type_special_kind.array_kind)
            		{
            			int rank = 1;
            			if (param0.type is compiled_type_node)
            				rank = (param0.type as compiled_type_node).rank;
            			else if (param0.type is common_type_node)
            				rank = (param0.type as common_type_node).rank;
            			if (_method_call.parameters.expressions.Count-1 != rank)
            				AddError(get_location(_method_call), "{0}_PARAMETERS_EXPECTED", rank+1);
            			if (rank > 1)
            			{
            				type_node tn = param0.type.element_type;
            				location loc = get_location(_method_call);
            				typeof_operator to = new typeof_operator(tn, loc);
                    		List<expression_node> lst = new List<expression_node>();
                    		//размер
                    		for (int i=1; i<_method_call.parameters.expressions.Count; i++)
                    		{
                    			expression_node expr = convert_strong(_method_call.parameters.expressions[i]);;
                    			expr = convertion_data_and_alghoritms.convert_type(expr, SystemLibrary.SystemLibrary.integer_type);
                    			if (expr is int_const_node && (expr as int_const_node).constant_value < 0)
                    				AddError(expr.location,"NEGATIVE_ARRAY_LENGTH_({0})_NOT_ALLOWED", (expr as int_const_node).constant_value);
                    			lst.Add(expr);
                    		}
                    		//это вызов спецфункции
                    		
                    		expression_node retv = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.NewArrayProcedureDecl, loc, to, new int_const_node(lst.Count,loc));
                    		common_namespace_function_call cnfc = retv as common_namespace_function_call;
                    		foreach (expression_node e in lst)
                    			cnfc.parameters.AddElement(e);
                    		expression_node en = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.CopyWithSizeFunction.sym_info as function_node,loc,param0,cnfc);
                    		function_node fn = convertion_data_and_alghoritms.get_empty_conversion(en.type, retv.type, false);
                    		en = convertion_data_and_alghoritms.create_simple_function_call(fn, loc, en);
                    		basic_function_call bfc = new basic_function_call(tn.find(compiler_string_consts.assign_name).sym_info as basic_function_node,loc,param0,en);
                    		return_value(bfc);
                    		return;
            			}
            		}
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.InsertProcedure.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 3)
            	{
            		//expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		expression_node param1 = convert_strong(_method_call.parameters.expressions[1]);
            		//expression_node param2 = convert_strong(_method_call.parameters.expressions[2]);
            		if (param1.type.type_special_kind == SemanticTree.type_special_kind.short_string)
            		{
            			expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            			expression_node param2 = convert_strong(_method_call.parameters.expressions[2]);
            			param0 = convertion_data_and_alghoritms.convert_type(param0,SystemLibrary.SystemLibrary.string_type);
            			param2 = convertion_data_and_alghoritms.convert_type(param2,SystemLibrary.SystemLibrary.integer_type);
                        base_function_call cnfn = null;
                        if (SystemLibrary.SystemLibInitializer.InsertInShortStringProcedure.sym_info is common_namespace_function_node)
                            cnfn = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.InsertInShortStringProcedure.sym_info as common_namespace_function_node, get_location(_method_call));
            			else
                            cnfn = new compiled_static_method_call(SystemLibrary.SystemLibInitializer.InsertInShortStringProcedure.sym_info as compiled_function_node, get_location(_method_call));
                        cnfn.parameters.AddElement(param0);
            			cnfn.parameters.AddElement(param1);
            			cnfn.parameters.AddElement(param2);
            			cnfn.parameters.AddElement(new int_const_node((param1.type as short_string_type_node).Length,null));
            			switch (mot)
                    	{
                        	case motivation.expression_evaluation:
                            {
                                return_value(cnfn);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(cnfn);
                                return;
                            }
                        	default:
                            {
                                AddError(cnfn.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    	}
            		}
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.DeleteProcedure.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 3)
            	{
            		//expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		//expression_node param2 = convert_strong(_method_call.parameters.expressions[2]);
            		if (param0.type.type_special_kind == SemanticTree.type_special_kind.short_string)
            		{
            			expression_node param1 = convert_strong(_method_call.parameters.expressions[1]);
            			expression_node param2 = convert_strong(_method_call.parameters.expressions[2]);
            			param1 = convertion_data_and_alghoritms.convert_type(param1,SystemLibrary.SystemLibrary.integer_type);
            			param2 = convertion_data_and_alghoritms.convert_type(param2,SystemLibrary.SystemLibrary.integer_type);
                        base_function_call cnfn = null;
                        if (SystemLibrary.SystemLibInitializer.DeleteProcedure.sym_info is common_namespace_function_node) 
                            cnfn = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.DeleteProcedure.sym_info as common_namespace_function_node, get_location(_method_call));
                        else
                            cnfn = new compiled_static_method_call(SystemLibrary.SystemLibInitializer.DeleteProcedure.sym_info as compiled_function_node, get_location(_method_call));
            			cnfn.parameters.AddElement(param0);
            			cnfn.parameters.AddElement(param1);
            			cnfn.parameters.AddElement(param2);
            			switch (mot)
                    	{
                        	case motivation.expression_evaluation:
                            {
                                return_value(cnfn);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(cnfn);
                                return;
                            }
                        	default:
                            {
                                AddError(cnfn.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    	}
            		}
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.IncludeProcedure.Equal(si)
                            || SystemLibrary.SystemLibInitializer.ExcludeProcedure.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 2)
            	{
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		expression_node param1 = convert_strong(_method_call.parameters.expressions[1]);
            		expressions_list args = new expressions_list();
            		args.AddElement(param0);
            		args.AddElement(param1);
            		CheckSpecialFunctionCall(si,args,get_location(_method_call));
                    expression_node en_cnfn = null;
                    if (SystemLibrary.SystemLibInitializer.IncludeProcedure.sym_info is common_namespace_function_node)
                    {
                        common_namespace_function_call cnfn = null;
                        if (SystemLibrary.SystemLibInitializer.IncludeProcedure.Equal(si)) cnfn = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.IncludeProcedure.sym_info as common_namespace_function_node, get_location(_method_call));
                        else cnfn = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.ExcludeProcedure.sym_info as common_namespace_function_node, get_location(_method_call));
                        cnfn.parameters.AddElement(param0);
                        cnfn.parameters.AddElement(param1);
                        en_cnfn = cnfn;
                    }
                    else
                    {
                        compiled_static_method_call cnfn = null;
                        if (SystemLibrary.SystemLibInitializer.IncludeProcedure.Equal(si)) cnfn = new compiled_static_method_call(SystemLibrary.SystemLibInitializer.IncludeProcedure.sym_info as compiled_function_node, get_location(_method_call));
                        else cnfn = new compiled_static_method_call(SystemLibrary.SystemLibInitializer.ExcludeProcedure.sym_info as compiled_function_node, get_location(_method_call));
                        cnfn.parameters.AddElement(param0);
                        cnfn.parameters.AddElement(param1);
                        en_cnfn = cnfn;
                    }
            		switch (mot)
                    {
                        	case motivation.expression_evaluation:
                            {
                                return_value(en_cnfn);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(en_cnfn);
                                return;
                            }
                        	default:
                            {
                                AddError(en_cnfn.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.IncProcedure.Equal(si))
            {
            	expression_node bfcint = make_inc_call(si, _method_call.parameters, subloc2);
            	if (!proc_wait)
                        AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (SystemLibrary.SystemLibInitializer.DecProcedure.Equal(si))
            {
            	expression_node bfcint = make_dec_call(si, _method_call.parameters, subloc2);
            	if (!proc_wait)
                        AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (SystemLibrary.SystemLibInitializer.SuccFunction.Equal(si))
            {
            	expression_node bfcint = make_succ_call(si, _method_call.parameters, subloc2);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (SystemLibrary.SystemLibInitializer.PredFunction.Equal(si))
            {
            	expression_node bfcint = make_pred_call(si, _method_call.parameters, subloc2);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (SystemLibrary.SystemLibInitializer.OrdFunction.Equal(si))
            {
            	expression_node bfcint = make_ord_call(si, _method_call.parameters, subloc2);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (SystemLibrary.SystemLibInitializer.LowFunction.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 1)
            	{
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		if (param0.type.type_special_kind == SemanticTree.type_special_kind.array_wrapper)
            		{
            			bounded_array_interface bai = param0.type.get_internal_interface(internal_interface_kind.bounded_array_interface) as bounded_array_interface;
            			expression_node en = new int_const_node(bai.ordinal_type_interface.ordinal_type_to_int(bai.ordinal_type_interface.lower_value),get_location(_method_call));
            			switch (mot)
                    	{
                        	case motivation.expression_evaluation:
                            {
                                return_value(en);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(en);
                                return;
                            }
                        	default:
                            {
                                AddError(en.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    	}
            		}
            	}
            }
            else if (SystemLibrary.SystemLibInitializer.HighFunction.Equal(si))
            {
            	if (_method_call.parameters != null && _method_call.parameters.expressions.Count == 1)
            	{
            		expression_node param0 = convert_strong(_method_call.parameters.expressions[0]);
            		if (param0.type.type_special_kind == SemanticTree.type_special_kind.array_wrapper)
            		{
            			bounded_array_interface bai = param0.type.get_internal_interface(internal_interface_kind.bounded_array_interface) as bounded_array_interface;
            			expression_node en = new int_const_node(bai.ordinal_type_interface.ordinal_type_to_int(bai.ordinal_type_interface.upper_value),get_location(_method_call));
            			switch (mot)
                    	{
                        	case motivation.expression_evaluation:
                            {
                                return_value(en);
                                return;
                            }
                        	case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(en);
                                return;
                            }
                        	default:
                            {
                                AddError(en.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    	}
            		}
            	}
            }
            else if (si == SystemLibrary.SystemLibInitializer.NewProcedure)
            {
            	expression_node bfcint = make_new_call(si, _method_call.parameters, subloc2);
            	if (!proc_wait)
                        AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name);
            	switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
            }
            else if (si == SystemLibrary.SystemLibInitializer.DisposeProcedure)
            {
                //if (convertion_data_and_alghoritms.select_function(convert_expression_list(_method_call.parameters.expressions), si, subloc2) == SystemLibrary.SystemLibInitializer.DisposeProcedure.sym_info)
                //{
                    expression_node bfcint = make_dispose_call(si, _method_call.parameters, subloc2);
                    if (!proc_wait)
                        AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name);
                    switch (mot)
                    {
                        case motivation.expression_evaluation:
                            {
                                return_value(bfcint);
                                return;
                            }
                        case motivation.semantic_node_reciving:
                            {
                                return_semantic_value(bfcint);
                                return;
                            }
                        default:
                            {
                                AddError(bfcint.location, "EXPRESSION_IS_NOT_ADDRESSED");
                                return;
                            }
                    }

                    return;
               // }
            }
            else if (!debug && SystemLibrary.SystemLibInitializer.AssertProcedure.Equal(si))
            {
//            	return_value(new empty_statement(null));
//            	return;
            }
            /*else if (SystemLibrary.SystemLibInitializer.IncProcedure != null && SystemLibrary.SystemLibInitializer.IncProcedure.Equal(si))
            	{
            		expression_node bfcint = make_inc_call(si, _method_call.parameters, subloc2);
            	}*/

            if (si.sym_info.general_node_type != general_node_type.function_node)
            {
                if (si.sym_info.general_node_type == general_node_type.type_node)
                {
                    to_type = ((type_node)(si.sym_info));
                    /*if (to_type == SystemLibrary.SystemLibrary.void_type)
                    {
                        throw new VoidNotValid(subloc2);
                    }*/
                    check_for_type_allowed(to_type,subloc2);
                }
                else
                {
                    exp2 = ident_value_reciving(si, id);
                    internal_interface ii = exp2.type.get_internal_interface(internal_interface_kind.delegate_interface);
                    if (ii == null)
                    {
                        AddError(subloc2, "EXPECTED_DELEGATE");
                    }
                    if (exp2 is nonstatic_event_reference)
                    {
                    	nonstatic_event_reference nser = exp2 as nonstatic_event_reference;
                    	common_event ce = nser.en as common_event;
                    	if (ce != null)
                    		exp2 = new class_field_reference(ce.field,new this_node(ce.cont_type,null),null);
                    	else
                    		AddError(get_location(_method_call), "EVENT_{0}_MUST_BE_IN_LEFT_PART", nser.en.name);
                    }
                    else if (exp2 is static_event_reference)
                    {
                    	static_event_reference nser = exp2 as static_event_reference;
                    	common_event ce = nser.en as common_event;
                        if (ce != null)
                            exp2 = new static_class_field_reference(ce.field, null);
                        else if (nser.en is common_namespace_event && _compiled_unit.namespaces.IndexOf((nser.en as common_namespace_event).namespace_node) != -1)
                            exp2 = new namespace_variable_reference((nser.en as common_namespace_event).field, null);
                        else
                            AddError(get_location(_method_call), "EVENT_{0}_MUST_BE_IN_LEFT_PART", nser.en.name);
                    }
                    delegate_internal_interface dii = ii as delegate_internal_interface;
                    si = new SymbolInfo(dii.invoke_method);
                }
            }

            if (to_type != null)
            {
                if ((_method_call.parameters == null) || (_method_call.parameters.expressions.Count != 1))
                {
                    AddError(get_location(_method_call), "ONLY_ONE_PARAMETER_OF_TYPE_CONVERSION_ALLOWED");
                }
            }

            if (_method_call.parameters != null)
            {
                foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                {
                	bool tmp = is_format_allowed;
					
					#region Отмечаем флаг в лямбдах, говорящий о том, что в первый раз будем их "обходить" для вывода типов
                    //lroman//
                    if (en is SyntaxTree.function_lambda_definition)
                    {
                        lambdas_are_in_parameters = true;
                        ((SyntaxTree.function_lambda_definition)en).lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                    }
                    //lroman//
                    #endregion
					
                	exprs.AddElement(convert_strong(en));
                	is_format_allowed = tmp;
                }
            }
			is_format_allowed = false;
            CheckSpecialFunctionCall(si, exprs,get_location(_method_call));

            ssi=si;
            foreach (SymbolInfo sii in sibak)
            {
                ssi.Next = sii;
                ssi = sii;
            }

            if (to_type != null)
            {
                //(ssyy) К вызову функции здесь явно не приводим, т.к. это излишне.
                expression_node ee = exprs[0];
                bool del = to_type is common_type_node && (to_type as common_type_node).IsDelegate;
                if (!del)
                try_convert_typed_expression_to_function_call(ref ee);
                else
                	ee = convert_strong(_method_call.parameters.expressions[0]);
                expr_node = convertion_data_and_alghoritms.explicit_convert_type(ee, to_type);
                //expression_node expr = convert_if_typed_expression_to_function_call(exprs[0]);
                //expr_node = convertion_data_and_alghoritms.explicit_convert_type(expr, to_type);
            }
            else
            {
                if (exp2 == null)
                {
                    location mcloc = get_location(_method_call);
                    if (iwt != null)
                    {
                        si = get_generic_functions(si, true, mcloc);
                        si = get_function_instances(si, iwt.template_params.params_list, id.name, mcloc, si.Next == null);
                    }
					
					#region Если встретились лямбды в фактических параметрах, то выбираем нужную функцию из перегруженных, выводим типы, отмечаем флаг в лямбдах, говорящий о том, что мы их реально обходим 
                    //lroman//
                    if (lambdas_are_in_parameters)
                    {
                        LambdaHelper.processingLambdaParametersForTypeInference++;
                        // SSM 21.05.14 - попытка обработать перегруженные функции с параметрами-лямбдами с различными возвращаемыми значениями
                        function_node_list spf = null;
                        try
                        {
                            function_node fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc2, syntax_nodes_parameters);
                            int exprCounter = 0;
                            foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                            {
                                if (!(en is SyntaxTree.function_lambda_definition))
                                {
                                    exprCounter++;
                                    continue;
                                }
                                else
                                {
                                    var enLambda = (SyntaxTree.function_lambda_definition) en;
                                    LambdaHelper.InferTypesFromVarStmt(fn.parameters[exprCounter].type, enLambda, this);
                                    enLambda.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing;
                                    exprs[exprCounter] = convert_strong(en);
                                    enLambda.lambda_visit_mode = LambdaVisitMode.VisitForInitialMethodCallProcessing;
                                    exprCounter++;
                                }
                            }
                        }
                        catch (SeveralFunctionsCanBeCalled sf)
                        {
                            spf = sf.set_of_possible_functions; // Возможны несколько перегруженных версий - надо выводить дальше в надежде что какие-то уйдут и останется одна
                        }

                        Exception lastmultex = null;
                        if (spf != null) // пытаемся инстанцировать одну за другой и ошибки гасим try
                        {   // exprs - глобальная, поэтому надо копировать
                            int spfnum = -1; // первый номер правильно инстанцированной. Если потом встретился второй, то тоже ошибка
                                             // SSM 4.08.15. Сейчас меняю эту логику. Если будет много кандидатов, но ровно один с совпадающим типом возвращаемого значения, то его и надо выбирать.
                                             // не забыть, что аналогичный код есть в create_constructor_call!!!!!!! И еще выше по коду!!! кошмар!!!
                            int GoodVersionsCount = 0;
                            int GoodVersionsCountWithSameResType = 0;
                            for (int i = 0; i < spf.Count; i++) // цикл по версиям
                            {
                                function_node fn = spf[i];
                                try // внутренний try регенерирует исключение, а этот гасит
                                {
                                    int exprCounter = 0;
                                    expressions_list exprs1 = new expressions_list();
                                    exprs1.AddRange(exprs); // сделали копию

                                    foreach (SyntaxTree.expression en in _method_call.parameters.expressions)
                                    {
                                        if (!(en is SyntaxTree.function_lambda_definition))
                                        {
                                            exprCounter++;
                                            continue;
                                        }
                                        else
                                        {
                                            var fld = en as SyntaxTree.function_lambda_definition;

                                            var lambdaName = fld.lambda_name;                           //lroman Сохранять имя необходимо
                                            var fl = fld.lambda_visit_mode;

                                            // запомнили типы параметров лямбды - SSM
                                            object[] realparamstype = new object[fld.formal_parameters.params_list.Count]; // здесь хранятся выведенные типы лямбд или null если типы явно заданы
                                            for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                            {
                                                var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                if (laminftypeK == null)
                                                    realparamstype[k] = null;
                                                else realparamstype[k] = laminftypeK.real_type;
                                            }

                                            // запоминаем реальный тип возвращаемого значения если он не указан явно (это должен быть any_type или null если он указан явно) - он может измениться при следующем вызове, поэтому мы его восстановим
                                            var restype = fld.return_type as SyntaxTree.lambda_inferred_type;
                                            object realrestype = null;
                                            if (restype != null) 
                                                realrestype = restype.real_type;  

                                            LambdaHelper.InferTypesFromVarStmt(fn.parameters[exprCounter].type, fld, this);
                                            fld.lambda_visit_mode = LambdaVisitMode.VisitForAdvancedMethodCallProcessing; //lroman
                                            fld.lambda_name = LambdaHelper.GetAuxiliaryLambdaName(lambdaName); // поправляю имя. Думаю, назад возвращать не надо. ПРОВЕРИТЬ!

                                            //contextChanger.SaveContextAndUpToNearestDefSect();
                                            try
                                            {
                                                exprs1[exprCounter] = convert_strong(en);

                                                // SSM 7/08/15

                                                type_node resexprtype = fld.RealSemTypeOfResExpr as type_node;
                                                type_node resformaltype = fld.RealSemTypeOfResult as type_node;
                                                var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                if (bbb)
                                                {
                                                    GoodVersionsCountWithSameResType += 1;
                                                    spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                }

                                                /*var tt = fn.parameters[exprCounter].type as compiled_type_node;
                                                if (tt != null && tt.compiled_type.FullName.ToLower().StartsWith("system.func"))
                                                {
                                                    resformaltype = tt.instance_params[tt.instance_params.Count - 1]; // Последний параметр в записи Func<T,T1,...TN> - тип возвращаемого значения
                                                    var bbb = resexprtype == resformaltype; // только в одном случае должно быть true - эту версию и надо выбирать. Если в нескольких, то неоднозначность
                                                    if (bbb)
                                                    {
                                                        GoodVersionsCountWithSameResType += 1;
                                                        spfnum = i; // здесь запоминаем индекс потому что он точно подойдет. Тогда ниже он запоминаться не будет. 
                                                    }
                                                }*/
                                            }
                                            catch
                                            {
                                                throw;
                                            }
                                            finally
                                            {
                                                LambdaHelper.RemoveLambdaInfoFromCompilationContext(context, en as function_lambda_definition);
                                                // восстанавливаем сохраненный тип возвращаемого значения
                                                if (restype != null)
                                                    restype.real_type = realrestype;
                                                // восстанавливаем сохраненные типы параметров лямбды, которые не были заданы явно
                                                for (var k = 0; k < fld.formal_parameters.params_list.Count; k++)
                                                {
                                                    var laminftypeK = fld.formal_parameters.params_list[k].vars_type as SyntaxTree.lambda_inferred_type;
                                                    if (laminftypeK != null)
                                                        laminftypeK.real_type = realparamstype[k];
                                                }

                                                fld.lambda_name = lambdaName; //lroman Восстанавливаем имена
                                                fld.lambda_visit_mode = fl;
                                            }

                                            //contextChanger.RestoreCurrentContext();
                                            exprCounter++;
                                        }
                                    }
                                    /*if (spfnum >= 0) // два удачных инстанцирования - плохо. Может, одно - с более близким типом возвращаемого значения, тогда это плохо - надо доделать, но пока так
                                    {
                                        spfnum = -2;
                                        break;
                                    }*/

                                    if (GoodVersionsCountWithSameResType==0)
                                        spfnum = i; // здесь запоминаем индекс только если нет подошедших, совпадающих по типу возвращаемого значения
                                    GoodVersionsCount += 1;
                                    for (int j = 0; j < exprs.Count; j++) // копируем назад если всё хорошо
                                        exprs[j] = exprs1[j];
                                }
                                catch (Exception e)
                                {
                                    // если сюда попали, значит, не вывели типы в лямбде и надо эту инстанцию пропускать
                                    //contextChanger.RestoreCurrentContext();
                                    lastmultex = e;
                                }
                            } //--------------- конец цикла по версиям

                            if (GoodVersionsCount>1 && GoodVersionsCountWithSameResType!=1) // подошло много, но не было ровно одной с совпадающим типом возвращаемого значения
                                throw new SeveralFunctionsCanBeCalled(subloc2, spf);
                            if (GoodVersionsCount == 0) // было много, но ни одна не подошла из-за лямбд
                            {
                                throw lastmultex;
                                //throw new NoFunctionWithSameArguments(subloc2, false);
                            }

                            var kk = 0;
                            foreach (SyntaxTree.expression en in _method_call.parameters.expressions) //lroman окончательно подставить типы в лямбды
                            {
                                if (!(en is SyntaxTree.function_lambda_definition))
                                {
                                    kk++;
                                    continue;
                                }
                                else
                                {
                                    LambdaHelper.InferTypesFromVarStmt(spf[spfnum].parameters[kk].type, en as SyntaxTree.function_lambda_definition, this);
                                    exprs[kk] = convert_strong(en);
                                    kk++;
                                }
                            }    
                        }
                        // SSM 21.05.14 end
                        LambdaHelper.processingLambdaParametersForTypeInference--;
                    }
                    //lroman//
                    #endregion
					
                    expr_node = convertion_data_and_alghoritms.create_full_function_call(exprs, si, mcloc,
                        context.converted_type, context.top_function, proc_wait);
                }
                else
                {
                    function_node fn = convertion_data_and_alghoritms.select_function(exprs, si, subloc2, syntax_nodes_parameters);
                    base_function_call bbffcc = create_not_static_method_call(fn, exp2, subloc2, proc_wait);
                    bbffcc.parameters.AddRange(exprs);
                    expr_node = bbffcc;
                }
            }

            /*if ((proc_wait==false)&&(expr_node.type==null))
            {
                throw new FunctionExpectedProcedureMeet((function_node)dn,get_location(_method_call));
            }*/

            switch (mot)
            {
                case motivation.expression_evaluation:
                    {
                        return_value(expr_node);
                        return;
                    }
                case motivation.semantic_node_reciving:
                    {
                        return_semantic_value(expr_node);
                        return;
                    }
            	case motivation.address_reciving:
            		{
                        AddError(get_location(_method_call), "LEFT_SIDE_CANNOT_BE_ASSIGNED_TO");
                        return;
            		}
                default:
                    {
                        //throw new CompilerInternalError("Can not recive address from method call");//!
                        AddError(get_location(_method_call), "EXPECTED_VARIABLE");
                        return;
                    }
            }
            //throw new CompilerInternalError("Error in creation method call");

        }
 //remove extension methods when static methods called
 private void delete_extension_methods(ref SymbolInfo si, type_node tn)
 {
     List<SymbolInfo> si_list = new List<SymbolInfo>();
     SymbolInfo tmp_si = si;
     while (tmp_si != null)
     {
         var fn = tmp_si.sym_info as function_node;
         if (fn != null)
         {
             if (fn.is_extension_method)
             {
                 compiled_function_node cfn = fn as compiled_function_node;
                 if (cfn != null && cfn.cont_type == tn)
                     si_list.Add(tmp_si);
             }
             else
                 si_list.Add(tmp_si);
         }
         else
             si_list.Add(tmp_si);
         /*if (!(fn != null && fn.is_extension_method))
             si_list.Add(tmp_si);*/
         tmp_si = tmp_si.Next;
     }
     /*tmp_si = si;
     while (tmp_si != null)
     {
         var fn = tmp_si.sym_info as function_node;
         if (fn != null && fn.is_extension_method)
         {
             var b = false;
             foreach (var x in si_list)
             {
                 var xn = x.sym_info as function_node;
                 if (convertion_data_and_alghoritms.function_eq_params(fn, xn))
                 {
                     b = true;
                     break;
                 }
             }
             if (!b)
                 si_list.Add(tmp_si);
         }
         tmp_si = tmp_si.Next;
     }*/
     SymbolInfo new_si = null;
     for (int i = 0; i < si_list.Count; i++)
     {
         if (new_si == null)
         {
             new_si = si_list[i];
             si = new_si;
         }
         else
         {
             si.Next = si_list[i];
             si = si.Next;
         }
     }
     if (si != null)
         si.Next = null;
     si = new_si;
 }
 private semantic_node ident_semantic_reciving(SymbolInfo si_left, SyntaxTree.ident _ident)
 {
     //SymbolInfo si_left=blocks.find(_ident.name);
     location lloc = get_location(_ident);
     if (si_left == null)
     {
         AddError(new UndefinedNameReference(_ident.name, lloc));
     }
     definition_node dn = context.check_name_node_type(_ident.name, si_left, get_location(_ident),
         general_node_type.constant_definition, general_node_type.function_node,
         general_node_type.namespace_node, general_node_type.property_node,
         general_node_type.type_node, general_node_type.variable_node,
         general_node_type.unit_node);
     switch (dn.general_node_type)
     {
         case general_node_type.constant_definition:
         case general_node_type.function_node:
         case general_node_type.property_node:
         case general_node_type.variable_node:
             {
                 return ident_value_reciving(si_left, _ident);
             }
         case general_node_type.namespace_node:
             {
                 //throw new CompilerInternalError("Unsupported now.");
                 return dn;
             }
         case general_node_type.type_node:
             {
                 type_node tn = dn as type_node;
                 //dot_node_as_type_ident(tn,id_right,mot);
                 return tn;
             }
         case general_node_type.unit_node:
             {
                 //throw new CompilerInternalError("Unsupproted now.");
                 //throw new NotSupportedError(get_location(_ident));
                 return dn;
             }
     }
     return null;
 }
        private void CheckSpecialFunctionCall(SymbolInfo si, expressions_list exprs, location loc)
        {
            if (SystemUnitAssigned)
            {
                bool write_proc = SystemLibrary.SystemLibInitializer.write_procedure.Equal(si);
                if (write_proc && exprs.Count > 1)
                {
                    //возможно это запись в типизированый файл
                    if (exprs[0].type.type_special_kind == SemanticTree.type_special_kind.typed_file)
                    //да, точно это типизированый файл!
                    {
                        //Проверим типы параметров вызова на совпадение с типом элементов файла
                        type_node element_type = exprs[0].type.element_type;
                        for (int i = 1; i < exprs.Count; i++)
                            convertion_data_and_alghoritms.check_convert_type(exprs[i], element_type, exprs[i].location);
                        if (element_type.type_special_kind == SemanticTree.type_special_kind.short_string)
                        {
                        	for (int i=1; i<exprs.Count; i++)
                        	{
                        		//common_namespace_function_call cmc = new common_namespace_function_call(SystemLibrary.SystemLibInitializer.ClipShortStringProcedure.sym_info as common_namespace_function_node,null);
                        		//cmc.parameters.AddElement(exprs[i]);
                        		//cmc.parameters.AddElement(new int_const_node((element_type as short_string_type_node).Length,null));
                        		expression_node cmc = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.ClipShortStringProcedure.sym_info as function_node,null,convertion_data_and_alghoritms.convert_type(exprs[i],SystemLibrary.SystemLibrary.string_type),new int_const_node((element_type as short_string_type_node).Length,null));
                        		exprs[i] = cmc;
                        	}
                        }
                        //if (exprs[i].type != element_type)
                        //  throw new ExpectedExprHaveTypeTypedFile(element_type, exprs[i].type, false, get_location(_method_call.parameters.expressions[i]));
                    }
                    else
                        //(ssyy) а может быть, в бинарный!
                        if (exprs[0].type.type_special_kind == SemanticTree.type_special_kind.binary_file)
                        {
                            //(ssyy) действительно, бинарный
                            for (int i = 1; i < exprs.Count; i++)
                            {
                                if (!CanUseThisTypeForBinaryFiles(exprs[i].type))
                                {
                                    AddError(exprs[i].location, "CAN_NOT_WRITE_REFERENCE_DATA_TO_BINARY_FILE");
                                }
                            }
                        }
                        else
                        {
                            if (SystemLibrary.SystemLibInitializer.write_procedure.sym_info is common_namespace_function_node)
                                ConvertPointersForWrite(exprs);
                            else
                                ConvertPointersForWriteFromDll(exprs);
                        }
                }
                else if (write_proc || SystemLibrary.SystemLibInitializer.writeln_procedure.Equal(si))
                {
                    //(ssyy) Преобразуем указатели в строки для вывода write/writeln
                    if (SystemLibrary.SystemLibInitializer.writeln_procedure.sym_info is common_namespace_function_node)
                        ConvertPointersForWrite(exprs);
                    else
                        ConvertPointersForWriteFromDll(exprs);
                }
                else if (SystemLibrary.SystemLibInitializer.IncludeProcedure.Equal(si)
                            || SystemLibrary.SystemLibInitializer.ExcludeProcedure.Equal(si))
                {
                    if (exprs.Count != 2) AddError( new NoFunctionWithSameArguments(loc, true));
                    type_node element_type = exprs[0].type.element_type;
                    if (exprs[0].type.type_special_kind != SemanticTree.type_special_kind.base_set_type && exprs[0].type.type_special_kind != SemanticTree.type_special_kind.set_type)
                    {
                    	AddError( new NoFunctionWithSameArguments(loc, true));
                    }
                    if (element_type != null)
                        convertion_data_and_alghoritms.check_convert_type(exprs[1], element_type, exprs[1].location);
                    else convertion_data_and_alghoritms.check_convert_type(exprs[1], exprs[0].type, exprs[0].location);
                    if (!exprs[0].is_addressed) AddError( new ThisExpressionCanNotBePassedAsVarParameter(exprs[0]));
                }
                else if (SystemLibrary.SystemLibInitializer.InSetProcedure.Equal(si))
                {
                    if (exprs.Count != 2) AddError( new NoFunctionWithSameArguments(loc, true));
                    type_node element_type = exprs[1].type.element_type;
                    if (element_type != null)
                    {
                        //exprs[0] = convertion_data_and_alghoritms.convert_type(exprs[0], element_type, exprs[0].location);
                        convertion_data_and_alghoritms.check_convert_type(exprs[0], element_type, exprs[0].location);
                    }
                    else convertion_data_and_alghoritms.check_convert_type(exprs[0], exprs[1].type, exprs[0].location);
                }
                else if (SystemLibrary.SystemLibInitializer.SetUnionProcedure.Equal(si)
                   || SystemLibrary.SystemLibInitializer.SetIntersectProcedure.Equal(si) || SystemLibrary.SystemLibInitializer.SetSubtractProcedure.Equal(si))
                {
                    if (exprs.Count != 2) AddError( new NoFunctionWithSameArguments(loc, true));
                    convertion_data_and_alghoritms.check_convert_type(exprs[1], exprs[0].type, exprs[1].location);
                }

                if (si == SystemLibrary.SystemLibInitializer.NewProcedure || si == SystemLibrary.SystemLibInitializer.DisposeProcedure)
                {
                    if (exprs[0].type == SystemLibrary.SystemLibrary.pointer_type)
                        AddError(exprs[0].location, "EXPECTED_TYPED_POINTER_IN_PROCEDURE{0}", (si.sym_info as function_node).name);
                }
            }
        }
 internal typed_expression make_delegate_wrapper(expression_node obj, SymbolInfo si, location loc, bool is_static)
 {
     base_function_call_list fnl = create_possible_delegates_list(obj, si, loc, is_static);
     if (fnl.Count == 0)
     {
         if (is_static)
         {
             AddError(loc, "EXPECTED_STATIC_METHOD");
         }
         else
         {
             AddError(loc, "EXPECTED_NON_STATIC_METHOD");
         }
     }
     delegated_methods dm = new delegated_methods();
     dm.proper_methods.AddRange(fnl);
     typed_expression te = new typed_expression(dm, loc);
     return te;
 }
 private expression_node make_pred_call(SymbolInfo si, SyntaxTree.expression_list parameters, location loc)
 {
     if (parameters == null)
     {
         AddError(new NoFunctionWithSameParametresNum(loc, false, si.sym_info as function_node));
         return null;
     }
 	if (parameters.expressions.Count == 1)
 	{
 		expression_node param0 = convert_strong(parameters.expressions[0]);
 		if (param0 is typed_expression) param0 = convert_typed_expression_to_function_call(param0 as typed_expression);
 		basic_function_call bfc = null;
 		int type_flag = 0;
 		expressions_list el = new expressions_list();
 		el.AddElement(param0);
 		function_node fn = null;
 		try
 		{
 			fn = convertion_data_and_alghoritms.select_function(el,si,loc);
 		}
 		catch(Exception e)
 		{
 			
 		}
 		if (fn != null)
 		{
             if (fn is common_namespace_function_node)
             {
                 common_namespace_function_call cnfc = new common_namespace_function_call(fn as common_namespace_function_node, loc);
                 cnfc.parameters.AddElement(param0);
                 return cnfc;
             }
             else
             {
                 compiled_static_method_call cnfc = new compiled_static_method_call(fn as compiled_function_node, loc);
                 cnfc.parameters.AddElement(param0);
                 return cnfc;
             }
 		}
 		else if (param0.type.type_special_kind == PascalABCCompiler.SemanticTree.type_special_kind.diap_type || param0.type.IsEnum)
 		{
 			el = new expressions_list();
 			el.AddElement(new int_const_node(1,null));
 			fn = convertion_data_and_alghoritms.select_function(el,si,loc);
 			//bfc = new basic_function_call(SystemLibrary.SystemLibrary.int_add as basic_function_node,loc);
 			//bfc.ret_type = param0.type;
             if (fn is common_namespace_function_node)
             {
                 common_namespace_function_call cnfc = new common_namespace_function_call(fn as common_namespace_function_node, loc);
                 cnfc.parameters.AddElement(param0);
                 cnfc.type = param0.type;
                 return cnfc;
             }
             else
             {
                 compiled_static_method_call cnfc = new compiled_static_method_call(fn as compiled_function_node, loc);
                 cnfc.parameters.AddElement(param0);
                 cnfc.type = param0.type;
                 return cnfc;
             }
 		}
 		else AddError(new NoFunctionWithSameArguments(loc,false));
 		bfc.parameters.AddElement(param0);
 		if (type_flag == 0 || type_flag == 3)
 		bfc.parameters.AddElement(new int_const_node(1,null));
 		else if (type_flag == 1)
 		bfc.parameters.AddElement(new long_const_node(1,null));
 		else if (type_flag == 2)
 		bfc.parameters.AddElement(new ulong_const_node(1,null));
 		return bfc;
 	}
 	AddError(new NoFunctionWithSameParametresNum(loc,false,si.sym_info as function_node));
     return null;
 }
 public type_node get_generic_instance(SymbolInfo si, List<SyntaxTree.type_definition> type_pars)
 {
     type_node node = si.sym_info as type_node;
     compiled_type_node comp_node = node as compiled_type_node;
     List<generic_parameter_eliminations> lgpe = null;
     if (!context.skip_check_where_sections)
     {
         lgpe = (comp_node == null) ?
             (node as common_type_node).parameters_eliminations :
             comp_node.parameters_eliminations;
     }
     List<type_node> tparams = visit_type_list_with_check(type_pars, lgpe, !context.skip_check_where_sections);
     return node.get_instance(tparams);
 }
        private expression_node make_read_call(SymbolInfo si, SyntaxTree.expression_list parameters, location loc)
        {

            // вызов read(a,b,c) разбивается на несколько вызовов, последний возвращается узлом, а остальные добавляются здесь в теле            expressions_list exl = new expressions_list();
            expression_node last_call = null;
            expressions_list exl = new expressions_list();
            expression_node file = null;
            bool read_from_file = false;
            bool read_from_text_file = false;
            bool read_from_typed_file = false;
            bool read_from_binary_file = false;
            bool readln_string_file = false;
            if (parameters != null) // если список параметров не пуст
            {
                if (parameters.expressions.Count >= 1)
                {
                    expression_node param0 = convert_strong(parameters.expressions[0]);
                    if (param0.type != null)
                    {
                        if (SystemLibrary.SystemLibInitializer.TextFileType.Found && param0.type == SystemLibrary.SystemLibInitializer.TextFileType.sym_info)
                        {
                            file = param0;
                            read_from_text_file = true;
                        }
                        if (param0.type.type_special_kind == SemanticTree.type_special_kind.typed_file
                            && parameters.expressions.Count > 1                        //это можно внести во внутрь
                            )//и побросать приличные исключения
                        {
                            if (!SystemLibrary.SystemLibInitializer.read_procedure.FromDll)
                            {
                                if (si == SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo)
                                {
                                    file = param0;
                                    read_from_typed_file = true;
                                }
                            }
                            else if (SystemLibrary.SystemLibInitializer.read_procedure.Equal(si))
                            {
                                file = param0;
                                read_from_typed_file = true;
                            }
                        }
                        if (param0.type.type_special_kind == SemanticTree.type_special_kind.binary_file
                            && parameters.expressions.Count > 1                        //это можно внести во внутрь
                            )//и побросать приличные исключения
                        {
                            if (!SystemLibrary.SystemLibInitializer.read_procedure.FromDll)
                            {
                                if (si == SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo)
                                {
                                    file = param0;
                                    read_from_binary_file = true;
                                }
                            }
                            else if (SystemLibrary.SystemLibInitializer.read_procedure.Equal(si))
                            {
                                file = param0;
                                read_from_binary_file = true;
                            }
                        }
                    }
                    read_from_file = read_from_text_file || read_from_typed_file || read_from_binary_file;
                }
                bool first_iteration = true;
                
                foreach (SyntaxTree.expression ex in parameters.expressions)
                {
                    if (first_iteration && read_from_file)
                    {
                        first_iteration = false;
                        continue;
                    }
                    if (last_call != null && convertion_data_and_alghoritms.statement_list_stack.size > 0)
                        convertion_data_and_alghoritms.statement_list_stack.top().statements.AddElement(last_call);
                    expression_node en = convert_strong(ex);
                    check_on_loop_variable(en);
                    //if (en.type == null)
                    //throw new CanNotRead(en.location);
                    exl.clear();
                    if (read_from_file)
                        exl.AddElement(file);
                    if (read_from_typed_file)
                    {
                        if (SystemLibrary.SystemLibInitializer.TypedFileReadProcedure == null)
                            AddError(new NotSupportedError(loc));
                        if (en.type != file.type.element_type)
                            AddError(new ExpectedExprHaveTypeTypedFile(file.type.element_type, en.type, true, get_location(ex)));
                        bool is_char_getter = false;
                        if (!en.is_addressed)
                        {
                            if (en is compiled_function_call)
                            {
                                compiled_function_call cfc = en as compiled_function_call;
                                
                                if ((cfc.function_node.return_value_type == SystemLibrary.SystemLibrary.char_type && cfc.function_node.cont_type == SystemLibrary.SystemLibrary.string_type
                                      && cfc.function_node == cfc.function_node.cont_type.default_property_node.get_function))
                                {
                                    en = new simple_array_indexing((en as compiled_function_call).obj, (en as compiled_function_call).parameters[0], SystemLibrary.SystemLibrary.char_type, en.location);
                                    is_char_getter = true;
                                }
                                
                            }
                        }
                        function_node fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.TypedFileReadProcedure.SymbolInfo, loc);
                        expression_node expr = convertion_data_and_alghoritms.create_simple_function_call(fn, get_location(ex), file);
                        //expression_node expr = convertion_data_and_alghoritms.create_full_function_call(exl, SystemLibrary.SystemLibInitializer.TypedFileReadProcedure.SymbolInfo, loc, context.converted_type, context.top_function, true);
                        expr = convertion_data_and_alghoritms.explicit_convert_type(expr, file.type.element_type);
                        if (is_char_getter)
                            expr = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.StringDefaultPropertySetProcedure.sym_info as function_node, loc, (en as simple_array_indexing).simple_arr_expr, (en as simple_array_indexing).ind_expr, expr);
                        else
                            expr = find_operator(compiler_string_consts.assign_name, en, expr, loc);
                        last_call = expr;
                    }
                    else if (read_from_binary_file)
                    {
                        if (SystemLibrary.SystemLibInitializer.BinaryFileReadProcedure == null)
                            AddError(new NotSupportedError(loc));
                        if (!CanUseThisTypeForBinaryFiles(en.type))
                        {
                            AddError(en.location, "CAN_NOT_READ_REFERENCE_DATA_FROM_BINARY_FILE");
                        }
                        exl.AddElement(new typeof_operator(en.type, loc));
                        function_node fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.BinaryFileReadProcedure.SymbolInfo, loc);
                        expression_node expr = convertion_data_and_alghoritms.create_simple_function_call(fn, get_location(ex), exl.ToArray());
                        expr = convertion_data_and_alghoritms.explicit_convert_type(expr, en.type);
                        expr = find_operator(compiler_string_consts.assign_name, en, expr, loc);
                        last_call = expr;
                    }
                    else
                    {
                        exl.AddElement(en);
                        try
                        {
                        	function_node fn = null;
                        	if (en.type.type_special_kind == SemanticTree.type_special_kind.short_string)
                        	{
                        		exl.AddElement(new int_const_node((en.type as short_string_type_node).Length,null));
                        		if (!read_from_file)
                        		last_call = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.read_short_string_procedure.sym_info as function_node,get_location(ex),exl.ToArray());
                        		else
                        		last_call = convertion_data_and_alghoritms.create_simple_function_call(SystemLibrary.SystemLibInitializer.read_short_string_from_file_procedure.sym_info as function_node,get_location(ex),exl.ToArray());
                        	}
                        	else if (en.type.type_special_kind == SemanticTree.type_special_kind.diap_type)
                        	{
                        		exl.remove(en);
                        		en.type = en.type.base_type;
                        		exl.AddElement(en);
                        		fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo, loc);
                            	last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, get_location(ex), exl.ToArray());
                        	}
                        	else
                        	{
                                if (SystemLibrary.SystemLibInitializer.readln_procedure.Equal(si) && parameters.expressions.Count == 2 && en.type == SystemLibrary.SystemLibrary.string_type)
                                {
                                    fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.readln_procedure.SymbolInfo, loc);
                                    readln_string_file = true;
                                }
                                else
                                    fn = convertion_data_and_alghoritms.select_function(exl, SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo, loc);
                            	last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, get_location(ex), exl.ToArray());
                        	}
                            //last_call = convertion_data_and_alghoritms.create_full_function_call(exl, SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo, loc, context.converted_type, context.top_function, true);
                        }
                        catch (NoFunctionWithSameArguments)
                        {
                            AddError(en.location, "CAN_NOT_READ");
                        }
                    }
                    first_iteration = false;
                }
            }
            if ((parameters == null) || (parameters.expressions.Count == 0)) // read(), readln()
            {
                if (SystemLibrary.SystemLibInitializer.read_procedure.Equal(si))
                {
                    if (read_from_file)
                        exl.AddElement(file);
                    function_node fn = convertion_data_and_alghoritms.select_function(exl,
                        SystemLibrary.SystemLibInitializer.read_procedure.SymbolInfo, loc);
                    if (read_from_file)
                        last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, loc, file);
                    else
                        last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, loc);
                }
            }
            if (SystemLibrary.SystemLibInitializer.readln_procedure.Equal(si)) // readln(...)
            {
                if (!readln_string_file)
                {
                    if (last_call != null && convertion_data_and_alghoritms.statement_list_stack.size > 0)
                        convertion_data_and_alghoritms.statement_list_stack.top().statements.AddElement(last_call);
                    exl.clear();

                    if (read_from_file)
                        exl.AddElement(file);

                    function_node fn = convertion_data_and_alghoritms.select_function(exl,
                            SystemLibrary.SystemLibInitializer.readln_procedure.SymbolInfo, loc);
                    if (read_from_file)
                        last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, loc, file);
                    else
                        last_call = convertion_data_and_alghoritms.create_simple_function_call(fn, loc);
                }
            }
            return last_call;
        }
        public SymbolInfo ConvertTypeToInstance(SymbolInfo si, List<SyntaxTree.type_definition> type_pars, location loc)
        {
            if (si == null)
                return null;
            template_class tclass = si.sym_info as template_class;
            if (tclass == null)
            {
                generic_indicator gi = si.sym_info as generic_indicator;
                if (gi != null)
                {
                    AddError(loc, "TYPE_{0}_HAS_{1}_GENERIC_PARAMETERS", gi.generic.name, gi.generic.generic_params.Count);
                }
                return null;
            }
            //Формируем список параметров инстанцирования
            List<type_node> tparams = visit_type_list(type_pars);

            type_node t = instance_any(tclass, tparams, loc);
            return new SymbolInfo(t);
        }
        private expression_node create_static_expression(type_node tn, SyntaxTree.ident id_right,
            SymbolInfo si_right)
        {
            definition_node dn = context.check_name_node_type(id_right.name, si_right, get_location(id_right), general_node_type.variable_node,
                general_node_type.function_node, general_node_type.property_node, general_node_type.constant_definition);
            switch (dn.general_node_type)
            {
                case general_node_type.variable_node:
                    {
                        return create_class_static_field_reference(tn, dn, id_right);
                    }
                case general_node_type.constant_definition:
                    {
                        constant_definition_node cdn = (constant_definition_node)dn;
                        return cdn.const_value.get_constant_copy(get_location(id_right));
                    }
                case general_node_type.function_node:
                    {
                        //TODO: Передается пустой список выражений.
                        /*
                        function_node fn=convertion_data_and_alghoritms.select_function(new expressions_list(),
                            si_right,get_location(id_right));
                        return create_static_method_call(fn,get_location(id_right),tn,false);
                        */
                        //if (!(si_right.sym_info is common_in_function_function_node))
                        if (dn is compiled_function_node)
                        {
                            if ((dn as compiled_function_node).ConnectedToType == tn)
                                AddError(new UndefinedNameReference(id_right.name, get_location(id_right)));
                        }
                        else if (dn is common_namespace_function_node)
                        {
                            if ((dn as common_namespace_function_node).ConnectedToType == tn)
                                AddError(new UndefinedNameReference(id_right.name, get_location(id_right)));
                        }
                        if (dn.semantic_node_type == semantic_node_type.indefinite_definition_node)
                        {
                            return new indefinite_reference(dn as indefinite_definition_node, get_location(id_right));
                        }
                        return make_delegate_wrapper(null, si_right, get_location(id_right), true);

                    }
                case general_node_type.property_node:
                    {
                        property_node pn = (property_node)dn;
                        if (pn.polymorphic_state != SemanticTree.polymorphic_state.ps_static)
                        {
                            AddError(new CanNotReferenceToNonStaticPropertyWithType(pn, get_location(id_right), tn));
                        }
                        function_node fn = pn.get_function;
                        if (fn == null)
                        {
                            AddError(new ThisPropertyCanNotBeReaded(pn, get_location(id_right)));
                        }
                        location lloc = get_location(id_right);
                        check_property_no_params(pn, lloc);
                        return create_static_method_call(fn, lloc, tn, false);
                    }
            }
            throw new CompilerInternalError("Error in creating static expression.");
        }
        public void lambda_header_visit(SymbolInfo si, SyntaxTree.function_header _function_header, type_node tn1)
        {
            type_node tn = null;
            if (_function_header.return_type == null)
            {
                if (context.top_function.IsOperator)
                    AddError(get_location(_function_header), "FUNCTION_NEED_RETURN_TYPE");
            }
            if (_function_header.return_type != null)
            {
                check_parameter_on_complex_type(_function_header.return_type);
                if (tn1 != null)
                    tn = tn1;
                else
                    tn = convert_strong(_function_header.return_type);
                //if (tn == SystemLibrary.SystemLibrary.void_type)
                //    AddError(new VoidNotValid(get_location(_function_header.return_type)));
                check_for_type_allowed(tn, get_location(_function_header.return_type));
            }
            //(ssyy) moved up, так как при проверке аттрибута override надо знать тип возвращаемого значения
            context.top_function.return_value_type = tn;
            assign_doc_info(context.top_function, _function_header);
            if (_function_header.attributes != null)
            {
                make_attributes_for_declaration(_function_header, context.top_function);
            }
            if (context.converted_type != null && has_dll_import_attribute(context.top_function))
                AddError(get_dll_import_attribute(context.top_function).location, "DLLIMPORT_ATTRIBUTE_CANNOT_BE_APPLIED_TO_METHOD");
            if (_function_header.name.class_name != null)
                with_class_name = true;
            if (_function_header.class_keyword && !has_static_attr(_function_header.proc_attributes.proc_attributes))
            {
                SyntaxTree.procedure_attribute pa = new SyntaxTree.procedure_attribute(PascalABCCompiler.SyntaxTree.proc_attribute.attr_static);
                pa.source_context = _function_header.source_context;
                _function_header.proc_attributes.proc_attributes.Add(pa);
            }
            weak_node_test_and_visit(_function_header.proc_attributes);
            if (context.top_function.IsOperator)
            {
                common_method_node cmmn = context.top_function as common_method_node;
                //if (cmmn == null)
                //{
                //    throw new OverloadOperatorMustBeStaticFunction(get_location(_function_header), context.top_function);
                //}
                if (cmmn != null && cmmn.polymorphic_state != SemanticTree.polymorphic_state.ps_static)
                {
                    AddError(get_location(_function_header), "OVERLOADED_OPERATOR_MUST_BE_STATIC_FUNCTION");
                }
                if (cmmn != null && (cmmn.name == compiler_string_consts.implicit_operator_name || cmmn.name == compiler_string_consts.explicit_operator_name))
                    if (!convertion_data_and_alghoritms.eq_type_nodes(tn, cmmn.comperehensive_type as type_node) && !convertion_data_and_alghoritms.eq_type_nodes(cmmn.comperehensive_type as type_node, cmmn.parameters[0].type))
                    {
                        AddError(get_location(_function_header.return_type), "RETURN_VALUE_SHOULD_HAVE_TYPE_{0}", (cmmn.comperehensive_type as type_node).PrintableName);
                    }
                    else if (convertion_data_and_alghoritms.eq_type_nodes(tn, cmmn.parameters[0].type))
                    {
                        AddError(get_location(_function_header), "CIRCURAL_TYPE_CONVERSION_DEFINITION");
                    }
            }
            with_class_name = false;
            if (context.top_function != null && context.top_function is common_namespace_function_node && (context.top_function as common_namespace_function_node).ConnectedToType != null && !context.top_function.IsOperator)
            {
                concrete_parameter_type cpt = concrete_parameter_type.cpt_none;
                SemanticTree.parameter_type pt = PascalABCCompiler.SemanticTree.parameter_type.value;
                if ((context.top_function as common_namespace_function_node).ConnectedToType.is_value_type)
                {
                    cpt = concrete_parameter_type.cpt_var;
                    pt = PascalABCCompiler.SemanticTree.parameter_type.var;
                }
                common_parameter cp = new common_parameter(compiler_string_consts.self_word, (context.top_function as common_namespace_function_node).ConnectedToType, pt,
                                                                                context.top_function, cpt, null, null);
                context.top_function.parameters.AddElementFirst(cp);
                context.top_function.scope.AddSymbol(compiler_string_consts.self_word, new SymbolInfo(cp));
            }
            CheckOverrideOrReintroduceExpectedWarning(get_location(_function_header));

            bool unique = context.close_function_params(body_exists);
            if (context.top_function.return_value_type == null)
                AddError(get_location(_function_header), "FUNCTION_NEED_RETURN_TYPE");
            if (_function_header.where_defs != null)
            {
                if (unique)
                {
                    visit_where_list(_function_header.where_defs);
                }
                else
                {
                    AddError(get_location(_function_header.where_defs), "WHERE_SECTION_MUST_BE_ONLY_IN_FIRST_DECLARATION");
                }
            }
            convertion_data_and_alghoritms.create_function_return_variable(context.top_function, si);

            /*if (_function_header.name != null && context.converted_compiled_type != null && context.top_function is common_namespace_function_node)
            {
                if (context.FindMethodToOverride(context.top_function as common_namespace_function_node) != null)
                    AddError(new CanNotDeclareExtensionMethodAsOverrided(get_location(_function_header)));
            }*/
            //TODO: Разобрать подробнее.
            if (!body_exists)
            {
                if ((context.top_function.semantic_node_type == semantic_node_type.common_method_node)
                    || ((context.func_stack_size_is_one()) && (_is_interface_part)))
                {
                    context.leave_block();
                }
            }
            body_exists = false;
        }
 private expression_node expression_value_reciving(SyntaxTree.ident id_right, SymbolInfo si, expression_node en, bool expected_delegate)
 {
     definition_node dn = context.check_name_node_type(id_right.name, si, get_location(id_right), general_node_type.variable_node,
         general_node_type.function_node, general_node_type.property_node, general_node_type.constant_definition);
     switch (dn.general_node_type)
     {
         /*case general_node_type.constant_defenition:
         {
             constant_definition_node cdn=(constant_definition_node)dn;
             return cdn.const_value;
         }*/
         case general_node_type.variable_node:
             {
                 return create_class_field_reference(en, dn, id_right);
             }
         case general_node_type.function_node:
             {
                 if (dn.semantic_node_type == semantic_node_type.indefinite_definition_node)
                 {
                     return new indefinite_reference(dn as indefinite_definition_node, get_location(id_right));
                 }
                 if (expected_delegate)
                     return make_delegate_wrapper(en, si, get_location(id_right), false);
                 else
                 {
                     function_node fn = convertion_data_and_alghoritms.select_function(new expressions_list(),
                         si, get_location(id_right));
                     return create_not_static_method_call(fn, en, get_location(id_right), false);
                 }
             }
         case general_node_type.property_node:
             {
                 property_node pn = (property_node)dn;
                 if (pn.polymorphic_state == SemanticTree.polymorphic_state.ps_static)
                 {
                     AddError(new CanNotReferenceToStaticPropertyWithExpression(pn, get_location(id_right), pn.comprehensive_type));
                 }
                 function_node fn = pn.get_function;
                 if (fn == null)
                 {
                     AddError(new ThisPropertyCanNotBeReaded(pn, get_location(id_right)));
                 }
                 location lloc = get_location(id_right);
                 check_property_no_params(pn, lloc);
                 return create_not_static_method_call(fn, en, lloc, false);
             }
         case general_node_type.constant_definition:
             {
                 //throw new ConstMemberCannotBeAccessedWithAnInstanceReference((class_constant_definition)dn, get_location(id_right));
                 return ((constant_definition_node)dn).const_value;
             }
     }
     throw new CompilerInternalError("Invalid class member");
 }
 internal SymbolInfo get_function_instances(SymbolInfo si, List<SyntaxTree.type_definition> type_pars, string name, location loc, bool stop_on_error)
 {
     List<type_node> tparams = visit_type_list(type_pars);
     for (int i = 0; i < tparams.Count; i++)
     {
         CompilationErrorWithLocation err = generic_parameter_eliminations.check_type_generic_useful(tparams[i], loc);
         if (err != null)
         {
             AddError( err);
         }
     }
     SymbolInfo start = null;
     SymbolInfo tek = null;
     while (si != null)
     {
         function_node fn = si.sym_info as function_node;
         if (fn != null)
         {
             function_node inst = fn.get_instance(tparams, stop_on_error, loc);
             if (inst != null)
             {
                 SymbolInfo s = new SymbolInfo(inst);
                 if (start == null)
                 {
                     start = tek = s;
                 }
                 else
                 {
                     tek.Next = s;
                     tek = s;
                 }
             }
         }
         si = si.Next;
     }
     if (start == null)
     {
         AddError(loc, "NO_FUNCTIONS_{0}_CAN_BE_USED_WITH_THIS_SPECIFICATION", name);
     }
     return start;
 }
예제 #29
0
 public override void add_generated_name(string name, SymbolInfo si)
 {
     //ничего не делаем
 }
 private SymbolInfo get_generic_functions(SymbolInfo funcs, bool stop_on_none, location loc)
 {
     SymbolInfo start = null;
     SymbolInfo cur = null;
     while (funcs != null)
     {
         function_node f = funcs.sym_info as function_node;
         if (f.is_generic_function)
         {
             //Проверяем на совпадение
             bool found = false;
             SymbolInfo fsi = start;
             while (fsi != null && fsi != funcs)
             {
                 if (convertion_data_and_alghoritms.function_eq_params(fsi.sym_info as function_node, f))
                 {
                     found = true;
                     break;
                 }
                 fsi = fsi.Next;
             }
             if (!found)
             {
                 if (start == null)
                 {
                     start = funcs;
                 }
                 else
                 {
                     cur.Next = funcs;
                 }
                 cur = funcs;
             }
         }
         funcs = funcs.Next;
     }
     if (start == null)
     {
         if (stop_on_none)
         {
             AddError(loc, "TRIANGLE_BRACKETS_NOT_ALLOWED_WITH_COMMON_FUNCTIONS");
         }
         return null;
     }
     cur.Next = null;
     return start;
 }