Merge pull request #2727 from SunSerega/fix-2725

Исправление #2725
This commit is contained in:
Ivan Bondarev 2022-10-01 17:32:09 +02:00 committed by GitHub
commit 6dc9a7ed1c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
16 changed files with 243 additions and 274 deletions

Binary file not shown.

View file

@ -1,11 +1,10 @@
type
t1=abstract class
//!Класс t2 абстрактный и не может иметь атрибут sealed, потому что метод test не реализован
type
t1 = abstract class
procedure test; abstract;
end;
t2=sealed class(t1)
t2 = sealed class(t1)
end;
begin
end.
begin end.

View file

@ -1,4 +1,5 @@
type
//!Предописание I2<T> не может быть использовано в качестве базового типа
type
I1<T> = interface;
I2<T> = interface;

View file

@ -1,13 +0,0 @@
type
t0<T> = class end;
A = class;
B = class(t0<A>)
end;
A = class
end;
begin
end.

View file

@ -1,11 +0,0 @@
type
TErr<T3> = class;
TDer<T4> = class(List<TErr<T4>>)
end;
TErr<T3> = class end;
begin
end.

View file

@ -1,4 +1,5 @@
type
//!Невозможно инстанцировать, так как тип T не наследован от List<integer>
type
t1<T> = class
where T: List<integer>;

View file

@ -0,0 +1,11 @@
//!Тип 't1<T>' наследует от самого себя
type
t1<T> = partial class
end;
t2<T> = class(t1<T>) end;
t1<T> = partial class(t2<byte>)
end;
begin end.

View file

@ -0,0 +1,32 @@
// issue#2725
type
i0 = interface end;
base_i<TSelf> = interface
where TSelf: base_i<TSelf>;
function fi(a: TSelf): TSelf;
end;
base_c<TSelf> = abstract class
where TSelf: base_c<TSelf>;
function fc(a: TSelf): TSelf; abstract;
end;
class1 = class(i0, base_i<class1>)
public function fi(a: class1) := a;
end;
class2 = class(base_c<class2>, base_i<class2>)
public function fi(a: class2) := self;
public function fc(a: class2): class2; override := self;
end;
record1 = record(i0, base_i<record1>)
public function fi(a: record1) := self;
end;
interface1 = interface(i0, base_i<interface1>)
end;
begin end.

View file

@ -3058,19 +3058,6 @@ namespace PascalABCCompiler.TreeConverter
return null; // это вхолостую
}
public bool ContainsForward(type_node tn)
{
if (tn.ForwardDeclarationOnly || tn.original_generic != null && tn.original_generic.ForwardDeclarationOnly)
return true;
if (tn is generic_instance_type_node tni)
foreach (var t in tn.instance_params)
{
var r = ContainsForward(t);
if (r)
return r;
}
return false;
}
}
}

View file

