#include "clang/Tooling/CommonOptionsParser.h"
#include "clang/Tooling/Refactoring.h"
#include "clang/Tooling/Tooling.h"
+
#include <algorithm>
#include <set>
#include <string>
// to virtual method.
class AdditionalUSRFinder : public RecursiveASTVisitor<AdditionalUSRFinder> {
public:
- explicit AdditionalUSRFinder(const Decl *FoundDecl, ASTContext &Context,
- std::vector<std::string> *USRs)
- : FoundDecl(FoundDecl), Context(Context), USRs(USRs) {}
+ AdditionalUSRFinder(const Decl *FoundDecl, ASTContext &Context)
+ : FoundDecl(FoundDecl), Context(Context) {}
- void Find() {
+ std::vector<std::string> Find() {
// Fill OverriddenMethods and PartialSpecs storages.
TraverseDecl(Context.getTranslationUnitDecl());
if (const auto *MethodDecl = dyn_cast<CXXMethodDecl>(FoundDecl)) {
} else {
USRSet.insert(getUSRForDecl(FoundDecl));
}
- USRs->insert(USRs->end(), USRSet.begin(), USRSet.end());
+ return std::vector<std::string>(USRSet.begin(), USRSet.end());
}
bool VisitCXXMethodDecl(const CXXMethodDecl *MethodDecl) {
const Decl *FoundDecl;
ASTContext &Context;
- std::vector<std::string> *USRs;
std::set<std::string> USRSet;
std::vector<const CXXMethodDecl *> OverriddenMethods;
std::vector<const ClassTemplatePartialSpecializationDecl *> PartialSpecs;
};
} // namespace
-struct NamedDeclFindingConsumer : public ASTConsumer {
- void HandleTranslationUnit(ASTContext &Context) override {
- const SourceManager &SourceMgr = Context.getSourceManager();
- // The file we look for the USR in will always be the main source file.
+class NamedDeclFindingConsumer : public ASTConsumer {
+public:
+ NamedDeclFindingConsumer(ArrayRef<unsigned> SymbolOffsets,
+ ArrayRef<std::string> QualifiedNames,
+ std::vector<std::string> &SpellingNames,
+ std::vector<std::vector<std::string>> &USRList,
+ bool &ErrorOccurred)
+ : SymbolOffsets(SymbolOffsets), QualifiedNames(QualifiedNames),
+ SpellingNames(SpellingNames), USRList(USRList),
+ ErrorOccurred(ErrorOccurred) {}
+
+private:
+ bool FindSymbol(ASTContext &Context, const SourceManager &SourceMgr,
+ unsigned SymbolOffset, const std::string &QualifiedName) {
+ DiagnosticsEngine &Engine = Context.getDiagnostics();
+
const SourceLocation Point =
SourceMgr.getLocForStartOfFile(SourceMgr.getMainFileID())
.getLocWithOffset(SymbolOffset);
- if (!Point.isValid())
- return;
- const NamedDecl *FoundDecl = nullptr;
- if (OldName.empty())
- FoundDecl = getNamedDeclAt(Context, Point);
- else
- FoundDecl = getNamedDeclFor(Context, OldName);
+
+ if (!Point.isValid()) {
+ ErrorOccurred = true;
+ unsigned InvalidOffset = Engine.getCustomDiagID(
+ DiagnosticsEngine::Error,
+ "SourceLocation in file %0 at offset %1 is invalid");
+ Engine.Report(Point, InvalidOffset) << SourceMgr.getFilename(Point)
+ << SymbolOffset;
+ return false;
+ }
+
+ const NamedDecl *FoundDecl = QualifiedName.empty()
+ ? getNamedDeclAt(Context, Point)
+ : getNamedDeclFor(Context, QualifiedName);
+
if (FoundDecl == nullptr) {
- if (OldName.empty()) {
+ if (QualifiedName.empty()) {
FullSourceLoc FullLoc(Point, SourceMgr);
- errs() << "clang-rename: could not find symbol at "
- << SourceMgr.getFilename(Point) << ":"
- << FullLoc.getSpellingLineNumber() << ":"
- << FullLoc.getSpellingColumnNumber() << " (offset "
- << SymbolOffset << ").\n";
- } else {
- errs() << "clang-rename: could not find symbol " << OldName << ".\n";
+ unsigned CouldNotFindSymbolAt = Engine.getCustomDiagID(
+ DiagnosticsEngine::Error,
+ "clang-rename could not find symbol (offset %0)");
+ Engine.Report(Point, CouldNotFindSymbolAt) << SymbolOffset;
+ ErrorOccurred = true;
+ return false;
}
- return;
+ unsigned CouldNotFindSymbolNamed = Engine.getCustomDiagID(
+ DiagnosticsEngine::Error, "clang-rename could not find symbol %0");
+ Engine.Report(CouldNotFindSymbolNamed) << QualifiedName;
+ ErrorOccurred = true;
+ return false;
}
- // If FoundDecl is a constructor or destructor, we want to instead take the
- // Decl of the corresponding class.
+ // If FoundDecl is a constructor or destructor, we want to instead take
+ // the Decl of the corresponding class.
if (const auto *CtorDecl = dyn_cast<CXXConstructorDecl>(FoundDecl))
FoundDecl = CtorDecl->getParent();
else if (const auto *DtorDecl = dyn_cast<CXXDestructorDecl>(FoundDecl))
FoundDecl = DtorDecl->getParent();
- *SpellingName = FoundDecl->getNameAsString();
+ SpellingNames.push_back(FoundDecl->getNameAsString());
+ AdditionalUSRFinder Finder(FoundDecl, Context);
+ USRList.push_back(Finder.Find());
+ return true;
+ }
- AdditionalUSRFinder Finder(FoundDecl, Context, USRs);
- Finder.Find();
+ void HandleTranslationUnit(ASTContext &Context) override {
+ const SourceManager &SourceMgr = Context.getSourceManager();
+ for (unsigned Offset : SymbolOffsets) {
+ if (!FindSymbol(Context, SourceMgr, Offset, ""))
+ return;
+ }
+ for (const std::string &QualifiedName : QualifiedNames) {
+ if (!FindSymbol(Context, SourceMgr, 0, QualifiedName))
+ return;
+ }
}
- unsigned SymbolOffset;
- std::string OldName;
- std::string *SpellingName;
- std::vector<std::string> *USRs;
+ ArrayRef<unsigned> SymbolOffsets;
+ ArrayRef<std::string> QualifiedNames;
+ std::vector<std::string> &SpellingNames;
+ std::vector<std::vector<std::string>> &USRList;
+ bool &ErrorOccurred;
};
std::unique_ptr<ASTConsumer> USRFindingAction::newASTConsumer() {
- std::unique_ptr<NamedDeclFindingConsumer> Consumer(
- new NamedDeclFindingConsumer);
- SpellingName = "";
- Consumer->SymbolOffset = SymbolOffset;
- Consumer->OldName = OldName;
- Consumer->USRs = &USRs;
- Consumer->SpellingName = &SpellingName;
- return std::move(Consumer);
+ return llvm::make_unique<NamedDeclFindingConsumer>(
+ SymbolOffsets, QualifiedNames, SpellingNames, USRList, ErrorOccurred);
}
} // namespace rename
#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_RENAME_USR_FINDING_ACTION_H
#define LLVM_CLANG_TOOLS_EXTRA_CLANG_RENAME_USR_FINDING_ACTION_H
-#include "clang/Frontend/FrontendAction.h"
+#include "clang/Basic/LLVM.h"
+#include "llvm/ADT/ArrayRef.h"
+
+#include <string>
+#include <vector>
namespace clang {
class ASTConsumer;
namespace rename {
struct USRFindingAction {
- USRFindingAction(unsigned Offset, const std::string &Name)
- : SymbolOffset(Offset), OldName(Name) {}
+ USRFindingAction(ArrayRef<unsigned> SymbolOffsets,
+ ArrayRef<std::string> QualifiedNames)
+ : SymbolOffsets(SymbolOffsets), QualifiedNames(QualifiedNames),
+ ErrorOccurred(false) {}
std::unique_ptr<ASTConsumer> newASTConsumer();
- // \brief get the spelling of the USR(s) as it would appear in source files.
- const std::string &getUSRSpelling() { return SpellingName; }
-
- const std::vector<std::string> &getUSRs() { return USRs; }
+ ArrayRef<std::string> getUSRSpellings() { return SpellingNames; }
+ ArrayRef<std::vector<std::string>> getUSRList() { return USRList; }
+ bool errorOccurred() { return ErrorOccurred; }
private:
- unsigned SymbolOffset;
- std::string OldName;
- std::string SpellingName;
- std::vector<std::string> USRs;
+ std::vector<unsigned> SymbolOffsets;
+ std::vector<std::string> QualifiedNames;
+ std::vector<std::string> SpellingNames;
+ std::vector<std::vector<std::string>> USRList;
+ bool ErrorOccurred;
};
} // namespace rename
#include <system_error>
using namespace llvm;
-
using namespace clang;
-cl::OptionCategory ClangRenameAtCategory("clang-rename rename-at options");
-cl::OptionCategory ClangRenameAllCategory("clang-rename rename-all options");
-
-const char RenameAtUsage[] = "A tool to rename symbols in C/C++ code.\n\
-clang-rename renames every occurrence of a symbol found at <offset> in\n\
-<source0>. If -i is specified, the edited files are overwritten to disk.\n\
-Otherwise, the results are written to stdout.\n";
-
-const char RenameAllUsage[] = "A tool to rename symbols in C/C++ code.\n\
-clang-rename performs renaming given pairs {offset | old-name} -> new-name.\n";
-
-static int renameAtMain(int argc, const char *argv[]);
-static int renameAllMain(int argc, const char *argv[]);
-static int helpMain(int argc, const char *argv[]);
-
/// \brief An oldname -> newname rename.
struct RenameAllInfo {
- std::string OldName;
unsigned Offset = 0;
+ std::string QualifiedName;
std::string NewName;
};
/// (de)serialized.
template <> struct MappingTraits<RenameAllInfo> {
static void mapping(IO &IO, RenameAllInfo &Info) {
- IO.mapOptional("OldName", Info.OldName);
IO.mapOptional("Offset", Info.Offset);
+ IO.mapOptional("QualifiedName", Info.QualifiedName);
IO.mapRequired("NewName", Info.NewName);
}
};
} // end namespace yaml
} // end namespace llvm
-int main(int argc, const char **argv) {
- if (argc > 1) {
- using MainFunction = std::function<int(int, const char *[])>;
- MainFunction Func = StringSwitch<MainFunction>(argv[1])
- .Case("rename-at", renameAtMain)
- .Case("rename-all", renameAllMain)
- .Cases("-help", "--help", helpMain)
- .Default(nullptr);
+static cl::OptionCategory ClangRenameOptions("clang-rename common options");
+
+static cl::list<unsigned> SymbolOffsets(
+ "offset",
+ cl::desc("Locates the symbol by offset as opposed to <line>:<column>."),
+ cl::ZeroOrMore, cl::cat(ClangRenameOptions));
+static cl::opt<bool> Inplace("i", cl::desc("Overwrite edited <file>s."),
+ cl::cat(ClangRenameOptions));
+static cl::list<std::string>
+ QualifiedNames("qualified-name",
+ cl::desc("The fully qualified name of the symbol."),
+ cl::ZeroOrMore, cl::cat(ClangRenameOptions));
+
+static cl::list<std::string>
+ NewNames("new-name", cl::desc("The new name to change the symbol to."),
+ cl::ZeroOrMore, cl::cat(ClangRenameOptions));
+static cl::opt<bool> PrintName(
+ "pn",
+ cl::desc("Print the found symbol's name prior to renaming to stderr."),
+ cl::cat(ClangRenameOptions));
+static cl::opt<bool> PrintLocations(
+ "pl", cl::desc("Print the locations affected by renaming to stderr."),
+ cl::cat(ClangRenameOptions));
+static cl::opt<std::string>
+ ExportFixes("export-fixes",
+ cl::desc("YAML file to store suggested fixes in."),
+ cl::value_desc("filename"), cl::cat(ClangRenameOptions));
+static cl::opt<std::string>
+ Input("input", cl::desc("YAML file to load oldname-newname pairs from."),
+ cl::Optional, cl::cat(ClangRenameOptions));
- if (Func) {
- std::string Invocation = std::string(argv[0]) + " " + argv[1];
- argv[1] = Invocation.c_str();
- return Func(argc - 1, argv + 1);
- } else {
- return renameAtMain(argc, argv);
- }
- }
-
- helpMain(argc, argv);
- return 1;
-}
-
-int subcommandMain(bool isRenameAll, int argc, const char **argv) {
- cl::OptionCategory *Category = nullptr;
- const char *Usage = nullptr;
- if (isRenameAll) {
- Category = &ClangRenameAllCategory;
- Usage = RenameAllUsage;
- } else {
- Category = &ClangRenameAtCategory;
- Usage = RenameAtUsage;
- }
-
- cl::list<std::string> NewNames(
- "new-name", cl::desc("The new name to change the symbol to."),
- (isRenameAll ? cl::ZeroOrMore : cl::Required), cl::cat(*Category));
- cl::list<unsigned> SymbolOffsets(
- "offset",
- cl::desc("Locates the symbol by offset as opposed to <line>:<column>."),
- (isRenameAll ? cl::ZeroOrMore : cl::Required), cl::cat(*Category));
- cl::list<std::string> OldNames(
- "old-name",
- cl::desc(
- "The fully qualified name of the symbol, if -offset is not used."),
- (isRenameAll ? cl::ZeroOrMore : cl::Optional),
- cl::cat(ClangRenameAllCategory));
- cl::opt<bool> Inplace("i", cl::desc("Overwrite edited <file>s."),
- cl::cat(*Category));
- cl::opt<bool> PrintName(
- "pn",
- cl::desc("Print the found symbol's name prior to renaming to stderr."),
- cl::cat(ClangRenameAtCategory));
- cl::opt<bool> PrintLocations(
- "pl", cl::desc("Print the locations affected by renaming to stderr."),
- cl::cat(ClangRenameAtCategory));
- cl::opt<std::string> ExportFixes(
- "export-fixes", cl::desc("YAML file to store suggested fixes in."),
- cl::value_desc("filename"), cl::cat(*Category));
- cl::opt<std::string> Input(
- "input", cl::desc("YAML file to load oldname-newname pairs from."),
- cl::Optional, cl::cat(ClangRenameAllCategory));
-
- tooling::CommonOptionsParser OP(argc, argv, *Category, Usage);
+int main(int argc, const char **argv) {
+ tooling::CommonOptionsParser OP(argc, argv, ClangRenameOptions);
if (!Input.empty()) {
- // Populate OldNames and NewNames from a YAML file.
+ // Populate QualifiedNames and NewNames from a YAML file.
ErrorOr<std::unique_ptr<MemoryBuffer>> Buffer =
llvm::MemoryBuffer::getFile(Input);
if (!Buffer) {
llvm::yaml::Input YAML(Buffer.get()->getBuffer());
YAML >> Infos;
for (const auto &Info : Infos) {
- if (!Info.OldName.empty())
- OldNames.push_back(Info.OldName);
+ if (!Info.QualifiedName.empty())
+ QualifiedNames.push_back(Info.QualifiedName);
else
SymbolOffsets.push_back(Info.Offset);
NewNames.push_back(Info.NewName);
}
// Check the arguments for correctness.
-
if (NewNames.empty()) {
- errs() << "clang-rename: either -new-name or -input is required.\n\n";
+ errs() << "clang-rename: -new-name must be specified.\n\n";
+ exit(1);
+ }
+
+ if (SymbolOffsets.empty() == QualifiedNames.empty()) {
+ errs() << "clang-rename: -offset and -qualified-name can't be present at "
+ "the same time.\n";
exit(1);
}
// Check if NewNames is a valid identifier in C++17.
+ LangOptions Options;
+ Options.CPlusPlus = true;
+ Options.CPlusPlus1z = true;
+ IdentifierTable Table(Options);
for (const auto &NewName : NewNames) {
- LangOptions Options;
- Options.CPlusPlus = true;
- Options.CPlusPlus1z = true;
- IdentifierTable Table(Options);
auto NewNameTokKind = Table.get(NewName).getTokenID();
if (!tok::isAnyIdentifier(NewNameTokKind)) {
errs() << "ERROR: new name is not a valid identifier in C++17.\n\n";
}
}
- if (!OldNames.empty() && OldNames.size() != NewNames.size()) {
- errs() << "clang-rename: number of old names (" << OldNames.size()
- << ") do not equal to number of new names (" << NewNames.size()
- << ").\n\n";
- cl::PrintHelpMessage();
- exit(1);
- }
-
- if (!SymbolOffsets.empty() && SymbolOffsets.size() != NewNames.size()) {
- errs() << "clang-rename: number of symbol offsets (" << SymbolOffsets.size()
- << ") do not equal to number of new names (" << NewNames.size()
+ if (SymbolOffsets.size() + QualifiedNames.size() != NewNames.size()) {
+ errs() << "clang-rename: number of symbol offsets(" << SymbolOffsets.size()
+ << ") + number of qualified names (" << QualifiedNames.size()
+ << ") must be equal to number of new names(" << NewNames.size()
<< ").\n\n";
cl::PrintHelpMessage();
exit(1);
}
- std::vector<std::vector<std::string>> USRList;
- std::vector<std::string> PrevNames;
auto Files = OP.getSourcePathList();
tooling::RefactoringTool Tool(OP.getCompilations(), Files);
- unsigned Count = OldNames.size() ? OldNames.size() : SymbolOffsets.size();
- for (unsigned I = 0; I < Count; ++I) {
- unsigned SymbolOffset = SymbolOffsets.empty() ? 0 : SymbolOffsets[I];
- const std::string &OldName = OldNames.empty() ? std::string() : OldNames[I];
-
- // Get the USRs.
- rename::USRFindingAction USRAction(SymbolOffset, OldName);
-
- // Find the USRs.
- Tool.run(tooling::newFrontendActionFactory(&USRAction).get());
- const auto &USRs = USRAction.getUSRs();
- USRList.push_back(USRs);
- const auto &PrevName = USRAction.getUSRSpelling();
- PrevNames.push_back(PrevName);
-
- if (PrevName.empty()) {
- // An error should have already been printed.
- exit(1);
+ rename::USRFindingAction FindingAction(SymbolOffsets, QualifiedNames);
+ Tool.run(tooling::newFrontendActionFactory(&FindingAction).get());
+ const std::vector<std::vector<std::string>> &USRList =
+ FindingAction.getUSRList();
+ const std::vector<std::string> &PrevNames = FindingAction.getUSRSpellings();
+ if (PrintName) {
+ for (const auto &PrevName : PrevNames) {
+ outs() << "clang-rename found name: " << PrevName << '\n';
}
+ }
- if (PrintName) {
- errs() << "clang-rename: found name: " << PrevName << '\n';
- }
+ if (FindingAction.errorOccurred()) {
+ // Diagnostics are already issued at this point.
+ exit(1);
}
// Perform the renaming.
rename::RenamingAction RenameAction(NewNames, PrevNames, USRList,
Tool.getReplacements(), PrintLocations);
- auto Factory = tooling::newFrontendActionFactory(&RenameAction);
+ std::unique_ptr<tooling::FrontendActionFactory> Factory =
+ tooling::newFrontendActionFactory(&RenameAction);
int ExitCode;
if (Inplace) {
exit(ExitCode);
}
-
-/// \brief Top level help.
-/// FIXME It would be better if this could be auto-generated.
-static int helpMain(int argc, const char *argv[]) {
- errs() << "Usage: clang-rename {rename-at|rename-all} [OPTION]...\n\n"
- "A tool to rename symbols in C/C++ code.\n\n"
- "Subcommands:\n"
- " rename-at: Perform rename off of a location in a file. (This "
- "is the default.)\n"
- " rename-all: Perform rename of all symbols matching one or more "
- "fully qualified names.\n";
- return 0;
-}
-
-static int renameAtMain(int argc, const char *argv[]) {
- return subcommandMain(false, argc, argv);
-}
-
-static int renameAllMain(int argc, const char *argv[]) {
- return subcommandMain(true, argc, argv);
-}
Although a command line interface exists, it is highly recommended to use the
text editor interface instead for better experience.
-You can also identify one or more symbols to be renamed by giving the fully qualified
-name:
+You can also identify one or more symbols to be renamed by giving the fully
+qualified name:
.. code-block:: console
- $ clang-rename rename-all -old-name=foo -new-name=bar test.cpp
+ $ clang-rename -qualified-name=foo -new-name=bar test.cpp
+Renaming multiple symbols at once is supported, too. However,
+:program:`clang-rename` doesn't accept both `-offset` and `-qualified-name` at
+the same time. So, you can either specify multiple `-offset` or
+`-qualified-name`.
-Alternatively, old name / new name pairs can be put into a YAML file:
-
-.. code-block:: yaml
-
- ---
- - OldName: foo
- NewName: bar
- ...
+.. code-block:: console
+ $ clang-rename -offset=42 -new-name=bar1 -offset=150 -new-name=bar2 test.cpp
-That way you can avoid spelling out all the names as command line arguments:
+or
.. code-block:: console
- $ clang-rename rename-all -input=test.yaml test.cpp
+ $ clang-rename -qualified-name=foo1 -new-name=bar1 -qualified-name=foo2 -new-name=bar2 test.cpp
-The YAML file also supports offsets:
+Alternatively, {offset | qualified-name} / new-name pairs can be put into a YAML
+file:
.. code-block:: yaml
---
- Offset: 42
- NewName: foo
+ NewName: bar1
+ - Offset: 150
+ NewName: bar2
...
+or
-:program:`clang-rename` offers the following options:
-
-.. code-block:: console
-
- $ clang-rename -help
- Usage: clang-rename {rename-at|rename-all} [OPTION]...
-
- A tool to rename symbols in C/C++ code.
+.. code-block:: yaml
- Subcommands:
- rename-at: Perform rename off of a location in a file. (This is the default.)
- rename-all: Perform rename of all symbols matching one or more fully qualified names.
+ ---
+ - QualifiedName: foo1
+ NewName: bar1
+ - QualifiedName: foo2
+ NewName: bar2
+ ...
+That way you can avoid spelling out all the names as command line arguments:
.. code-block:: console
- $ clang-rename rename-at -help
- OVERVIEW: A tool to rename symbols in C/C++ code.
- clang-rename renames every occurrence of a symbol found at <offset> in
- <source0>. If -i is specified, the edited files are overwritten to disk.
- Otherwise, the results are written to stdout.
-
- USAGE: clang-rename rename-at [subcommand] [options] <source0> [... <sourceN>]
-
- OPTIONS:
-
- Generic Options:
-
- -help - Display available options (-help-hidden for more)
- -help-list - Display list of available options (-help-list-hidden for more)
- -version - Display the version of this program
-
- clang-rename rename-at options:
-
- -export-fixes=<filename> - YAML file to store suggested fixes in.
- -extra-arg=<string> - Additional argument to append to the compiler command line.
- -extra-arg-before=<string> - Additional argument to prepend to the compiler command line.
- -i - Overwrite edited <file>s.
- -new-name=<string> - The new name to change the symbol to.
- -offset=<uint> - Locates the symbol by offset as opposed to <line>:<column>.
- -p=<string> - Build path.
- -pl - Print the locations affected by renaming to stderr.
- -pn - Print the found symbol's name prior to renaming to stderr.
+ $ clang-rename -input=test.yaml test.cpp
+:program:`clang-rename` offers the following options:
.. code-block:: console
- $ clang-rename rename-all -help
- OVERVIEW: A tool to rename symbols in C/C++ code.
- clang-rename renames every occurrence of a symbol named <old-name>.
-
- USAGE: clang-rename rename-all [subcommand] [options] <source0> [... <sourceN>]
+ $ clang-rename --help
+ USAGE: clang-rename [subcommand] [options] <source0> [... <sourceN>]
OPTIONS:
Generic Options:
- -help - Display available options (-help-hidden for more).
- -help-list - Display list of available options (-help-list-hidden for more).
- -version - Display the version of this program.
+ -help - Display available options (-help-hidden for more)
+ -help-list - Display list of available options (-help-list-hidden for more)
+ -version - Display the version of this program
- clang-rename rename-all options:
+ clang-rename common options:
-export-fixes=<filename> - YAML file to store suggested fixes in.
- -extra-arg=<string> - Additional argument to append to the compiler command line.
- -extra-arg-before=<string> - Additional argument to prepend to the compiler command line.
+ -extra-arg=<string> - Additional argument to append to the compiler command line
+ -extra-arg-before=<string> - Additional argument to prepend to the compiler command line
-i - Overwrite edited <file>s.
-input=<string> - YAML file to load oldname-newname pairs from.
-new-name=<string> - The new name to change the symbol to.
-offset=<uint> - Locates the symbol by offset as opposed to <line>:<column>.
- -old-name=<string> - The fully qualified name of the symbol, if -offset is not used.
- -p=<string> - Build path.
-
+ -p=<string> - Build path
+ -pl - Print the locations affected by renaming to stderr.
+ -pn - Print the found symbol's name prior to renaming to stderr.
+ -qualified-name=<string> - The fully qualified name of the symbol.
Vim Integration
===============
}
// Test 1.
-// RUN: clang-rename rename-all -old-name=Foo -new-name=Bar %s -- | sed 's,//.*,,' | FileCheck %s
+// RUN: clang-rename -qualified-name=Foo -new-name=Bar %s -- | sed 's,//.*,,' | FileCheck %s
};
// Test 1.
-// RUN: clang-rename rename-all -offset=6 -new-name=Bar1 -offset=76 -new-name=Bar2 %s -- | sed 's,//.*,,' | FileCheck %s
+// RUN: clang-rename -offset=6 -new-name=Bar1 -offset=76 -new-name=Bar2 %s -- | sed 's,//.*,,' | FileCheck %s
// To find offsets after modifying the file, use:
// grep -Ubo 'Foo.*' <file>
};
// Test 1.
-// RUN: clang-rename rename-all -old-name=Foo1 -new-name=Bar1 -old-name=Foo2 -new-name=Bar2 %s -- | sed 's,//.*,,' | FileCheck %s
+// RUN: clang-rename -qualified-name=Foo1 -new-name=Bar1 -qualified-name=Foo2 -new-name=Bar2 %s -- | sed 's,//.*,,' | FileCheck %s
+++ /dev/null
-class Foo1 { // CHECK: class Bar1
-};
-
-class Foo2 { // CHECK: class Bar2
-};
-
-// Test 1.
-// RUN: clang-rename rename-all -input %S/Inputs/ClassTestMultiByNameYAMLRenameAll.yaml %s -- | sed 's,//.*,,' | FileCheck %s
-// Test 2.
-// RUN: clang-rename rename-all -input %S/Inputs/ClassTestMultiByNameYAMLRenameAt.yaml %s -- | sed 's,//.*,,' | FileCheck %s
return 0;
}
-// RUN: clang-rename rename-all -old-name=Foo -new-name=Bar %s -- | sed 's,//.*,,' | FileCheck %s
+// RUN: clang-rename -qualified-name=Foo -new-name=Bar %s -- | sed 's,//.*,,' | FileCheck %s
---
-- OldName: Foo1
+- QualifiedName: Foo1
NewName: Bar1
-- OldName: Foo2
+- QualifiedName: Foo2
NewName: Bar2
...
+++ /dev/null
-// RUN: not clang-rename rename-all -new-name=Foo -old-name=Bar %s -- 2>&1 | FileCheck %s
-// CHECK: clang-rename: could not find symbol Bar.
// Check for an error while -new-name argument has not been passed to
// clang-rename.
// RUN: not clang-rename -offset=133 %s 2>&1 | FileCheck %s
-// CHECK: clang-rename: for the -new-name option: must be specified
+// CHECK: clang-rename: -new-name must be specified.
--- /dev/null
+class Foo1 { // CHECK: class Bar1
+};
+
+class Foo2 { // CHECK: class Bar2
+};
+
+// Test 1.
+// RUN: clang-rename -input %S/Inputs/OffsetToNewName.yaml %s -- | sed 's,//.*,,' | FileCheck %s
+// Test 2.
+// RUN: clang-rename -input %S/Inputs/QualifiedNameToNewName.yaml %s -- | sed 's,//.*,,' | FileCheck %s
endfunction()
add_subdirectory(clang-apply-replacements)
-add_subdirectory(clang-rename)
add_subdirectory(clang-query)
add_subdirectory(clang-tidy)
add_subdirectory(include-fixer)
+++ /dev/null
-set(LLVM_LINK_COMPONENTS
- support
- )
-
-get_filename_component(CLANG_RENAME_SOURCE_DIR
- ${CMAKE_CURRENT_SOURCE_DIR}/../../clang-rename REALPATH)
-include_directories(
- ${CLANG_RENAME_SOURCE_DIR}
- )
-
-add_extra_unittest(ClangRenameTests
- USRLocFindingTest.cpp
- ${CLANG_RENAME_SOURCE_DIR}/USRFinder.cpp
- ${CLANG_RENAME_SOURCE_DIR}/USRFindingAction.cpp
- )
-
-target_link_libraries(ClangRenameTests
- clangAST
- clangASTMatchers
- clangBasic
- clangFrontend
- clangIndex
- clangLex
- clangTooling
- )
+++ /dev/null
-#include "USRFindingAction.h"
-#include "clang/Tooling/Tooling.h"
-#include "gtest/gtest.h"
-#include <map>
-#include <set>
-#include <vector>
-
-namespace clang {
-namespace rename {
-namespace test {
-
-// Determines if the symbol group invariants hold. To recap, those invariants
-// are:
-// (1) All symbols in the same symbol group share the same USR.
-// (2) Two symbols from two different groups do not share the same USR.
-static void testOffsetGroups(const char *Code,
- const std::vector<std::vector<unsigned>> Groups) {
- std::set<std::string> AllUSRs, CurrUSR;
-
- for (const auto &Group : Groups) {
- // Groups the invariants do not hold then the value of USR is also invalid,
- // but at that point the test has already failed and USR ceases to be
- // useful.
- std::string USR;
- for (const auto &Offset : Group) {
- USRFindingAction Action(Offset, std::string());
- auto Factory = tooling::newFrontendActionFactory(&Action);
- EXPECT_TRUE(tooling::runToolOnCode(Factory->create(), Code));
- const auto &USRs = Action.getUSRs();
- EXPECT_EQ(1u, USRs.size());
- USR = USRs[0];
- CurrUSR.insert(USR);
- }
- EXPECT_EQ(1u, CurrUSR.size());
- CurrUSR.clear();
- AllUSRs.insert(USR);
- }
-
- EXPECT_EQ(Groups.size(), AllUSRs.size());
-}
-
-
-TEST(USRLocFinding, FindsVarUSR) {
- const char VarTest[] = "\n\
-namespace A {\n\
-int foo;\n\
-}\n\
-int foo;\n\
-int bar = foo;\n\
-int baz = A::foo;\n\
-void fun1() {\n\
- struct {\n\
- int foo;\n\
- } b = { 100 };\n\
- int foo = 100;\n\
- baz = foo;\n\
- {\n\
- extern int foo;\n\
- baz = foo;\n\
- foo = A::foo + baz;\n\
- A::foo = b.foo;\n\
- }\n\
- foo = b.foo;\n\
-}\n";
- std::vector<std::vector<unsigned>> VarTestOffsets(3);
- VarTestOffsets[0].push_back(19);
- VarTestOffsets[0].push_back(63);
- VarTestOffsets[0].push_back(205);
- VarTestOffsets[0].push_back(223);
- VarTestOffsets[1].push_back(30);
- VarTestOffsets[1].push_back(45);
- VarTestOffsets[1].push_back(172);
- VarTestOffsets[1].push_back(187);
- VarTestOffsets[2].push_back(129);
- VarTestOffsets[2].push_back(148);
- VarTestOffsets[2].push_back(242);
-
- testOffsetGroups(VarTest, VarTestOffsets);
-}
-
-} // namespace test
-} // namespace rename
-} // namespace clang