Clang: Fix local references for operator arguments

Workaround for wrong cursor annotated by Clang.

Use clang_getCursor in case of the variable used as
operator argument to get the proper cursor.

Task-number: QTCREATORBUG-20966
Change-Id: Idb195bffc2296f3fae27595cf9c43c9e6b2c5cd0
Reviewed-by: Marco Bubke <marco.bubke@qt.io>
This commit is contained in:
Ivan Donchevskii
2018-08-21 10:23:12 +02:00
parent 8d0391a4f9
commit 8c21a7a396
3 changed files with 74 additions and 4 deletions

View File

@@ -43,8 +43,15 @@ namespace {
class ReferencedCursor
{
public:
static ReferencedCursor find(const Cursor &cursor)
static ReferencedCursor find(const Cursor &cursor, const CXToken &token)
{
if (cursor.spelling().startsWith("operator")
&& clang_getTokenKind(token) == CXToken_Identifier) {
// We are actually inside operator, use clang_getCursor to return a proper cursor instead.
return find(clang_getCursor(cursor.cxTranslationUnit(),
clang_getTokenLocation(cursor.cxTranslationUnit(), token)),
token);
}
// Query the referenced cursor directly instead of first testing with cursor.isReference().
// cursor.isReference() reports false for e.g. CXCursor_DeclRefExpr or CXCursor_CallExpr
// although it returns a valid cursor.
@@ -194,7 +201,7 @@ bool ReferencesCollector::checkToken(unsigned index, const Utf8String &identifie
return false;
{ // For debugging only
// const SourceRange range = clang_getTokenExtent(m_cxTranslationUnit, token);
// const SourceRange range{m_cxTranslationUnit, clang_getTokenExtent(m_cxTranslationUnit, token)};
// const uint line = range.start().line();
// const ClangString spellingCs = clang_getTokenSpelling(m_cxTranslationUnit, token);
// const Utf8String spelling = spellingCs;
@@ -202,7 +209,7 @@ bool ReferencesCollector::checkToken(unsigned index, const Utf8String &identifie
}
const Cursor currentCursor(m_cxCursors[static_cast<int>(index)]);
const ReferencedCursor candidate = ReferencedCursor::find(currentCursor);
const ReferencedCursor candidate = ReferencedCursor::find(currentCursor, token);
return candidate.usr() == usr;
}
@@ -217,7 +224,7 @@ ReferencesResult ReferencesCollector::collect(uint line, uint column, bool local
const Cursor cursorFromUser = m_cxCursors[static_cast<int>(index)];
const ReferencedCursor refCursor = ReferencedCursor::find(cursorFromUser);
const ReferencedCursor refCursor = ReferencedCursor::find(cursorFromUser, m_cxTokens[index]);
const Utf8String usr = refCursor.usr();
if (usr.isEmpty())
return result;