[clang-move] ignore unsupported symbol kinds when checking if all symbols are moved.

llvm-svn: 288791
This commit is contained in:
Eric Liu 2016-12-06 10:12:23 +00:00
parent 8977223e55
commit 47a42d53fc
3 changed files with 41 additions and 5 deletions

View File

@ -713,7 +713,24 @@ void ClangMoveTool::onEndOfTranslationUnit() {
if (RemovedDecls.empty())
return;
if (UnremovedDeclsInOldHeader.empty() && !Context->Spec.OldHeader.empty()) {
// Ignore symbols that are not supported (e.g. typedef and enum) when
// checking if there is unremoved symbol in old header. This makes sure that
// we always move old files to new files when all symbols produced from
// dump_decls are moved.
auto IsSupportedKind = [](const clang::NamedDecl *Decl) {
switch (Decl->getKind()) {
case Decl::Kind::Function:
case Decl::Kind::FunctionTemplate:
case Decl::Kind::ClassTemplate:
case Decl::Kind::CXXRecord:
return true;
default:
return false;
}
};
if (std::none_of(UnremovedDeclsInOldHeader.begin(),
UnremovedDeclsInOldHeader.end(), IsSupportedKind) &&
!Context->Spec.OldHeader.empty()) {
auto &SM = RemovedDecls[0]->getASTContext().getSourceManager();
moveAll(SM, Context->Spec.OldHeader, Context->Spec.NewHeader);
moveAll(SM, Context->Spec.OldCC, Context->Spec.NewCC);

View File

@ -95,7 +95,9 @@ struct ClangMoveContext {
// The goal of this tool is to make the new files as compliable as possible.
//
// Note: When all declarations in old header are being moved, all code in
// old.h/cc will be moved, which means old.h/cc are empty.
// old.h/cc will be moved, which means old.h/cc are empty. This ignores symbols
// that are not supported (e.g. typedef and enum) so that we always move old
// files to new files when all symbols produced from dump_decls are moved.
class ClangMoveTool : public ast_matchers::MatchFinder::MatchCallback {
public:
ClangMoveTool(ClangMoveContext *const Context,

View File

@ -330,11 +330,8 @@ TEST(ClangMove, DontMoveAll) {
"#endif // NEW_FOO_H\n";
const char Code[] = "#include \"foo.h\"\nint A::f() { return 0; }";
std::vector<std::string> TestHeaders = {
"typedef int Int;\nclass A {\npublic:\n int f();\n};\n",
"using Int=int;\nclass A {\npublic:\n int f();\n};\n",
"class B {};\nclass A {\npublic:\n int f();\n};\n",
"void f() {};\nclass A {\npublic:\n int f();\n};\n",
"enum Color { RED };\nclass A {\npublic:\n int f();\n};\n",
};
move::MoveDefinitionSpec Spec;
Spec.Names.push_back("A");
@ -351,6 +348,26 @@ TEST(ClangMove, DontMoveAll) {
}
}
TEST(ClangMove, IgnoreUnsupportedKindsAndMoveAll) {
const char Code[] = "#include \"foo.h\"\nint A::f() { return 0; }";
std::vector<std::string> TestHeaders = {
"typedef int Int;\nclass A {\npublic:\n int f();\n};\n",
"using Int = int;\nclass A {\npublic:\n int f();\n};\n",
"enum Color { RED };\nclass A {\npublic:\n int f();\n};\n",
};
move::MoveDefinitionSpec Spec;
Spec.Names.push_back("A");
Spec.OldHeader = "foo.h";
Spec.OldCC = "foo.cc";
Spec.NewHeader = "new_foo.h";
Spec.NewCC = "new_foo.cc";
for (const auto &Header : TestHeaders) {
auto Results = runClangMoveOnCode(Spec, Header.c_str(), Code);
EXPECT_EQ(Header, Results[Spec.NewHeader]);
EXPECT_EQ("", Results[Spec.OldHeader]);
}
}
TEST(ClangMove, MacroInFunction) {
const char TestHeader[] = "#define INT int\n"
"class A {\npublic:\n int f();\n};\n"