better templates, index some initializer list values

This commit is contained in:
Jacob Dufault 2017-03-05 15:44:20 -08:00
parent 8e36152406
commit e06f9472c1
7 changed files with 217 additions and 3 deletions

View File

@ -354,6 +354,10 @@ void VisitDeclForTypeUsageVisitorHandler(clang::Cursor cursor, VisitDeclForTypeU
IndexedFile* db = param->db; IndexedFile* db = param->db;
std::string referenced_usr = cursor.get_referenced().template_specialization_to_template_definition().get_usr(); std::string referenced_usr = cursor.get_referenced().template_specialization_to_template_definition().get_usr();
// TODO: things in STL cause this to be empty. Figure out why and document it.
if (referenced_usr == "")
return;
TypeId ref_type_id = db->ToTypeId(referenced_usr); TypeId ref_type_id = db->ToTypeId(referenced_usr);
if (!param->initial_type) if (!param->initial_type)
@ -384,8 +388,25 @@ clang::VisiterResult VisitDeclForTypeUsageVisitor(clang::Cursor cursor, clang::C
} }
param->previous_cursor = cursor; param->previous_cursor = cursor;
break;
// We do not want to recurse for everything, since if we do that we will end
// up visiting method definition bodies/etc. Instead, we only recurse for
// things that can logically appear as part of an inline variable initializer,
// ie,
//
// class Foo {
// int x = (Foo)3;
// }
case CXCursor_CallExpr:
case CXCursor_CStyleCastExpr:
case CXCursor_CXXStaticCastExpr:
case CXCursor_CXXReinterpretCastExpr:
return clang::VisiterResult::Recurse;
} }
return clang::VisiterResult::Continue; return clang::VisiterResult::Continue;
} }
@ -408,6 +429,10 @@ optional<TypeId> ResolveToDeclarationType(IndexedFile* db, clang::Cursor cursor)
optional<TypeId> AddDeclUsages(IndexedFile* db, clang::Cursor decl_cursor, optional<TypeId> AddDeclUsages(IndexedFile* db, clang::Cursor decl_cursor,
bool is_interesting, const CXIdxContainerInfo* semantic_container, bool is_interesting, const CXIdxContainerInfo* semantic_container,
const CXIdxContainerInfo* lexical_container) { const CXIdxContainerInfo* lexical_container) {
//std::cerr << std::endl << "AddDeclUsages " << decl_cursor.get_spelling() << std::endl;
//Dump(decl_cursor);
// //
// The general AST format for definitions follows this pattern: // The general AST format for definitions follows this pattern:
// //
@ -534,6 +559,13 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
case CXIdxEntity_CXXStaticVariable: case CXIdxEntity_CXXStaticVariable:
{ {
clang::Cursor decl_cursor = decl->cursor; clang::Cursor decl_cursor = decl->cursor;
// Do not index implicit template instantiations.
if (decl_cursor != decl_cursor.template_specialization_to_template_definition())
break;
std::string decl_usr = decl_cursor.get_usr();
VarId var_id = db->ToVarId(decl->entityInfo->USR); VarId var_id = db->ToVarId(decl->entityInfo->USR);
IndexedVarDef* var_def = db->Resolve(var_id); IndexedVarDef* var_def = db->Resolve(var_id);
@ -969,7 +1001,7 @@ IndexedFile Parse(std::string filename, std::vector<std::string> args, bool dump
NamespaceHelper ns; NamespaceHelper ns;
IndexParam param(&db, &ns); IndexParam param(&db, &ns);
clang_indexTranslationUnit(index_action, &param, callbacks, sizeof(callbacks), clang_indexTranslationUnit(index_action, &param, callbacks, sizeof(callbacks),
CXIndexOpt_IndexFunctionLocalSymbols | CXIndexOpt_SkipParsedBodiesInSession | CXIndexOpt_IndexImplicitTemplateInstantiations, tu.cx_tu); CXIndexOpt_IndexFunctionLocalSymbols | CXIndexOpt_SkipParsedBodiesInSession, tu.cx_tu);
clang_IndexAction_dispose(index_action); clang_IndexAction_dispose(index_action);

View File

@ -106,6 +106,10 @@ bool Cursor::operator==(const Cursor& rhs) const {
return clang_equalCursors(cx_cursor, rhs.cx_cursor); return clang_equalCursors(cx_cursor, rhs.cx_cursor);
} }
bool Cursor::operator!=(const Cursor& rhs) const {
return !(*this == rhs);
}
CXCursorKind Cursor::get_kind() const { CXCursorKind Cursor::get_kind() const {
return cx_cursor.kind; return cx_cursor.kind;
} }

View File

@ -47,8 +47,9 @@ public:
Cursor(); Cursor();
Cursor(const CXCursor& other); Cursor(const CXCursor& other);
operator bool() const; explicit operator bool() const;
bool operator==(const Cursor& rhs) const; bool operator==(const Cursor& rhs) const;
bool operator!=(const Cursor& rhs) const;
CXCursorKind get_kind() const; CXCursorKind get_kind() const;
Type get_type() const; Type get_type() const;

View File

@ -94,7 +94,7 @@ int main(int argc, char** argv) {
*/ */
for (std::string path : GetFilesInFolder("tests", true /*add_folder_to_path*/)) { for (std::string path : GetFilesInFolder("tests", true /*add_folder_to_path*/)) {
//if (path == "tests/foobar.cc") continue; //if (path != "tests/usage/var_usage_cstyle_cast.cc") continue;
//if (path == "tests/inheritance/class_inherit_templated_parent.cc") continue; //if (path == "tests/inheritance/class_inherit_templated_parent.cc") continue;
//if (path != "tests/templates/template_class_type_usage_folded_into_one.cc") continue; //if (path != "tests/templates/template_class_type_usage_folded_into_one.cc") continue;

View File

@ -9,6 +9,9 @@ struct Foo {
Foo<A>::Inner a; Foo<A>::Inner a;
Foo<B> b; Foo<B> b;
//#include <string>
#if false #if false
// We could store how many template parameters Foo has and then skip that many TypeRefs..., // We could store how many template parameters Foo has and then skip that many TypeRefs...,

View File

@ -0,0 +1,63 @@
namespace ns {
enum VarType {};
template<typename _>
struct Holder {
static constexpr VarType static_var = (VarType)0x0;
};
template<typename _>
const typename VarType Holder<_>::static_var;
int Foo = Holder<int>::static_var;
int Foo2 = Holder<int>::static_var;
}
/*
OUTPUT:
{
"types": [{
"id": 0,
"usr": "c:@N@ns@E@VarType",
"short_name": "VarType",
"qualified_name": "ns::VarType",
"definition": "1:2:8",
"uses": ["*1:2:8", "*1:6:22", "*1:6:44", "*1:10:18"]
}, {
"id": 1,
"usr": "c:@N@ns@ST>1#T@Holder",
"short_name": "Holder",
"qualified_name": "ns::Holder",
"definition": "1:5:10",
"vars": [0],
"uses": ["*1:5:10", "*1:10:26", "1:13:13", "1:14:14"]
}],
"functions": [],
"variables": [{
"id": 0,
"usr": "c:@N@ns@ST>1#T@Holder@static_var",
"short_name": "static_var",
"qualified_name": "ns::Holder::static_var",
"declaration": "1:6:30",
"definition": "1:10:37",
"variable_type": 0,
"declaring_type": 1,
"uses": ["1:6:30", "1:10:37", "1:13:26", "1:14:27"]
}, {
"id": 1,
"usr": "c:@N@ns@Foo",
"short_name": "Foo",
"qualified_name": "ns::Foo",
"definition": "1:13:7",
"uses": ["1:13:7"]
}, {
"id": 2,
"usr": "c:@N@ns@Foo2",
"short_name": "Foo2",
"qualified_name": "ns::Foo2",
"definition": "1:14:7",
"uses": ["1:14:7"]
}]
}
*/

View File

@ -0,0 +1,111 @@
enum VarType {};
struct Holder {
static constexpr VarType static_var = (VarType)0x0;
};
const VarType Holder::static_var;
/*
OUTPUT:
{
"types": [{
"id": 0,
"usr": "c:@E@VarType",
"short_name": "VarType",
"qualified_name": "VarType",
"definition": "1:1:6",
"uses": ["*1:1:6", "*1:4:20", "*1:4:42", "*1:7:7"]
}, {
"id": 1,
"usr": "c:@S@Holder",
"short_name": "Holder",
"qualified_name": "Holder",
"definition": "1:3:8",
"vars": [0],
"uses": ["*1:3:8", "1:7:15"]
}],
"functions": [],
"variables": [{
"id": 0,
"usr": "c:@S@Holder@static_var",
"short_name": "static_var",
"qualified_name": "Holder::static_var",
"declaration": "1:4:28",
"definition": "1:7:23",
"variable_type": 0,
"declaring_type": 1,
"uses": ["1:4:28", "1:7:23"]
}]
}
*/
//#include <string>
//#include <xiosbase>
//#include <sstream>
//#include <algorithm>
//#include <vector>
//#include <string>
//#include <cstddef>
//#include <sstream>
//#include <iomanip>
//#include <limits>
//#include <vector>
//#include <cstddef>
//#include <tuple>
//#include <type_traits>
//#include <string>
//#include <string>
//#include <type_traits>
//#include <iterator>
//#include <vector>
//#include <string>
//#include <stdlib.h>
//#include <string>
//#include <vector>
//#include <string>
//#include <cstddef>
//#include <cmath>
//#include <limits>
//#include <type_traits>
//#include <set>
//#include <string>
//#include <vector>
//#include <iosfwd>
//#include <streambuf>
//#include <ostream>
//#include <fstream>
//#include <memory>
//#include <vector>
//#include <string>
//#include <stdexcept>
//#include <string>
//#include <vector>
//#include <sstream>
//#include <algorithm>