@ -3756,121 +3756,160 @@ namespace PascalABCCompiler.TreeConverter
context.converted_type.SetIsSealed(true);
context.converted_type.SetIsAbstract(true, null); // Причина null, потому что причины нет, класс статический а не абстрактный
}
common_type_node converted_type;
//TODO Выглядит странно - в каком это случае семантический узел записи создаётся с задержкой?
if (_class_definition.keyword==PascalABCCompiler.SyntaxTree.class_keyword.Record)
{
if (_record_created)
{
_record_created = false;
converted_type = context.converted_type;
}
else
{
converted_type = context.create_record_type(get_location(_class_definition), record_type_name);
if (record_is_generic)
{
context.create_generic_indicator(converted_type);
visit_generic_params(converted_type, _class_definition.template_args.idents);
}
else
{
if (_class_definition.template_args != null && _class_definition.template_args.idents != null)
{
AddError(get_location(_class_definition.template_args), "GENERIC_TYPE_NOT_ALLOWED_HERE");
}
}
visit_where_list(_class_definition.where_section);
}
}
else
converted_type = context.converted_type;
// Для записей базовый класс устанавливает на SemanticRules.StructBaseType ещё в context.create_record_type
var need_set_base = _class_definition.keyword != PascalABCCompiler.SyntaxTree.class_keyword.Record;
if (_class_definition.class_parents != null)
{
// Ограничение шаблонов предка и интерфейсов нельзя проверять
// на первом проходе, когда они не добавлены в converted_type
var need_recheck_where = new List<syntax_tree_node>(_class_definition.class_parents.Count);
// В случае partial классов можно (и желательно) указывать интерфейсы, которые уже были в предыдущем описании
// Поэтому проверять нужно только уникальное среди списка интерфейсов в этом описании
var curr_def_interfaces = new List<type_node>(need_recheck_where.Capacity);
// Отключаем проверки where для случая
// t1 = ...(t0<t1>)
context.skip_check_where_sections = true;
for (int i = 0; i < _class_definition.class_parents.Count; i++)
{
var syntax_tn = _class_definition.class_parents[i];
location loc = get_location(syntax_tn);
var tn = (type_node)ret.visit(syntax_tn);
if (tn.is_generic_type_definition || tn.is_generic_type_instance) need_recheck_where.Add(syntax_tn);
if ((tn.original_generic??tn).ForwardDeclarationOnly)
AddError(loc, "FORWARD_DECLARATION_{0}_AS_BASE_TYPE", tn.PrintableName);
if (tn.is_generic_parameter)
AddError(loc, "CAN_NOT_INHERIT_FROM_GENERIC_PARAMETER");
for (var curr = tn; curr!=null; curr=curr.base_type)
{
curr = curr.original_generic ?? curr;
if (curr == converted_type)
AddError(loc, "TYPE_{0}_INHERITS_SELF", converted_type.PrintableName);
}
// Если первый тип в списке - класс-предок
if (i==0 && !tn.IsInterface && _class_definition.keyword==PascalABCCompiler.SyntaxTree.class_keyword.Class)
{
if (tn.IsSealed)
AddError(loc, "PARENT_TYPE_IS_SEALED{0}", tn.PrintableName);
if (tn == SystemLibrary.SystemLibrary.value_type)
AddError(loc, "CAN_NOT_INHERIT_FROM_VALUE_TYPE");
if (tn.IsPointer)
AddError(loc, "CAN_NOT_INHERIT_FROM_POINTER");
if (tn.IsDelegate)
AddError(loc, "CAN_NOT_INHERIT_FROM_FUNCTION_TYPE");
if (tn == SystemLibrary.SystemLibrary.delegate_base_type || tn == SystemLibrary.SystemLibrary.system_delegate_type)
AddError(loc, "CAN_NOT_INHERIT_FROM_DELEGATE_TYPE");
converted_type.SetBaseType(tn);
need_set_base = false;
if (tn is common_type_node ctn && ctn.IsPartial)
inherited_from_partials_list.Add(converted_type);
continue;
}
// type_table.AddInterface проверяет что tn это интерфейс
type_table.AddInterface(converted_type, tn, loc);
if (curr_def_interfaces.Contains(tn))
AddError(loc, "INTERFACE_{0}_ALREADY_ADDED_TO_IMPLEMENTING_LIST", tn.PrintableName);
else
curr_def_interfaces.Add(tn);
}
context.skip_check_where_sections = false;
// Проверяем секции where предка/интерфейсов
// В самом конце, когда converted_type
// уже содержит всю информацию о предке и интерфейсах
foreach (var syntax_tn in need_recheck_where)
ret.visit(syntax_tn);
}
if (need_set_base)
{
var bt =
(converted_type.IsPartial ? converted_type.base_type : null) ??
SemanticRules.ClassBaseType;
converted_type.SetBaseType(bt);
}
if (_class_definition.keyword==PascalABCCompiler.SyntaxTree.class_keyword.Class)
foreach (generic_type_instance_info gti in generic_convertions.get_type_instances(converted_type))
{
if (!(gti.pseudo_instance.base_type != null && gti.pseudo_instance.base_type.is_generic_type_instance && converted_type.IsPartial))
gti.pseudo_instance.SetBaseType(converted_type.base_type);
}
switch (_class_definition.keyword)
{
case PascalABCCompiler.SyntaxTree.class_keyword.Class:
//if (context.converted_type.IsPartial)
// generic_convertions.remove_type_instances(context.converted_type);
if (context.converted_type.is_value || context.converted_type.IsInterface)
{
AddError(get_location(_class_definition), "FORWARD_DECLARATION_OF_{0}_MISMATCH_DECLARATION", context.converted_type.name);
}
if ((_class_definition.class_parents != null) && (_class_definition.class_parents.types.Count > 0))
{
if (context.converted_type.IsStatic)
AddError(get_location(_class_definition), "STATIC_CLASS_CANNOT_HAVE_PARENT");
context.skip_check_where_sections = true;
type_node tn = ret.visit(_class_definition.class_parents.types[0]);
context.skip_check_where_sections = false;
//if (tn == context.converted_type)
if (type_table.original_types_equals(tn, context.converted_type))
AddError(new UndefinedNameReference(tn.name, get_location(_class_definition.class_parents.types[0])));
if (tn.IsSealed)
AddError(get_location(_class_definition.class_parents.types[0]), "PARENT_TYPE_IS_SEALED{0}", tn.name);
if (tn == SystemLibrary.SystemLibrary.value_type)
{
AddError(get_location(_class_definition.class_parents.types[0]), "CAN_NOT_INHERIT_FROM_VALUE_TYPE");
}
if (tn.IsPointer)
{
AddError(get_location(_class_definition.class_parents.types[0]), "CAN_NOT_INHERIT_FROM_POINTER");
}
if (tn.IsDelegate)
{
AddError(get_location(_class_definition.class_parents.types[0]), "CAN_NOT_INHERIT_FROM_FUNCTION_TYPE");
}
if (tn == SystemLibrary.SystemLibrary.delegate_base_type || tn == SystemLibrary.SystemLibrary.system_delegate_type)
{
AddError(get_location(_class_definition.class_parents.types[0]), "CAN_NOT_INHERIT_FROM_DELEGATE_TYPE");
}
Hashtable used_interfs = new Hashtable();
if (tn is common_type_node && (tn as common_type_node).IsPartial)
inherited_from_partials_list.Add(context.converted_type);
//Если tn - это интерфейс
if (tn.IsInterface)
{
//Первым в списке предков идёт интерфейс, поэтому базовым будет object.
context.converted_type.SetBaseType(SemanticRules.ClassBaseType);
//if (converted_type.IsPartial)
// generic_convertions.remove_type_instances(converted_type);
if (converted_type.is_value || converted_type.IsInterface)
AddError(get_location(_class_definition), "FORWARD_DECLARATION_OF_{0}_MISMATCH_DECLARATION", converted_type.name);
converted_type.is_class = true;
//Добавляем интерфейс
used_interfs.Add(tn, tn);
type_table.AddInterface(context.converted_type, tn, get_location(_class_definition.class_parents.types[0]));
if (tn.is_generic_type_instance)
ret.visit(_class_definition.class_parents.types[0]);
}
else
{
if (convertion_data_and_alghoritms.ContainsForward(tn)) // SSM 20/05/2020 #2140
{
AddError(get_location(_class_definition.class_parents.types[0]), "FORWARD_DECLARATION_{0}_AS_BASE_TYPE", tn.name);
}
if (tn.is_generic_parameter)
{
AddError(get_location(_class_definition.class_parents.types[0]), "CAN_NOT_INHERIT_FROM_GENERIC_PARAMETER");
}
context.converted_type.SetBaseType(tn);
if (tn.is_generic_type_instance)
ret.visit(_class_definition.class_parents.types[0]);
var type_instances = generic_convertions.get_type_instances(context.converted_type);
if (type_instances != null)
foreach (generic_type_instance_info gti in type_instances)
{
if (!(gti.pseudo_instance.base_type != null && gti.pseudo_instance.base_type.is_generic_type_instance && context.converted_type.IsPartial))
gti.pseudo_instance.SetBaseType(tn);
}
}
//Теперь добавляем интерфейсы.
//Цикл с единицы, т.к. нулевой элемент уже был рассмотрен.
VisitAndAddInterfaces(context.converted_type, _class_definition.class_parents.types, 1, used_interfs);
//for (int i = 1; i < _class_definition.class_parents.types.Count; i++)
//{
// type_node interf = ret.visit(_class_definition.class_parents.types[i]);
// AddInterface(context.converted_type, interf, get_location(_class_definition.class_parents.types[i]));
//}
}
else
{
if (!(context.converted_type.IsPartial && context.converted_type.base_type != null && context.converted_type.base_type != SemanticRules.ClassBaseType))
context.converted_type.SetBaseType(SemanticRules.ClassBaseType);
else if (context.converted_type.IsPartial && context.converted_type.base_type != null)
context.converted_type.SetBaseType(context.converted_type.base_type);
}
context.converted_type.is_class = true;
if (_class_definition.body == null &&
(_class_definition.class_parents == null || _class_definition.class_parents.types.Count == 0))
{
if (context.converted_type.ForwardDeclarationOnly)
{
AddError(new NameRedefinition(context.converted_type.name, context.converted_type.Location, get_location(_class_definition)));
}
context.types_predefined.Add(context.converted_type);
context.converted_type.ForwardDeclarationOnly = true;
if (converted_type.ForwardDeclarationOnly)
AddError(new NameRedefinition(converted_type.name, converted_type.Location, get_location(_class_definition)));
converted_type.ForwardDeclarationOnly = true;
context.types_predefined.Add(converted_type);
}
else
{
context.converted_type.ForwardDeclarationOnly = false;
converted_type.ForwardDeclarationOnly = false;
if (_class_definition.body == null)
{
generate_inherit_constructors();
if (!context.converted_type.has_default_constructor)
if (!converted_type.has_default_constructor)
{
generate_default_constructor();
}
}
List<SyntaxTree.ident> names = new List<SyntaxTree.ident>();
List<SyntaxTree.type_definition> types = new List<SyntaxTree.type_definition>();
if ((_class_definition.IsAutoClass()))
if (_class_definition.IsAutoClass())
{
// Если снова возникнет ошибка с предками в автоклассах, то не раскомментировать эти строки, а подумать, как разрешить
//if (_class_definition.class_parents!=null)
@ -3888,6 +3927,8 @@ namespace PascalABCCompiler.TreeConverter
}
List<SyntaxTree.ident> names = new List<SyntaxTree.ident>();
List<SyntaxTree.type_definition> types = new List<SyntaxTree.type_definition>();
SyntaxTreeBuilder.AddMembersForAutoClass(_class_definition,ref names,ref types);
//if (names.Select(s => s.name.ToLower()).Distinct().Count() != names.Count)
@ -3928,92 +3969,61 @@ namespace PascalABCCompiler.TreeConverter
}
}
}
//if (!SemanticRules.OrderIndependedNames)
weak_node_test_and_visit(_class_definition.body);
//if (!SemanticRules.OrderIndependedNames)
weak_node_test_and_visit(_class_definition.body);
}
common_type_node converted_type = context.converted_type;
context.leave_block();
// Обязательно после context.leave_block, потому что там неявно-абстрактные методы помечают свой IsAbstract
if (converted_type.IsSealed && converted_type.IsAbstract && !converted_type.IsStatic)
{
if (converted_type.AbstractReason == null)
AddError(get_location(_class_definition), "ABSTRACT_CLASS_CANNOT_BE_SEALED");
else
AddError(get_location(_class_definition), converted_type.AbstractReason.Explanation, converted_type.name, converted_type.AbstractReason.ObjName);
return;
}
break;
case PascalABCCompiler.SyntaxTree.class_keyword.Record:
common_type_node ctn;
if (_record_created)
{
_record_created = false;
ctn = context.converted_type;
}
else
{
ctn = context.create_record_type(get_location(_class_definition), record_type_name);
if (record_is_generic)
{
context.create_generic_indicator(ctn);
visit_generic_params(ctn, _class_definition.template_args.idents);
}
else
{
if (_class_definition.template_args != null && _class_definition.template_args.idents != null)
{
AddError(get_location(_class_definition.template_args), "GENERIC_TYPE_NOT_ALLOWED_HERE");
}
}
visit_where_list(_class_definition.where_section);
}
if (context.CurrentScope is SymbolTable.BlockScope)
{
AddError(get_location(_class_definition), "RECORD_CANNOT_BE_DECLARED_IN_BLOCK");
ctn.internal_is_value = true;
converted_type.internal_is_value = true;
context.leave_record();
return_value(ctn);
return_value(converted_type);
return;
}
//Добавляем интерфейсы - предки.
if (_class_definition.class_parents != null)
{
VisitAndAddInterfaces(context.converted_type, _class_definition.class_parents.types, 0, new Hashtable());
//for (int i = 0; i < _class_definition.class_parents.types.Count; i++)
//{
// type_node interf = ret.visit(_class_definition.class_parents.types[i]);
// AddInterface(context.converted_type, interf, get_location(_class_definition.class_parents.types[i]));
//}
}
CheckWaitedRefTypes(ctn);
// "PMyRec = ^MyRec" перед описанием "MyRec"
CheckWaitedRefTypes(converted_type);
record_type_name = null;
record_is_generic = false;
context.converted_type.internal_is_value = true;
converted_type.internal_is_value = true;
if (_class_definition.body == null &&
(_class_definition.class_parents == null || _class_definition.class_parents.types.Count == 0))
{
if (context.converted_type.ForwardDeclarationOnly)
{
AddError(new NameRedefinition(context.converted_type.name, context.converted_type.Location, get_location(_class_definition)));
}
context.types_predefined.Add(context.converted_type);
context.converted_type.ForwardDeclarationOnly = true;
if (converted_type.ForwardDeclarationOnly)
AddError(new NameRedefinition(converted_type.name, converted_type.Location, get_location(_class_definition)));
context.types_predefined.Add(converted_type);
converted_type.ForwardDeclarationOnly = true;
}
else
{
context.converted_type.ForwardDeclarationOnly = false;
converted_type.ForwardDeclarationOnly = false;
weak_node_test_and_visit(_class_definition.body);
}
/*if (_class_definition.body != null)
hard_node_test_and_visit(_class_definition.body);
else
{
context.converted_type.ForwardDeclarationOnly = true;
converted_type.ForwardDeclarationOnly = true;
}*/
/*if (_class_definition.body != null)
foreach (SyntaxTree.var_def_statement var in (_class_definition.body.class_def_blocks[0].members))
@ -4021,32 +4031,22 @@ namespace PascalABCCompiler.TreeConverter
hard_node_test_and_visit(var);
}*/
context.leave_record();
return_value(ctn);
return;
return_value(converted_type);
break;
//ssyy owns
case PascalABCCompiler.SyntaxTree.class_keyword.Interface:
if (context.converted_type.is_value || !context.converted_type.IsInterface)
if (converted_type.is_value || !converted_type.IsInterface)
{
AddError(get_location(_class_definition), "FORWARD_DECLARATION_OF_{0}_MISMATCH_DECLARATION", context.converted_type.name);
AddError(get_location(_class_definition), "FORWARD_DECLARATION_OF_{0}_MISMATCH_DECLARATION", converted_type.name);
}
if (SemanticRules.GenerateNativeCode)
context.converted_type.SetBaseType(SemanticRules.ClassBaseType);
converted_type.SetBaseType(SemanticRules.ClassBaseType);
else
context.converted_type.SetBaseType(SystemLibrary.SystemLibrary.object_type);
context.converted_type.IsInterface = true;
context.converted_type.is_class = true;
//Добавляем интерфейсы - предки.
if (_class_definition.class_parents != null)
{
VisitAndAddInterfaces(context.converted_type, _class_definition.class_parents.types, 0, new Hashtable());
//for (int i = 0; i < _class_definition.class_parents.types.Count; i++)
//{
// type_node interf = ret.visit(_class_definition.class_parents.types[i]);
// AddInterface(context.converted_type, interf, get_location(_class_definition.class_parents.types[i]));
//}
}
converted_type.SetBaseType(SystemLibrary.SystemLibrary.object_type);
converted_type.IsInterface = true;
converted_type.is_class = true;
InitInterfaceScope(context.converted_type);
InitInterfaceScope(converted_type);
//if (_class_definition.body == null)
//{
@ -4056,43 +4056,27 @@ namespace PascalABCCompiler.TreeConverter
if (_class_definition.body == null &&
(_class_definition.class_parents == null || _class_definition.class_parents.types.Count == 0))
{
if (context.converted_type.ForwardDeclarationOnly)
if (converted_type.ForwardDeclarationOnly)
{
AddError(new NameRedefinition(context.converted_type.name, context.converted_type.Location, get_location(_class_definition)));
AddError(new NameRedefinition(converted_type.name, converted_type.Location, get_location(_class_definition)));
}
context.types_predefined.Add(context.converted_type);
context.converted_type.ForwardDeclarationOnly = true;
context.types_predefined.Add(converted_type);
converted_type.ForwardDeclarationOnly = true;
}
else
{
context.converted_type.ForwardDeclarationOnly = false;
converted_type.ForwardDeclarationOnly = false;
weak_node_test_and_visit(_class_definition.body);
}
//hard_node_test_and_visit(_class_definition.body);
context.leave_block();
return;
break;
//\ssyy owns
default:
throw new NotSupportedError(get_location(_class_definition));
}
}
private void VisitAndAddInterfaces(common_type_node t, List<SyntaxTree.named_type_reference> types, int start, Hashtable used_interfaces)
{
for (int i = start; i < types.Count; i++)
{
type_node interf = ret.visit(types[i]);
location loc = get_location(types[i]);
if (used_interfaces[interf] != null)
{
AddError(loc, "INTERFACE_{0}_ALREADY_ADDED_TO_IMPLEMENTING_LIST", interf.PrintableName);
}
used_interfaces.Add(interf, interf);
check_cycle_interface_inheritance(t, interf, new List<common_type_node>());
type_table.AddInterface(t, interf, loc);
}
}
private void InitInterfaceScope(common_type_node ctn)
{
List<SymbolTable.Scope> interf_scopes = new List<SymbolTable.Scope>(ctn.ImplementingInterfaces.Count);
@ -12782,30 +12766,6 @@ namespace PascalABCCompiler.TreeConverter
}
}
private void check_cycle_interface_inheritance(common_type_node cnode, type_node base_of_cnode, List<common_type_node> interfaces)
{
// Для интерфейсов всё это излишне. Поскольку нельзя использовать предописанные интерфейсы в списке наследования, то
// циклически интерфейс может наследовать только от себя. Поэтому достаточно проверять нерекурсивно свой список ImplementingInterfaces и если там есть этот интерфейс, то ошибка
if (!cnode.IsInterface)
return;
interfaces.Add(cnode);
common_type_node bt = base_of_cnode as common_type_node;
if (bt != null && bt.original_generic != null)
bt = bt.original_generic as common_type_node;
if (bt != null)
{
if (interfaces.Contains(bt))
{
AddError(bt.loc, "TYPE_{0}_DERIVED_FROM_ITSELF", bt.PrintableName);
}
interfaces.Add(bt);
foreach (var tn in bt.ImplementingInterfaces)
{
check_cycle_interface_inheritance(bt, tn as type_node, interfaces);
}
}
}
private void check_where_from_base_class(common_type_node ctn)
{
if (ctn.base_type != null && ctn.base_type.is_generic_type_instance && ctn.is_generic_type_definition)

View file

@ -168,7 +168,7 @@ namespace PascalABCCompiler.TreeRealization
// tn - не generic параметр - закомментировал
if (base_type != tn && !type_table.is_derived(base_type, tn) /*&& !tn.is_generic_parameter*/)
{
return new SimpleSemanticError(null, "PARAMETER_{0}_MUST_BE_DERIVED_FROM_{1}", tn.PrintableName, base_type.name);
return new SimpleSemanticError(null, "PARAMETER_{0}_MUST_BE_DERIVED_FROM_{1}", tn.PrintableName, base_type.PrintableName);
}
}
if (gpe.is_class && !tn.is_class)
@ -186,7 +186,7 @@ namespace PascalABCCompiler.TreeRealization
(tn.ImplementingInterfaces == null ||
!type_table.is_derived(di, tn)))
{
return new SimpleSemanticError(null, "PARAMETER_{0}_MUST_IMPLEMENT_INTERFACE_{1}", tn.PrintableName, di.name);
return new SimpleSemanticError(null, "PARAMETER_{0}_MUST_IMPLEMENT_INTERFACE_{1}", tn.PrintableName, di.PrintableName);
}
}
if (tn.IsStatic)

