Browse Source

Fix/parser improvements (#1919)

* Parser improvements

* Fix AST Converter missing conversion data

* Fix bug in test code

Can't return `T();` if `T` is a const reference type.

* Fix other test compile bug

It's kinda weird to call it pure virtual and then implement it anyway no?

* Fix test compiler error

Don't skip function bodies to force template instantiations

* Fix clang assert
pull/1920/head
Jelle 4 months ago committed by GitHub
parent
commit
88204f7fb7
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
  1. 16
      src/CppParser/Bootstrap/StmtCodeGenerators.cs
  2. 3
      src/CppParser/ParseExpr.cpp
  3. 31
      src/CppParser/Parser.cpp
  4. 12
      src/Generator/Passes/SymbolsCodeGenerator.cs
  5. 363
      src/Parser/ASTConverter.cs
  6. 15
      tests/dotnet/CSharp/CSharp.Gen.cs
  7. 5
      tests/dotnet/CSharp/CSharpTemplates.h
  8. 6
      tests/dotnet/Common/Common.h

16
src/CppParser/Bootstrap/StmtCodeGenerators.cs

@ -341,8 +341,20 @@ namespace CppSharp
WriteLine($"_S->{fieldName} = static_cast<AST::{typeName}>(" + WriteLine($"_S->{fieldName} = static_cast<AST::{typeName}>(" +
$"WalkStatement(S->{methodName}()));"); $"WalkStatement(S->{methodName}()));");
else if (typeName.Contains("Expr")) else if (typeName.Contains("Expr"))
WriteLine($"_S->{fieldName} = static_cast<AST::{typeName}>(" + {
$"WalkExpression(S->{methodName}()));"); var expr = $"_S->{fieldName} = static_cast<AST::{typeName}>(WalkExpression(S->{methodName}()));";
if (fieldName == "base" && typeName is "CXXDependentScopeMemberExpr")
{
// Clang asserts that 'getBase()' is not called when 'isImplicitAccess()' returns true
WriteLine("if (!S->isImplicitAccess())");
WriteLineIndent(expr);
}
else
{
WriteLine(expr);
}
}
else if (fieldName == "guidDecl") else if (fieldName == "guidDecl")
WriteLine($"_S->{fieldName} = S->getGuidDecl()->getNameAsString();"); WriteLine($"_S->{fieldName} = S->getGuidDecl()->getNameAsString();");
else if (typeName.Contains("Decl") || typeName.Contains("Method") || else if (typeName.Contains("Decl") || typeName.Contains("Method") ||

3
src/CppParser/ParseExpr.cpp

@ -2426,7 +2426,8 @@ AST::Expr* Parser::WalkExpression(const clang::Expr* Expr)
_S->refersToMatrixElement = S->refersToMatrixElement(); _S->refersToMatrixElement = S->refersToMatrixElement();
_S->hasPlaceholderType = S->hasPlaceholderType(); _S->hasPlaceholderType = S->hasPlaceholderType();
_S->isImplicitAccess = S->isImplicitAccess(); _S->isImplicitAccess = S->isImplicitAccess();
_S->base = static_cast<AST::Expr*>(WalkExpression(S->getBase())); if (!S->isImplicitAccess())
_S->base = static_cast<AST::Expr*>(WalkExpression(S->getBase()));
_S->baseType = GetQualifiedType(S->getBaseType()); _S->baseType = GetQualifiedType(S->getBaseType());
_S->isArrow = S->isArrow(); _S->isArrow = S->isArrow();
_S->firstQualifierFoundInScope = static_cast<AST::Declaration*>(WalkDeclaration(S->getFirstQualifierFoundInScope())); _S->firstQualifierFoundInScope = static_cast<AST::Declaration*>(WalkDeclaration(S->getFirstQualifierFoundInScope()));

31
src/CppParser/Parser.cpp

@ -165,6 +165,12 @@ Parser::Parser(CppParserOptions* Opts)
{ {
supportedStdTypes.insert("allocator"); supportedStdTypes.insert("allocator");
supportedStdTypes.insert("basic_string"); supportedStdTypes.insert("basic_string");
walkedNamespaces.reserve(8192);
walkedTypeTemplateParameters.reserve(8192);
walkedTemplateTemplateParameters.reserve(32);
walkedNonTypeTemplateParameters.reserve(1024);
walkedParameters.reserve(65536);
} }
LayoutField Parser::WalkVTablePointer(Class* Class, LayoutField Parser::WalkVTablePointer(Class* Class,
@ -424,27 +430,23 @@ void Parser::Setup(bool Compile)
if (opts->verbose) if (opts->verbose)
HSOpts.Verbose = true; HSOpts.Verbose = true;
for (unsigned I = 0, E = opts->IncludeDirs.size(); I != E; ++I) for (const auto& s : opts->IncludeDirs)
{ {
const auto& s = opts->IncludeDirs[I];
HSOpts.AddPath(s, frontend::Angled, false, false); HSOpts.AddPath(s, frontend::Angled, false, false);
} }
for (unsigned I = 0, E = opts->SystemIncludeDirs.size(); I != E; ++I) for (const auto& s : opts->SystemIncludeDirs)
{ {
const auto& s = opts->SystemIncludeDirs[I];
HSOpts.AddPath(s, frontend::System, false, false); HSOpts.AddPath(s, frontend::System, false, false);
} }
for (unsigned I = 0, E = opts->Defines.size(); I != E; ++I) for (const auto& define : opts->Defines)
{ {
const auto& define = opts->Defines[I];
PPOpts.addMacroDef(define); PPOpts.addMacroDef(define);
} }
for (unsigned I = 0, E = opts->Undefines.size(); I != E; ++I) for (const auto& undefine : opts->Undefines)
{ {
const auto& undefine = opts->Undefines[I];
PPOpts.addMacroUndef(undefine); PPOpts.addMacroUndef(undefine);
} }
@ -480,8 +482,7 @@ void Parser::Setup(bool Compile)
} }
} }
if (TC) delete TC;
delete TC;
// Enable preprocessing record. // Enable preprocessing record.
PPOpts.DetailedRecord = true; PPOpts.DetailedRecord = true;
@ -2537,7 +2538,7 @@ Type* Parser::WalkType(clang::QualType QualType, const clang::TypeLoc* TL, bool
EnumDecl* ED = ET->getDecl(); EnumDecl* ED = ET->getDecl();
auto TT = new AST::TagType(); auto TT = new AST::TagType();
TT->declaration = TT->declaration = WalkDeclaration(ED); TT->declaration = WalkDeclaration(ED);
Ty = TT; Ty = TT;
break; break;
@ -4430,8 +4431,8 @@ Declaration* Parser::WalkDeclaration(const clang::Decl* D)
{ {
auto MD = cast<CXXMethodDecl>(D); auto MD = cast<CXXMethodDecl>(D);
Decl = WalkMethodCXX(MD); Decl = WalkMethodCXX(MD);
if (Decl == nullptr) if (!Decl)
return Decl; return nullptr;
auto NS = GetNamespace(MD); auto NS = GetNamespace(MD);
Decl->_namespace = NS; Decl->_namespace = NS;
@ -4609,7 +4610,7 @@ void Parser::SetupLLVMCodegen()
c->getHeaderSearchOpts(), c->getPreprocessorOpts(), c->getHeaderSearchOpts(), c->getPreprocessorOpts(),
c->getCodeGenOpts(), *LLVMModule, c->getDiagnostics())); c->getCodeGenOpts(), *LLVMModule, c->getDiagnostics()));
codeGenTypes.reset(new clang::CodeGen::CodeGenTypes(*CGM.get())); codeGenTypes.reset(new clang::CodeGen::CodeGenTypes(*CGM));
} }
bool Parser::SetupSourceFiles(const std::vector<std::string>& SourceFiles, bool Parser::SetupSourceFiles(const std::vector<std::string>& SourceFiles,
@ -4710,7 +4711,7 @@ ParserResult* Parser::Parse(const std::vector<std::string>& SourceFiles)
DiagClient->BeginSourceFile(c->getLangOpts(), &c->getPreprocessor()); DiagClient->BeginSourceFile(c->getLangOpts(), &c->getPreprocessor());
ParseAST(c->getSema()); ParseAST(c->getSema(), opts->verbose, opts->skipFunctionBodies);
DiagClient->EndSourceFile(); DiagClient->EndSourceFile();

12
src/Generator/Passes/SymbolsCodeGenerator.cs

@ -162,8 +162,7 @@ namespace CppSharp.Passes
bool isAbstract = ((Class)method.Namespace).IsAbstract; bool isAbstract = ((Class)method.Namespace).IsAbstract;
if (method.Access == AccessSpecifier.Protected || isAbstract) if (method.Access == AccessSpecifier.Protected || isAbstract)
{ {
Write($@"{{ ::new ({Helpers.InstanceField}) { Write($@"{{ ::new ({Helpers.InstanceField}) {wrapper}{method.Namespace.Name}({@params}); }}");
wrapper}{method.Namespace.Name}({@params}); }}");
WriteLine(!isAbstract ? " };" : string.Empty); WriteLine(!isAbstract ? " };" : string.Empty);
} }
else else
@ -210,12 +209,10 @@ namespace CppSharp.Passes
{ {
string @class = wrapper + method.Namespace.Name; string @class = wrapper + method.Namespace.Name;
WriteLine($"() {{ this->~{@class}(); }} }};"); WriteLine($"() {{ this->~{@class}(); }} }};");
Write($@"extern ""C"" {GetExporting()}void {wrapper}({ Write($@"extern ""C"" {GetExporting()}void {wrapper}({@class}* {instance}) {{ {instance}->{wrapper}Protected");
@class}* {instance}) {{ {instance}->{wrapper}Protected");
} }
else else
Write($@"({$"{@namespace}*{instance}"}) {{ { Write($@"({$"{@namespace}*{instance}"}) {{ {instance}->~{method.Namespace.Name}");
instance}->~{method.Namespace.Name}");
WriteLine("(); }"); WriteLine("(); }");
} }
@ -238,8 +235,7 @@ namespace CppSharp.Passes
var method = function as Method; var method = function as Method;
if (function.Namespace.Access == AccessSpecifier.Protected) if (function.Namespace.Access == AccessSpecifier.Protected)
Write($@"class {wrapper}{function.Namespace.Name} : public { Write($@"class {wrapper}{function.Namespace.Name} : public {function.Namespace.Namespace.Visit(cppTypePrinter)} {{ ");
function.Namespace.Namespace.Visit(cppTypePrinter)} {{ ");
string variable = $@"({(method?.IsStatic == false ? string variable = $@"({(method?.IsStatic == false ?
(@namespace + "::") : string.Empty)}*{wrapper}){signature}"; (@namespace + "::") : string.Empty)}*{wrapper}){signature}";

363
src/Parser/ASTConverter.cs

@ -41,100 +41,100 @@ namespace CppSharp
switch (type.Kind) switch (type.Kind)
{ {
case TypeKind.Tag: case TypeKind.Tag:
{ {
var _type = TagType.__CreateInstance(type.__Instance); var _type = TagType.__CreateInstance(type.__Instance);
return VisitTag(_type); return VisitTag(_type);
} }
case TypeKind.Array: case TypeKind.Array:
{ {
var _type = ArrayType.__CreateInstance(type.__Instance); var _type = ArrayType.__CreateInstance(type.__Instance);
return VisitArray(_type); return VisitArray(_type);
} }
case TypeKind.Function: case TypeKind.Function:
{ {
var _type = FunctionType.__CreateInstance(type.__Instance); var _type = FunctionType.__CreateInstance(type.__Instance);
return VisitFunction(_type); return VisitFunction(_type);
} }
case TypeKind.Pointer: case TypeKind.Pointer:
{ {
var _type = PointerType.__CreateInstance(type.__Instance); var _type = PointerType.__CreateInstance(type.__Instance);
return VisitPointer(_type); return VisitPointer(_type);
} }
case TypeKind.MemberPointer: case TypeKind.MemberPointer:
{ {
var _type = MemberPointerType.__CreateInstance(type.__Instance); var _type = MemberPointerType.__CreateInstance(type.__Instance);
return VisitMemberPointer(_type); return VisitMemberPointer(_type);
} }
case TypeKind.Typedef: case TypeKind.Typedef:
{ {
var _type = TypedefType.__CreateInstance(type.__Instance); var _type = TypedefType.__CreateInstance(type.__Instance);
return VisitTypedef(_type); return VisitTypedef(_type);
} }
case TypeKind.Attributed: case TypeKind.Attributed:
{ {
var _type = AttributedType.__CreateInstance(type.__Instance); var _type = AttributedType.__CreateInstance(type.__Instance);
return VisitAttributed(_type); return VisitAttributed(_type);
} }
case TypeKind.Decayed: case TypeKind.Decayed:
{ {
var _type = DecayedType.__CreateInstance(type.__Instance); var _type = DecayedType.__CreateInstance(type.__Instance);
return VisitDecayed(_type); return VisitDecayed(_type);
} }
case TypeKind.TemplateSpecialization: case TypeKind.TemplateSpecialization:
{ {
var _type = TemplateSpecializationType.__CreateInstance(type.__Instance); var _type = TemplateSpecializationType.__CreateInstance(type.__Instance);
return VisitTemplateSpecialization(_type); return VisitTemplateSpecialization(_type);
} }
case TypeKind.DependentTemplateSpecialization: case TypeKind.DependentTemplateSpecialization:
{ {
var _type = DependentTemplateSpecializationType.__CreateInstance(type.__Instance); var _type = DependentTemplateSpecializationType.__CreateInstance(type.__Instance);
return VisitDependentTemplateSpecialization(_type); return VisitDependentTemplateSpecialization(_type);
} }
case TypeKind.TemplateParameter: case TypeKind.TemplateParameter:
{ {
var _type = TemplateParameterType.__CreateInstance(type.__Instance); var _type = TemplateParameterType.__CreateInstance(type.__Instance);
return VisitTemplateParameter(_type); return VisitTemplateParameter(_type);
} }
case TypeKind.TemplateParameterSubstitution: case TypeKind.TemplateParameterSubstitution:
{ {
var _type = TemplateParameterSubstitutionType.__CreateInstance(type.__Instance); var _type = TemplateParameterSubstitutionType.__CreateInstance(type.__Instance);
return VisitTemplateParameterSubstitution(_type); return VisitTemplateParameterSubstitution(_type);
} }
case TypeKind.InjectedClassName: case TypeKind.InjectedClassName:
{ {
var _type = InjectedClassNameType.__CreateInstance(type.__Instance); var _type = InjectedClassNameType.__CreateInstance(type.__Instance);
return VisitInjectedClassName(_type); return VisitInjectedClassName(_type);
} }
case TypeKind.DependentName: case TypeKind.DependentName:
{ {
var _type = DependentNameType.__CreateInstance(type.__Instance); var _type = DependentNameType.__CreateInstance(type.__Instance);
return VisitDependentName(_type); return VisitDependentName(_type);
} }
case TypeKind.Builtin: case TypeKind.Builtin:
{ {
var _type = BuiltinType.__CreateInstance(type.__Instance); var _type = BuiltinType.__CreateInstance(type.__Instance);
return VisitBuiltin(_type); return VisitBuiltin(_type);
} }
case TypeKind.PackExpansion: case TypeKind.PackExpansion:
{ {
var _type = PackExpansionType.__CreateInstance(type.__Instance); var _type = PackExpansionType.__CreateInstance(type.__Instance);
return VisitPackExpansion(_type); return VisitPackExpansion(_type);
} }
case TypeKind.UnaryTransform: case TypeKind.UnaryTransform:
{ {
var _type = UnaryTransformType.__CreateInstance(type.__Instance); var _type = UnaryTransformType.__CreateInstance(type.__Instance);
return VisitUnaryTransform(_type); return VisitUnaryTransform(_type);
} }
case TypeKind.UnresolvedUsing: case TypeKind.UnresolvedUsing:
{ {
var _type = UnresolvedUsingType.__CreateInstance(type.__Instance); var _type = UnresolvedUsingType.__CreateInstance(type.__Instance);
return VisitUnresolvedUsing(_type); return VisitUnresolvedUsing(_type);
} }
case TypeKind.Vector: case TypeKind.Vector:
{ {
var _type = VectorType.__CreateInstance(type.__Instance); var _type = VectorType.__CreateInstance(type.__Instance);
return VisitVector(_type); return VisitVector(_type);
} }
} }
throw new ArgumentOutOfRangeException(); throw new ArgumentOutOfRangeException();
@ -182,135 +182,135 @@ namespace CppSharp
switch (decl.Kind) switch (decl.Kind)
{ {
case DeclarationKind.TranslationUnit: case DeclarationKind.TranslationUnit:
{ {
var _decl = TranslationUnit.__CreateInstance(decl.__Instance); var _decl = TranslationUnit.__CreateInstance(decl.__Instance);
return VisitTranslationUnit(_decl); return VisitTranslationUnit(_decl);
} }
case DeclarationKind.Namespace: case DeclarationKind.Namespace:
{ {
var _decl = Namespace.__CreateInstance(decl.__Instance); var _decl = Namespace.__CreateInstance(decl.__Instance);
return VisitNamespace(_decl); return VisitNamespace(_decl);
} }
case DeclarationKind.Typedef: case DeclarationKind.Typedef:
{ {
var _decl = TypedefDecl.__CreateInstance(decl.__Instance); var _decl = TypedefDecl.__CreateInstance(decl.__Instance);
return VisitTypedef(_decl); return VisitTypedef(_decl);
} }
case DeclarationKind.TypeAlias: case DeclarationKind.TypeAlias:
{ {
var _decl = TypeAlias.__CreateInstance(decl.__Instance); var _decl = TypeAlias.__CreateInstance(decl.__Instance);
return VisitTypeAlias(_decl); return VisitTypeAlias(_decl);
} }
case DeclarationKind.Parameter: case DeclarationKind.Parameter:
{ {
var _decl = Parameter.__CreateInstance(decl.__Instance); var _decl = Parameter.__CreateInstance(decl.__Instance);
return VisitParameter(_decl); return VisitParameter(_decl);
} }
case DeclarationKind.Function: case DeclarationKind.Function:
{ {
var _decl = Function.__CreateInstance(decl.__Instance); var _decl = Function.__CreateInstance(decl.__Instance);
return VisitFunction(_decl); return VisitFunction(_decl);
} }
case DeclarationKind.Method: case DeclarationKind.Method:
{ {
var _decl = Method.__CreateInstance(decl.__Instance); var _decl = Method.__CreateInstance(decl.__Instance);
return VisitMethod(_decl); return VisitMethod(_decl);
} }
case DeclarationKind.Enumeration: case DeclarationKind.Enumeration:
{ {
var _decl = Enumeration.__CreateInstance(decl.__Instance); var _decl = Enumeration.__CreateInstance(decl.__Instance);
return VisitEnumeration(_decl); return VisitEnumeration(_decl);
} }
case DeclarationKind.EnumerationItem: case DeclarationKind.EnumerationItem:
{ {
var _decl = Enumeration.Item.__CreateInstance(decl.__Instance); var _decl = Enumeration.Item.__CreateInstance(decl.__Instance);
return VisitEnumerationItem(_decl); return VisitEnumerationItem(_decl);
} }
case DeclarationKind.Variable: case DeclarationKind.Variable:
{ {
var _decl = Variable.__CreateInstance(decl.__Instance); var _decl = Variable.__CreateInstance(decl.__Instance);
return VisitVariable(_decl); return VisitVariable(_decl);
} }
case DeclarationKind.VarTemplate: case DeclarationKind.VarTemplate:
{ {
var _decl = VarTemplate.__CreateInstance(decl.__Instance); var _decl = VarTemplate.__CreateInstance(decl.__Instance);
return VisitVarTemplate(_decl); return VisitVarTemplate(_decl);
} }
case DeclarationKind.VarTemplateSpecialization: case DeclarationKind.VarTemplateSpecialization:
{ {
var _decl = VarTemplateSpecialization.__CreateInstance(decl.__Instance); var _decl = VarTemplateSpecialization.__CreateInstance(decl.__Instance);
return VisitVarTemplateSpecialization(_decl); return VisitVarTemplateSpecialization(_decl);
} }
case DeclarationKind.VarTemplatePartialSpecialization: case DeclarationKind.VarTemplatePartialSpecialization:
{ {
var _decl = VarTemplatePartialSpecialization.__CreateInstance(decl.__Instance); var _decl = VarTemplatePartialSpecialization.__CreateInstance(decl.__Instance);
return VisitVarTemplatePartialSpecialization(_decl); return VisitVarTemplatePartialSpecialization(_decl);
} }
case DeclarationKind.Friend: case DeclarationKind.Friend:
{ {
var _decl = Friend.__CreateInstance(decl.__Instance); var _decl = Friend.__CreateInstance(decl.__Instance);
return VisitFriend(_decl); return VisitFriend(_decl);
} }
case DeclarationKind.Field: case DeclarationKind.Field:
{ {
var _decl = Field.__CreateInstance(decl.__Instance); var _decl = Field.__CreateInstance(decl.__Instance);
return VisitField(_decl); return VisitField(_decl);
} }
case DeclarationKind.AccessSpecifier: case DeclarationKind.AccessSpecifier:
{ {
var _decl = AccessSpecifierDecl.__CreateInstance(decl.__Instance); var _decl = AccessSpecifierDecl.__CreateInstance(decl.__Instance);
return VisitAccessSpecifier(_decl); return VisitAccessSpecifier(_decl);
} }
case DeclarationKind.Class: case DeclarationKind.Class:
{ {
var _decl = Class.__CreateInstance(decl.__Instance); var _decl = Class.__CreateInstance(decl.__Instance);
return VisitClass(_decl); return VisitClass(_decl);
} }
case DeclarationKind.ClassTemplate: case DeclarationKind.ClassTemplate:
{ {
var _decl = ClassTemplate.__CreateInstance(decl.__Instance); var _decl = ClassTemplate.__CreateInstance(decl.__Instance);
return VisitClassTemplate(_decl); return VisitClassTemplate(_decl);
} }
case DeclarationKind.ClassTemplateSpecialization: case DeclarationKind.ClassTemplateSpecialization:
{ {
var _decl = ClassTemplateSpecialization.__CreateInstance(decl.__Instance); var _decl = ClassTemplateSpecialization.__CreateInstance(decl.__Instance);
return VisitClassTemplateSpecialization(_decl); return VisitClassTemplateSpecialization(_decl);
} }
case DeclarationKind.ClassTemplatePartialSpecialization: case DeclarationKind.ClassTemplatePartialSpecialization:
{ {
var _decl = ClassTemplatePartialSpecialization.__CreateInstance(decl.__Instance); var _decl = ClassTemplatePartialSpecialization.__CreateInstance(decl.__Instance);
return VisitClassTemplatePartialSpecialization(_decl); return VisitClassTemplatePartialSpecialization(_decl);
} }
case DeclarationKind.FunctionTemplate: case DeclarationKind.FunctionTemplate:
{ {
var _decl = FunctionTemplate.__CreateInstance(decl.__Instance); var _decl = FunctionTemplate.__CreateInstance(decl.__Instance);
return VisitFunctionTemplate(_decl); return VisitFunctionTemplate(_decl);
} }
case DeclarationKind.TypeAliasTemplate: case DeclarationKind.TypeAliasTemplate:
{ {
var _decl = TypeAliasTemplate.__CreateInstance(decl.__Instance); var _decl = TypeAliasTemplate.__CreateInstance(decl.__Instance);
return VisitTypeAliasTemplate(_decl); return VisitTypeAliasTemplate(_decl);
} }
case DeclarationKind.TemplateTemplateParm: case DeclarationKind.TemplateTemplateParm:
{ {
var _decl = TemplateTemplateParameter.__CreateInstance(decl.__Instance); var _decl = TemplateTemplateParameter.__CreateInstance(decl.__Instance);
return VisitTemplateTemplateParameter(_decl); return VisitTemplateTemplateParameter(_decl);
} }
case DeclarationKind.TemplateTypeParm: case DeclarationKind.TemplateTypeParm:
{ {
var _decl = TypeTemplateParameter.__CreateInstance(decl.__Instance); var _decl = TypeTemplateParameter.__CreateInstance(decl.__Instance);
return VisitTypeTemplateParameter(_decl); return VisitTypeTemplateParameter(_decl);
} }
case DeclarationKind.NonTypeTemplateParm: case DeclarationKind.NonTypeTemplateParm:
{ {
var _decl = NonTypeTemplateParameter.__CreateInstance(decl.__Instance); var _decl = NonTypeTemplateParameter.__CreateInstance(decl.__Instance);
return VisitNonTypeTemplateParameter(_decl); return VisitNonTypeTemplateParameter(_decl);
} }
case DeclarationKind.UnresolvedUsingTypename: case DeclarationKind.UnresolvedUsingTypename:
{ {
var _decl = UnresolvedUsingTypename.__CreateInstance(decl.__Instance); var _decl = UnresolvedUsingTypename.__CreateInstance(decl.__Instance);
return VisitUnresolvedUsingTypename(_decl); return VisitUnresolvedUsingTypename(_decl);
} }
} }
throw new ArgumentOutOfRangeException(); throw new ArgumentOutOfRangeException();
@ -1833,6 +1833,8 @@ namespace CppSharp
var _spec = (AST.ClassTemplateSpecialization)Visit(spec); var _spec = (AST.ClassTemplateSpecialization)Visit(spec);
_decl.Specializations.Add(_spec); _decl.Specializations.Add(_spec);
} }
_decl.TemplatedClass.TemplateParameters.AddRange(_decl.Parameters);
_decl.TemplatedClass.Specializations.AddRange(_decl.Specializations);
return _decl; return _decl;
} }
@ -1927,6 +1929,7 @@ namespace CppSharp
var _param = Visit(param); var _param = Visit(param);
_decl.Parameters.Add(_param); _decl.Parameters.Add(_param);
} }
_decl.TemplateParameters.AddRange(_decl.TemplatedDecl.Parameters);
return _decl; return _decl;
} }

