1 //===--- KernelNameRestrictionCheck.cpp - clang-tidy ----------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #include "KernelNameRestrictionCheck.h"
10 #include "clang/Frontend/CompilerInstance.h"
11 #include "clang/Lex/PPCallbacks.h"
12 #include "clang/Lex/Preprocessor.h"
16 using namespace clang::ast_matchers
;
18 namespace clang::tidy::altera
{
22 class KernelNameRestrictionPPCallbacks
: public PPCallbacks
{
24 explicit KernelNameRestrictionPPCallbacks(ClangTidyCheck
&Check
,
25 const SourceManager
&SM
)
26 : Check(Check
), SM(SM
) {}
28 void InclusionDirective(SourceLocation HashLoc
, const Token
&IncludeTok
,
29 StringRef FileName
, bool IsAngled
,
30 CharSourceRange FileNameRange
,
31 OptionalFileEntryRef File
, StringRef SearchPath
,
32 StringRef RelativePath
, const Module
*Imported
,
33 SrcMgr::CharacteristicKind FileType
) override
;
35 void EndOfMainFile() override
;
38 /// Returns true if the name of the file with path FileName is 'kernel.cl',
39 /// 'verilog.cl', or 'vhdl.cl'. The file name check is case insensitive.
40 bool fileNameIsRestricted(StringRef FileName
);
42 struct IncludeDirective
{
43 SourceLocation Loc
; // Location in the include directive.
44 StringRef FileName
; // Filename as a string.
47 std::vector
<IncludeDirective
> IncludeDirectives
;
48 ClangTidyCheck
&Check
;
49 const SourceManager
&SM
;
54 void KernelNameRestrictionCheck::registerPPCallbacks(const SourceManager
&SM
,
58 std::make_unique
<KernelNameRestrictionPPCallbacks
>(*this, SM
));
61 void KernelNameRestrictionPPCallbacks::InclusionDirective(
62 SourceLocation HashLoc
, const Token
&, StringRef FileName
, bool,
63 CharSourceRange
, OptionalFileEntryRef
, StringRef
, StringRef
, const Module
*,
64 SrcMgr::CharacteristicKind
) {
65 IncludeDirective ID
= {HashLoc
, FileName
};
66 IncludeDirectives
.push_back(std::move(ID
));
69 bool KernelNameRestrictionPPCallbacks::fileNameIsRestricted(
71 return FileName
.equals_insensitive("kernel.cl") ||
72 FileName
.equals_insensitive("verilog.cl") ||
73 FileName
.equals_insensitive("vhdl.cl");
76 void KernelNameRestrictionPPCallbacks::EndOfMainFile() {
78 // Check main file for restricted names.
79 OptionalFileEntryRef Entry
= SM
.getFileEntryRefForID(SM
.getMainFileID());
80 StringRef FileName
= llvm::sys::path::filename(Entry
->getName());
81 if (fileNameIsRestricted(FileName
))
82 Check
.diag(SM
.getLocForStartOfFile(SM
.getMainFileID()),
83 "compiling '%0' may cause additional compilation errors due "
84 "to the name of the kernel source file; consider renaming the "
85 "included kernel source file")
88 if (IncludeDirectives
.empty())
91 // Check included files for restricted names.
92 for (const IncludeDirective
&ID
: IncludeDirectives
) {
93 StringRef FileName
= llvm::sys::path::filename(ID
.FileName
);
94 if (fileNameIsRestricted(FileName
))
96 "including '%0' may cause additional compilation errors due "
97 "to the name of the kernel source file; consider renaming the "
98 "included kernel source file")
103 } // namespace clang::tidy::altera