View file

@ -352,16 +352,15 @@ namespace PascalABCCompiler.TreeRealization
{
throw new TreeConverter.SimpleSemanticError(loc, "FORWARD_DECLARATION_{0}_AS_IMPLEMENTING_INTERFACE", _interface.name);
}
if (!cnode.ImplementingInterfaces.Contains(_interface))
if (cnode.ImplementingInterfaces.Contains(_interface))
return;
cnode.ImplementingInterfaces.Add(_interface);
foreach (type_node tn in _interface.ImplementingInterfaces)
{
cnode.ImplementingInterfaces.Add(_interface);
foreach (type_node tn in _interface.ImplementingInterfaces)
{
if (!cnode.ImplementingInterfaces.Contains(tn))
{
cnode.ImplementingInterfaces.Add(tn);
}
}
if (cnode.ImplementingInterfaces.Contains(tn))
continue;
cnode.ImplementingInterfaces.Add(tn);
}
}

View file

@ -139,8 +139,8 @@ OPERATOR_RETURN_TYPE_UNDEFINED_{0}=Return type of operator {0} is not defined an
STRUCT_TYPE_DEFINITION_IN_AUTO_CLASS=Field types in auto classes cannot be record or array definition
EXTERNAL_METHOD_SHOULD_BE_STATIC=external-methods should be static
ABSTRACT_CLASS_CANNOT_BE_SEALED=Abstract classes can not be sealed
ABSTRACT_CLASS_CANNOT_BE_SEALED_BECAUSE_METHOD_NOT_IMPLEMENTED=Class {0} is abstract and connot be sealed, because method {1} not implement
ABSTRACT_CLASS_CANNOT_BE_SEALED_BECAUSE_PROPERTIE_NOT_IMPLEMENTED=Class {0} is abstract and connot be sealed, because propertie {1} not implement
ABSTRACT_CLASS_CANNOT_BE_SEALED_BECAUSE_METHOD_NOT_IMPLEMENTED=Class {0} is abstract and connot be sealed, because method {1} not implemented
ABSTRACT_CLASS_CANNOT_BE_SEALED_BECAUSE_PROPERTIE_NOT_IMPLEMENTED=Class {0} is abstract and connot be sealed, because propertie {1} not implemented
ABSTRACT_CLASS_CANNOT_BE_SEALED_BECAUSE_ABSTRACT_PROPERTIE=Class {0} is abstract and connot be sealed, because propertie {1} is abstract
EXPRESSION_EXPECTED=Expression expected
CLASS_ATTRIBUTE_NOT_ALLOWED_IN_CLASS_PREDEFINTIONS=Can not declare class attributes in class predefintions