15
tests/dotnet/CSharp/CSharp.Gen.cs

@ -25,6 +25,7 @@ namespace CppSharp.Tests
base.Setup(driver); base.Setup(driver);
driver.ParserOptions.UnityBuild = true; driver.ParserOptions.UnityBuild = true;
driver.ParserOptions.SkipFunctionBodies = false;
driver.ParserOptions.AddSupportedFunctionTemplates("FunctionTemplate"); driver.ParserOptions.AddSupportedFunctionTemplates("FunctionTemplate");
driver.Options.GenerateFreeStandingFunctionsClassName = t => t.FileNameWithoutExtension + "Cool"; driver.Options.GenerateFreeStandingFunctionsClassName = t => t.FileNameWithoutExtension + "Cool";
@ -42,7 +43,7 @@ namespace CppSharp.Tests
driver.Options.GenerateClassTemplates = true; driver.Options.GenerateClassTemplates = true;
var disableNativeToManaged = new ClassGenerationOptions { GenerateNativeToManaged = false }; var disableNativeToManaged = new ClassGenerationOptions { GenerateNativeToManaged = false };
driver.Options.GetClassGenerationOptions = e => driver.Options.GetClassGenerationOptions = e =>
{ {
return e.Name == "ClassWithoutNativeToManaged" ? disableNativeToManaged : null; return e.Name == "ClassWithoutNativeToManaged" ? disableNativeToManaged : null;
}; };
@ -237,16 +238,12 @@ namespace CppSharp.Tests
var specialization = type.GetClassTemplateSpecialization(); var specialization = type.GetClassTemplateSpecialization();
var typePrinter = new CSharpTypePrinter(null); var typePrinter = new CSharpTypePrinter(null);
typePrinter.PushContext(TypePrinterContextKind.Native); typePrinter.PushContext(TypePrinterContextKind.Native);
return new CustomType(string.Format($@"{ return new CustomType(string.Format($@"{specialization.Visit(typePrinter)}{(Type.IsAddress() ? "*" : string.Empty)}", specialization.Visit(typePrinter),
specialization.Visit(typePrinter)}{
(Type.IsAddress() ? "*" : string.Empty)}", specialization.Visit(typePrinter),
Type.IsAddress() ? "*" : string.Empty)); Type.IsAddress() ? "*" : string.Empty));
} }
return new CustomType( return new CustomType(
$@"global::System.Collections.Generic.{ $@"global::System.Collections.Generic.{(ctx.MarshalKind == MarshalKind.DefaultExpression ? "List" : "IList")}<{ctx.GetTemplateParameterList()}>");
(ctx.MarshalKind == MarshalKind.DefaultExpression ? "List" : "IList")}<{
ctx.GetTemplateParameterList()}>");
} }
public override void MarshalToNative(MarshalContext ctx) public override void MarshalToNative(MarshalContext ctx)
@ -292,9 +289,7 @@ namespace CppSharp.Tests
{ {
if (ctx.Kind == TypePrinterContextKind.Native) if (ctx.Kind == TypePrinterContextKind.Native)
{ {
return new CustomType($@"global::CSharp.QString.{ return new CustomType($@"global::CSharp.QString.{Helpers.InternalStruct}{(ctx.Type.IsAddress() ? "*" : string.Empty)}");
Helpers.InternalStruct}{
(ctx.Type.IsAddress() ? "*" : string.Empty)}");
} }
return new CILType(typeof(string)); return new CILType(typeof(string));
} }

5
tests/dotnet/CSharp/CSharpTemplates.h

@ -163,9 +163,10 @@ T IndependentFields<T>::getDependent(const T& t)
} }
template <typename T> template <typename T>
T IndependentFields<T>::property() typename IndependentFields<T>::Type IndependentFields<T>::property()
{ {
return T(); std::remove_reference_t<std::remove_const_t<Type>> t;
return t;
} }
template <typename T> template <typename T>

6
tests/dotnet/Common/Common.h

@ -790,13 +790,13 @@ public:
virtual ~PureDtor() = 0; virtual ~PureDtor() = 0;
}; };
class PureImplementedDtor class VirtualImplementedDtor
{ {
public: public:
virtual ~PureImplementedDtor() = 0; virtual ~VirtualImplementedDtor();
}; };
PureImplementedDtor::~PureImplementedDtor() inline VirtualImplementedDtor::~VirtualImplementedDtor()
{ {
} }

Loading…
Cancel
Save