diff options
author | Vassil Vassilev <v.g.vassilev@gmail.com> | 2017-04-27 16:58:33 +0000 |
---|---|---|
committer | Vassil Vassilev <v.g.vassilev@gmail.com> | 2017-04-27 16:58:33 +0000 |
commit | 2b676cfa55d0684e5323ce31e29c64d117740bfd (patch) | |
tree | 970c1bc1e47ec5c485d16653ce83711b73209093 /clang/lib/Frontend/PrintPreprocessedOutput.cpp | |
parent | c1db8cf9c1ddf2a113312b81e467fcd5b6f30194 (diff) | |
download | bcm5719-llvm-2b676cfa55d0684e5323ce31e29c64d117740bfd.tar.gz bcm5719-llvm-2b676cfa55d0684e5323ce31e29c64d117740bfd.zip |
Remove leaking UnknownPragmaHandlers right after we are done with them.
The UnknownPragmaHandlers added by DoPrintPreprocessedInput conflict with the
real PragmaHandlers from clang::Parser because they try to handle the same
#pragma directives. This makes it impossible to use a Preprocessor (that was
previously passed to DoPrintPreprocessedInput), as an Preprocessor for a
clang::Parser instance which is what we currently do in cling.
This patch removes the added UnknownPragmaHandler to avoid conflicts these
conflicts and leave the PragmaHandlers of the Preprocessors in a the same state
as before calling DoPrintPreprocessedInput.
Patch by Raphael Isemann (D32486)!
llvm-svn: 301563
Diffstat (limited to 'clang/lib/Frontend/PrintPreprocessedOutput.cpp')
-rw-r--r-- | clang/lib/Frontend/PrintPreprocessedOutput.cpp | 40 |
1 files changed, 27 insertions, 13 deletions
diff --git a/clang/lib/Frontend/PrintPreprocessedOutput.cpp b/clang/lib/Frontend/PrintPreprocessedOutput.cpp index 3168b3da70a..42d609cdb64 100644 --- a/clang/lib/Frontend/PrintPreprocessedOutput.cpp +++ b/clang/lib/Frontend/PrintPreprocessedOutput.cpp @@ -775,26 +775,33 @@ void clang::DoPrintPreprocessedInput(Preprocessor &PP, raw_ostream *OS, // Expand macros in pragmas with -fms-extensions. The assumption is that // the majority of pragmas in such a file will be Microsoft pragmas. - PP.AddPragmaHandler(new UnknownPragmaHandler( - "#pragma", Callbacks, + // Remember the handlers we will add so that we can remove them later. + std::unique_ptr<UnknownPragmaHandler> MicrosoftExtHandler( + new UnknownPragmaHandler( + "#pragma", Callbacks, + /*RequireTokenExpansion=*/PP.getLangOpts().MicrosoftExt)); + + std::unique_ptr<UnknownPragmaHandler> GCCHandler(new UnknownPragmaHandler( + "#pragma GCC", Callbacks, /*RequireTokenExpansion=*/PP.getLangOpts().MicrosoftExt)); - PP.AddPragmaHandler( - "GCC", new UnknownPragmaHandler( - "#pragma GCC", Callbacks, - /*RequireTokenExpansion=*/PP.getLangOpts().MicrosoftExt)); - PP.AddPragmaHandler( - "clang", new UnknownPragmaHandler( - "#pragma clang", Callbacks, - /*RequireTokenExpansion=*/PP.getLangOpts().MicrosoftExt)); + + std::unique_ptr<UnknownPragmaHandler> ClangHandler(new UnknownPragmaHandler( + "#pragma clang", Callbacks, + /*RequireTokenExpansion=*/PP.getLangOpts().MicrosoftExt)); + + PP.AddPragmaHandler(MicrosoftExtHandler.get()); + PP.AddPragmaHandler("GCC", GCCHandler.get()); + PP.AddPragmaHandler("clang", ClangHandler.get()); // The tokens after pragma omp need to be expanded. // // OpenMP [2.1, Directive format] // Preprocessing tokens following the #pragma omp are subject to macro // replacement. - PP.AddPragmaHandler("omp", - new UnknownPragmaHandler("#pragma omp", Callbacks, - /*RequireTokenExpansion=*/true)); + std::unique_ptr<UnknownPragmaHandler> OpenMPHandler( + new UnknownPragmaHandler("#pragma omp", Callbacks, + /*RequireTokenExpansion=*/true)); + PP.AddPragmaHandler("omp", OpenMPHandler.get()); PP.addPPCallbacks(std::unique_ptr<PPCallbacks>(Callbacks)); @@ -822,4 +829,11 @@ void clang::DoPrintPreprocessedInput(Preprocessor &PP, raw_ostream *OS, // Read all the preprocessed tokens, printing them out to the stream. PrintPreprocessedTokens(PP, Tok, Callbacks, *OS); *OS << '\n'; + + // Remove the handlers we just added to leave the preprocessor in a sane state + // so that it can be reused (for example by a clang::Parser instance). + PP.RemovePragmaHandler(MicrosoftExtHandler.get()); + PP.RemovePragmaHandler("GCC", GCCHandler.get()); + PP.RemovePragmaHandler("clang", ClangHandler.get()); + PP.RemovePragmaHandler("omp", OpenMPHandler.get()); } |