View file

@ -94,6 +94,7 @@ TRIANGLE_BRACKETS_NOT_ALLOWED_WITH_COMMON_FUNCTIONS=Non-generic methods cannot b
FUNCTION_{0}_DEPEND_FROM_{1}_TYPE_PARAMS=The number of type parameters in generic subprogramm '{0}' must be {1}
WHERE_SECTION_MUST_BE_ONLY_IN_FIRST_DECLARATION=where-section is not valid in this context
CAN_NOT_INHERIT_FROM_GENERIC_PARAMETER=Cannot derive from generic parameter
TYPE_{0}_INHERITS_SELF=Type '{0}' inherits from itself
GENERIC_FUNCTION_{0}_CAN_NOT_BE_CALLED_WITH_THESE_PARAMETERS=Cannot call the generic function '{0}' with these arguments
CAN_NOT_DEDUCE_TYPE_PARAMS_FROM_CALL_{0}=The type arguments for method '{0}' cannot be inferred from the usage. Try specifying the type arguments explicitly
CAN_NOT_CALL_ANY_GENERIC_FUNCTION_{0}_WITH_THESE_PARAMETERS=The best overloaded method match for '{0}' has some invalid arguments

View file

@ -94,6 +94,7 @@ TRIANGLE_BRACKETS_NOT_ALLOWED_WITH_COMMON_FUNCTIONS=Спецификация п
FUNCTION_{0}_DEPEND_FROM_{1}_TYPE_PARAMS=Число типов-параметров в спецификации обобщённой подпрограммы {0} должно быть равно {1}
WHERE_SECTION_MUST_BE_ONLY_IN_FIRST_DECLARATION=Секцию where следует указывать только в предописании (предописание найдено)
CAN_NOT_INHERIT_FROM_GENERIC_PARAMETER=Нельзя наследовать от generic-параметра
TYPE_{0}_INHERITS_SELF=Тип '{0}' наследует от самого себя
GENERIC_FUNCTION_{0}_CAN_NOT_BE_CALLED_WITH_THESE_PARAMETERS=Обобщённая функция {0} не может быть вызвана с данным набором фактических параметров
CAN_NOT_DEDUCE_TYPE_PARAMS_FROM_CALL_{0}=Невозможно вывести типы-параметры обобщённой подпрограммы {0} (укажите типы-параметры явно)
CAN_NOT_CALL_ANY_GENERIC_FUNCTION_{0}_WITH_THESE_PARAMETERS=С данным списком формальных параметров невозможно вызвать ни одну из перегруженных generic-подпрограмм {0}

