Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit cf4d59a

Browse files
committed
1783 Implement Interface And Inherit Class: Cleanup
- Added exceptions during unintended use of superclasses. - Removed invalid comment. - Improved exceptions from MetaType slightly.
1 parent 4f42458 commit cf4d59a

File tree

1 file changed

+34
-5
lines changed

1 file changed

+34
-5
lines changed

src/runtime/Types/MetaType.cs

+34-5
Original file line numberDiff line numberDiff line change
@@ -90,16 +90,33 @@ public static NewReference tp_new(BorrowedReference tp, BorrowedReference args,
9090
var baseTypes = new List<ClassBase>();
9191

9292
var baseClassCount = Runtime.PyTuple_Size(bases);
93+
if (baseClassCount == 0)
94+
{
95+
return Exceptions.RaiseTypeError("zero base classes ");
96+
}
9397

9498
for (nint i = 0; i < baseClassCount; i++)
9599
{
96100
var baseTypeIt = Runtime.PyTuple_GetItem(bases, (int)i);
97101

98102
if (GetManagedObject(baseTypeIt) is ClassBase classBaseIt)
99103
{
100-
if (classBaseIt.type.Valid && classBaseIt.type.Value.IsInterface)
104+
if (!classBaseIt.type.Valid)
105+
{
106+
return Exceptions.RaiseTypeError("Invalid type used as a super type.");
107+
}
108+
if (classBaseIt.type.Value.IsInterface)
109+
{
101110
interfaces.Add(classBaseIt.type.Value);
102-
else baseTypes.Add(classBaseIt);
111+
}
112+
else
113+
{
114+
baseTypes.Add(classBaseIt);
115+
}
116+
}
117+
else
118+
{
119+
return Exceptions.RaiseTypeError("Non .NET type used as super class for meta type. This is not supported.");
103120
}
104121
}
105122
// if the base type count is 0, there might still be interfaces to implement.
@@ -111,7 +128,20 @@ public static NewReference tp_new(BorrowedReference tp, BorrowedReference args,
111128
// Multiple inheritance is not supported, unless the other types are interfaces
112129
if (baseTypes.Count > 1)
113130
{
114-
return Exceptions.RaiseTypeError("cannot use multiple inheritance with managed classes");
131+
var types = string.Join(", ", baseTypes.Select(baseType => baseType.type.Value));
132+
return Exceptions.RaiseTypeError($"Multiple inheritance with managed classes cannot be used. Types: {types} ");
133+
}
134+
135+
// check if the list of interfaces contains no duplicates.
136+
if (interfaces.Distinct().Count() != interfaces.Count)
137+
{
138+
// generate a string containing the problematic types.
139+
var duplicateTypes = interfaces.GroupBy(type => type)
140+
.Where(typeGroup => typeGroup.Count() > 1)
141+
.Select(typeGroup => typeGroup.Key);
142+
var duplicateTypesString = string.Join(", ", duplicateTypes);
143+
144+
return Exceptions.RaiseTypeError($"An interface can only be implemented once. Duplicate types: {duplicateTypesString}");
115145
}
116146

117147
var cb = baseTypes[0];
@@ -133,8 +163,7 @@ public static NewReference tp_new(BorrowedReference tp, BorrowedReference args,
133163
return Exceptions.RaiseTypeError("subclasses of managed classes do not support __slots__");
134164
}
135165

136-
// If the base class has a parameterless constructor, or
137-
// if __assembly__ or __namespace__ are in the class dictionary then create
166+
// If __assembly__ or __namespace__ are in the class dictionary then create
138167
// a managed sub type.
139168
// This creates a new managed type that can be used from .net to call back
140169
// into python.

0 commit comments

Comments
 (0)