@@ -935,7 +935,7 @@ void KernelObjVisitor::VisitRecord(CXXRecordDecl *Owner, ParentTy &Parent,
935
935
936
936
// A base type that the SYCL OpenCL Kernel construction task uses to implement
937
937
// individual tasks.
938
- template < typename Derived> class SyclKernelFieldHandler {
938
+ class SyclKernelFieldHandler {
939
939
protected:
940
940
Sema &SemaRef;
941
941
SyclKernelFieldHandler (Sema &S) : SemaRef(S) {}
@@ -1001,11 +1001,12 @@ template <typename Derived> class SyclKernelFieldHandler {
1001
1001
virtual bool enterArray () { return true ; }
1002
1002
virtual bool nextElement (QualType) { return true ; }
1003
1003
virtual bool leaveArray (FieldDecl *, QualType, int64_t ) { return true ; }
1004
+
1005
+ virtual ~SyclKernelFieldHandler () = default ;
1004
1006
};
1005
1007
1006
1008
// A type to check the validity of all of the argument types.
1007
- class SyclKernelFieldChecker
1008
- : public SyclKernelFieldHandler<SyclKernelFieldChecker> {
1009
+ class SyclKernelFieldChecker : public SyclKernelFieldHandler {
1009
1010
bool IsInvalid = false ;
1010
1011
DiagnosticsEngine &Diag;
1011
1012
@@ -1101,8 +1102,7 @@ class SyclKernelFieldChecker
1101
1102
};
1102
1103
1103
1104
// A type to Create and own the FunctionDecl for the kernel.
1104
- class SyclKernelDeclCreator
1105
- : public SyclKernelFieldHandler<SyclKernelDeclCreator> {
1105
+ class SyclKernelDeclCreator : public SyclKernelFieldHandler {
1106
1106
FunctionDecl *KernelDecl;
1107
1107
llvm::SmallVector<ParmVarDecl *, 8 > Params;
1108
1108
SyclKernelFieldChecker &ArgChecker;
@@ -1286,8 +1286,7 @@ class SyclKernelDeclCreator
1286
1286
using SyclKernelFieldHandler::handleSyclSamplerType;
1287
1287
};
1288
1288
1289
- class SyclKernelBodyCreator
1290
- : public SyclKernelFieldHandler<SyclKernelBodyCreator> {
1289
+ class SyclKernelBodyCreator : public SyclKernelFieldHandler {
1291
1290
SyclKernelDeclCreator &DeclCreator;
1292
1291
llvm::SmallVector<Stmt *, 16 > BodyStmts;
1293
1292
llvm::SmallVector<Stmt *, 16 > FinalizeStmts;
@@ -1696,12 +1695,8 @@ class SyclKernelBodyCreator
1696
1695
using SyclKernelFieldHandler::leaveStruct;
1697
1696
};
1698
1697
1699
- class SyclKernelIntHeaderCreator
1700
- : public SyclKernelFieldHandler<SyclKernelIntHeaderCreator> {
1698
+ class SyclKernelIntHeaderCreator : public SyclKernelFieldHandler {
1701
1699
SYCLIntegrationHeader &Header;
1702
- const CXXRecordDecl *KernelObj;
1703
- // Necessary to figure out the offset of the base class.
1704
- const CXXRecordDecl *CurStruct = nullptr ;
1705
1700
int64_t CurOffset = 0 ;
1706
1701
1707
1702
void addParam (const FieldDecl *FD, QualType ArgTy,
@@ -1720,7 +1715,7 @@ class SyclKernelIntHeaderCreator
1720
1715
SyclKernelIntHeaderCreator (Sema &S, SYCLIntegrationHeader &H,
1721
1716
const CXXRecordDecl *KernelObj, QualType NameType,
1722
1717
StringRef Name, StringRef StableName)
1723
- : SyclKernelFieldHandler(S), Header(H), KernelObj(KernelObj) {
1718
+ : SyclKernelFieldHandler(S), Header(H) {
1724
1719
Header.startKernel (Name, NameType, StableName, KernelObj->getLocation ());
1725
1720
}
1726
1721
@@ -2120,13 +2115,19 @@ static const char *paramKind2Str(KernelParamKind K) {
2120
2115
#undef CASE
2121
2116
}
2122
2117
2123
- // Removes all "(anonymous namespace)::" substrings from given string
2124
- static std::string eraseAnonNamespace (std::string S) {
2118
+ // Removes all "(anonymous namespace)::" substrings from given string, and emits
2119
+ // it.
2120
+ static void emitWithoutAnonNamespaces (llvm::raw_ostream &OS, StringRef Source) {
2125
2121
const char S1[] = " (anonymous namespace)::" ;
2126
2122
2127
- for (auto Pos = S.find (S1); Pos != StringRef::npos; Pos = S.find (S1, Pos))
2128
- S.erase (Pos, sizeof (S1) - 1 );
2129
- return S;
2123
+ size_t Pos;
2124
+
2125
+ while ((Pos = Source.find (S1)) != StringRef::npos) {
2126
+ OS << Source.take_front (Pos);
2127
+ Source = Source.drop_front (Pos + sizeof (S1) - 1 );
2128
+ }
2129
+
2130
+ OS << Source;
2130
2131
}
2131
2132
2132
2133
static bool checkEnumTemplateParameter (const EnumDecl *ED,
@@ -2375,19 +2376,19 @@ void SYCLIntegrationHeader::emitForwardClassDecls(
2375
2376
}
2376
2377
}
2377
2378
2378
- static std::string getCPPTypeString ( QualType Ty) {
2379
+ static void emitCPPTypeString (raw_ostream &OS, QualType Ty) {
2379
2380
LangOptions LO;
2380
2381
PrintingPolicy P (LO);
2381
2382
P.SuppressTypedefs = true ;
2382
- return eraseAnonNamespace ( Ty.getAsString (P));
2383
+ emitWithoutAnonNamespaces (OS, Ty.getAsString (P));
2383
2384
}
2384
2385
2385
2386
static void printArguments (ASTContext &Ctx, raw_ostream &ArgOS,
2386
2387
ArrayRef<TemplateArgument> Args,
2387
2388
const PrintingPolicy &P);
2388
2389
2389
- static std::string getKernelNameTypeString (QualType T, ASTContext &Ctx,
2390
- const PrintingPolicy &TypePolicy);
2390
+ static void emitKernelNameType (QualType T, ASTContext &Ctx, raw_ostream &OS ,
2391
+ const PrintingPolicy &TypePolicy);
2391
2392
2392
2393
static void printArgument (ASTContext &Ctx, raw_ostream &ArgOS,
2393
2394
TemplateArgument Arg, const PrintingPolicy &P) {
@@ -2418,7 +2419,8 @@ static void printArgument(ASTContext &Ctx, raw_ostream &ArgOS,
2418
2419
TypePolicy.SuppressTypedefs = true ;
2419
2420
TypePolicy.SuppressTagKeyword = true ;
2420
2421
QualType T = Arg.getAsType ();
2421
- ArgOS << getKernelNameTypeString (T, Ctx, TypePolicy);
2422
+
2423
+ emitKernelNameType (T, Ctx, ArgOS, TypePolicy);
2422
2424
break ;
2423
2425
}
2424
2426
case TemplateArgument::ArgKind::Template: {
@@ -2456,42 +2458,46 @@ static void printTemplateArguments(ASTContext &Ctx, raw_ostream &ArgOS,
2456
2458
ArgOS << " >" ;
2457
2459
}
2458
2460
2459
- static std::string printRecordType ( QualType T, const CXXRecordDecl *RD,
2460
- const PrintingPolicy &TypePolicy) {
2461
+ static void emitRecordType (raw_ostream &OS, QualType T, const CXXRecordDecl *RD,
2462
+ const PrintingPolicy &TypePolicy) {
2461
2463
SmallString<64 > Buf;
2462
- llvm::raw_svector_ostream OS (Buf);
2463
- T.getCanonicalType ().getQualifiers ().print (OS , TypePolicy,
2464
+ llvm::raw_svector_ostream RecOS (Buf);
2465
+ T.getCanonicalType ().getQualifiers ().print (RecOS , TypePolicy,
2464
2466
/* appendSpaceIfNotEmpty*/ true );
2465
2467
if (const auto *TSD = dyn_cast<ClassTemplateSpecializationDecl>(RD)) {
2466
2468
2467
2469
// Print template class name
2468
- TSD->printQualifiedName (OS , TypePolicy, /* WithGlobalNsPrefix*/ true );
2470
+ TSD->printQualifiedName (RecOS , TypePolicy, /* WithGlobalNsPrefix*/ true );
2469
2471
2470
2472
// Print template arguments substituting enumerators
2471
2473
ASTContext &Ctx = RD->getASTContext ();
2472
2474
const TemplateArgumentList &Args = TSD->getTemplateArgs ();
2473
- printTemplateArguments (Ctx, OS , Args.asArray (), TypePolicy);
2475
+ printTemplateArguments (Ctx, RecOS , Args.asArray (), TypePolicy);
2474
2476
2475
- return eraseAnonNamespace (OS.str ().str ());
2477
+ emitWithoutAnonNamespaces (OS, RecOS.str ());
2478
+ return ;
2476
2479
}
2477
- if (RD->getDeclContext ()->isFunctionOrMethod ())
2478
- return eraseAnonNamespace (T.getCanonicalType ().getAsString (TypePolicy));
2480
+ if (RD->getDeclContext ()->isFunctionOrMethod ()) {
2481
+ emitWithoutAnonNamespaces (OS, T.getCanonicalType ().getAsString (TypePolicy));
2482
+ return ;
2483
+ }
2484
+
2479
2485
const NamespaceDecl *NS = dyn_cast<NamespaceDecl>(RD->getDeclContext ());
2480
- RD->printQualifiedName (OS, TypePolicy, !(NS && NS->isAnonymousNamespace ()));
2481
- return eraseAnonNamespace (OS.str ().str ());
2486
+ RD->printQualifiedName (RecOS, TypePolicy,
2487
+ !(NS && NS->isAnonymousNamespace ()));
2488
+ emitWithoutAnonNamespaces (OS, RecOS.str ());
2482
2489
}
2483
2490
2484
- static std::string getKernelNameTypeString (QualType T, ASTContext &Ctx,
2485
- const PrintingPolicy &TypePolicy) {
2486
- if (T->isRecordType ())
2487
- return printRecordType (T, T->getAsCXXRecordDecl (), TypePolicy);
2488
- if (T->isEnumeralType ()) {
2489
- SmallString<64 > Buf;
2490
- llvm::raw_svector_ostream OS (Buf);
2491
- OS << " ::" << T.getCanonicalType ().getAsString (TypePolicy);
2492
- return eraseAnonNamespace (OS.str ().str ());
2493
- }
2494
- return eraseAnonNamespace (T.getCanonicalType ().getAsString (TypePolicy));
2491
+ static void emitKernelNameType (QualType T, ASTContext &Ctx, raw_ostream &OS,
2492
+ const PrintingPolicy &TypePolicy) {
2493
+ if (T->isRecordType ()) {
2494
+ emitRecordType (OS, T, T->getAsCXXRecordDecl (), TypePolicy);
2495
+ return ;
2496
+ }
2497
+
2498
+ if (T->isEnumeralType ())
2499
+ OS << " ::" ;
2500
+ emitWithoutAnonNamespaces (OS, T.getCanonicalType ().getAsString (TypePolicy));
2495
2501
}
2496
2502
2497
2503
void SYCLIntegrationHeader::emit (raw_ostream &O) {
@@ -2519,9 +2525,9 @@ void SYCLIntegrationHeader::emit(raw_ostream &O) {
2519
2525
});
2520
2526
O << " // Specialization constants IDs:\n " ;
2521
2527
for (const auto &P : llvm::make_range (SpecConsts.begin (), End)) {
2522
- std::string CPPName = getCPPTypeString (P. first ) ;
2523
- O << " template <> struct sycl::detail::SpecConstantInfo< " << CPPName
2524
- << " > {\n " ;
2528
+ O << " template <> struct sycl::detail::SpecConstantInfo< " ;
2529
+ emitCPPTypeString (O, P. first );
2530
+ O << " > {\n " ;
2525
2531
O << " static constexpr const char* getName() {\n " ;
2526
2532
O << " return \" " << P.second << " \" ;\n " ;
2527
2533
O << " }\n " ;
@@ -2613,8 +2619,9 @@ void SYCLIntegrationHeader::emit(raw_ostream &O) {
2613
2619
LangOptions LO;
2614
2620
PrintingPolicy P (LO);
2615
2621
P.SuppressTypedefs = true ;
2616
- O << " template <> struct KernelInfo<"
2617
- << getKernelNameTypeString (K.NameType , S.getASTContext (), P) << " > {\n " ;
2622
+ O << " template <> struct KernelInfo<" ;
2623
+ emitKernelNameType (K.NameType , S.getASTContext (), O, P);
2624
+ O << " > {\n " ;
2618
2625
}
2619
2626
O << " DLL_LOCAL\n " ;
2620
2627
O << " static constexpr const char* getName() { return \" " << K.Name
0 commit comments