View file

@ -91,6 +91,7 @@ TRIANGLE_BRACKETS_NOT_ALLOWED_WITH_COMMON_FUNCTIONS=Специфікація з
FUNCTION_{0}_DEPEND_FROM_{1}_TYPE_PARAMS=Число типів-параметрів у специфікації generic-підпрограми {0} має дорівнювати {1}
WHERE_SECTION_MUST_BE_ONLY_IN_FIRST_DECLARATION=Секцію where слід вказувати тільки в передопису (предопис знайдено)
CAN_NOT_INHERIT_FROM_GENERIC_PARAMETER=Не можна успадкувати від generic-параметру
TYPE_{0}_INHERITS_SELF=Тип '{0}' успадковує від себе
GENERIC_FUNCTION_{0}_CAN_NOT_BE_CALLED_WITH_THESE_PARAMETERS=Generic-функція {0} не може бути викликана з даними набором фактичних параметрів
CAN_NOT_DEDUCE_TYPE_PARAMS_FROM_CALL_{0}=Неможливо вивести типи-параметри generic-підпрограми {0} (вкажіть типи-параметри явно)
CAN_NOT_CALL_ANY_GENERIC_FUNCTION_{0}_WITH_THESE_PARAMETERS=З даним списком формальних параметрів неможливо викликати жодну з перевантажених generic-підпрограм {0}