diff --git a/src/AST/Class.cs b/src/AST/Class.cs index 9a1d25ab..b1893f71 100644 --- a/src/AST/Class.cs +++ b/src/AST/Class.cs @@ -201,6 +201,22 @@ namespace CppSharp.AST } } + public Method GetRootBaseMethod(Method @override) + { + return (from @base in Bases + let baseMethod = ( + from method in @base.Class.Methods + where + method.Name == @override.Name && + method.ReturnType == @override.ReturnType && + method.Parameters.Count == @override.Parameters.Count && + method.Parameters.SequenceEqual(@override.Parameters, + new ParameterTypeComparer()) + select method).FirstOrDefault() + let rootBaseMethod = @base.Class.GetRootBaseMethod(@override) + select rootBaseMethod ?? baseMethod).FirstOrDefault(); + } + public override T Visit(IDeclVisitor visitor) { return visitor.VisitClassDecl(this); diff --git a/src/AST/Function.cs b/src/AST/Function.cs index 04a20a0a..f922218c 100644 --- a/src/AST/Function.cs +++ b/src/AST/Function.cs @@ -60,6 +60,19 @@ namespace CppSharp.AST } } + public class ParameterTypeComparer : IEqualityComparer + { + public bool Equals(Parameter x, Parameter y) + { + return x.QualifiedType == y.QualifiedType; + } + + public int GetHashCode(Parameter obj) + { + return obj.Type.GetHashCode(); + } + } + public enum FunctionSynthKind { None, diff --git a/src/Generator/Generators/CSharp/CSharpTextTemplate.cs b/src/Generator/Generators/CSharp/CSharpTextTemplate.cs index e2b76feb..9deb05d9 100644 --- a/src/Generator/Generators/CSharp/CSharpTextTemplate.cs +++ b/src/Generator/Generators/CSharp/CSharpTextTemplate.cs @@ -1483,7 +1483,7 @@ namespace CppSharp.Generators.CSharp PushBlock(CSharpBlockKind.Method); GenerateDeclarationCommon(method); - switch (method.Access) + switch (GetValidMethodAccess(method, @class)) { case AccessSpecifier.Public: Write(Driver.Options.GenerateAbstractImpls && @class.IsAbstract @@ -1578,6 +1578,20 @@ namespace CppSharp.Generators.CSharp PopBlock(NewLineKind.BeforeNextBlock); } + private static AccessSpecifier GetValidMethodAccess(Method method, Class @class) + { + switch (method.Access) + { + case AccessSpecifier.Public: + return @class.IsAbstract && method.IsConstructor ? + AccessSpecifier.Protected : AccessSpecifier.Public; + case AccessSpecifier.Protected: + return method.IsOverride ? + @class.GetRootBaseMethod(method).Access : AccessSpecifier.Protected; + } + return AccessSpecifier.Private; + } + private void GenerateVirtualTableFunctionCall(Function method, Class @class) { string delegateId; diff --git a/src/Generator/Utils/ParameterTypeComparer.cs b/src/Generator/Utils/ParameterTypeComparer.cs deleted file mode 100644 index a8740cdc..00000000 --- a/src/Generator/Utils/ParameterTypeComparer.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Collections.Generic; -using CppSharp.AST; - -namespace CppSharp.Utils -{ - public class ParameterTypeComparer : IEqualityComparer - { - public bool Equals(Parameter x, Parameter y) - { - return x.QualifiedType == y.QualifiedType; - } - - public int GetHashCode(Parameter obj) - { - return obj.Type.GetHashCode(); - } - } -}