Commit 1c078ec2 authored by Roberto Raggi's avatar Roberto Raggi

Ensure we keep the context around for as long as it is needed.

parent e26cf0ab
......@@ -56,6 +56,19 @@ FindUsages::FindUsages(Document::Ptr doc, const Snapshot &snapshot)
typeofExpression.init(_doc, _snapshot, _context.bindings());
}
FindUsages::FindUsages(const LookupContext &context)
: ASTVisitor(context.thisDocument()->translationUnit()),
_doc(context.thisDocument()),
_snapshot(context.snapshot()),
_context(context),
_source(_doc->source()),
_sem(_doc->translationUnit()),
_inSimpleDeclaration(0),
_inQProperty(false)
{
typeofExpression.init(_doc, _snapshot, _context.bindings());
}
QList<Usage> FindUsages::usages() const
{ return _usages; }
......
......@@ -60,6 +60,7 @@ class CPLUSPLUS_EXPORT FindUsages: protected ASTVisitor
{
public:
FindUsages(Document::Ptr doc, const Snapshot &snapshot);
FindUsages(const LookupContext &context);
void operator()(Symbol *symbol);
......
......@@ -565,6 +565,59 @@ protected:
}
};
struct FindCanonicalSymbol
{
CPPEditor *editor;
QString code;
TypeOfExpression typeOfExpression;
ExpressionUnderCursor expressionUnderCursor;
SemanticInfo info;
FindCanonicalSymbol(CPPEditor *editor, const SemanticInfo &info)
: editor(editor), info(info)
{
typeOfExpression.init(info.doc, info.snapshot);
}
const LookupContext &context() const
{
return typeOfExpression.context();
}
Symbol *operator()(const QTextCursor &cursor)
{
if (! info.doc)
return 0;
QTextCursor tc = cursor;
int line, col;
editor->convertPosition(tc.position(), &line, &col);
++col; // 1-based line and 1-based column
QTextDocument *document = editor->document();
int pos = tc.position();
while (document->characterAt(pos).isLetterOrNumber() ||
document->characterAt(pos) == QLatin1Char('_'))
++pos;
tc.setPosition(pos);
code = expressionUnderCursor(tc);
Scope *scope = info.doc->scopeAt(line, col);
const QList<LookupItem> results = typeOfExpression(code, scope, TypeOfExpression::Preprocess);
for (int i = results.size() - 1; i != -1; --i) { // ### TODO virtual methods and classes.
const LookupItem &r = results.at(i);
if (r.declaration())
return r.declaration();
}
return 0;
}
};
} // end of anonymous namespace
CPPEditorEditable::CPPEditorEditable(CPPEditor *editor)
......@@ -819,46 +872,7 @@ void CPPEditor::onDocumentUpdated(Document::Ptr doc)
updateMethodBoxIndexNow();
}
CPlusPlus::Symbol *CPPEditor::findCanonicalSymbol(const QTextCursor &cursor,
Document::Ptr doc,
const Snapshot &snapshot) const
{
if (! doc)
return 0;
QTextCursor tc = cursor;
int line, col;
convertPosition(tc.position(), &line, &col);
++col; // 1-based line and 1-based column
int pos = tc.position();
while (document()->characterAt(pos).isLetterOrNumber() ||
document()->characterAt(pos) == QLatin1Char('_'))
++pos;
tc.setPosition(pos);
ExpressionUnderCursor expressionUnderCursor;
const QString code = expressionUnderCursor(tc);
// qDebug() << "code:" << code;
TypeOfExpression typeOfExpression;
typeOfExpression.init(doc, snapshot);
Scope *scope = doc->scopeAt(line, col);
const QList<LookupItem> results = typeOfExpression(code, scope, TypeOfExpression::Preprocess);
for (int i = results.size() - 1; i != -1; --i) { // ### TODO virtual methods and classes.
const LookupItem &r = results.at(i);
if (r.declaration())
return r.declaration();
}
return 0;
}
const Macro *CPPEditor::findCanonicalMacro(const QTextCursor &cursor,
Document::Ptr doc) const
const Macro *CPPEditor::findCanonicalMacro(const QTextCursor &cursor, Document::Ptr doc) const
{
if (! doc)
return 0;
......@@ -877,9 +891,13 @@ const Macro *CPPEditor::findCanonicalMacro(const QTextCursor &cursor,
void CPPEditor::findUsages()
{
if (Symbol *canonicalSymbol = markSymbols()) {
m_modelManager->findUsages(m_lastSemanticInfo.doc, canonicalSymbol);
} else if (const Macro *macro = findCanonicalMacro(textCursor(), m_lastSemanticInfo.doc)) {
const SemanticInfo info = m_lastSemanticInfo;
FindCanonicalSymbol cs(this, info);
Symbol *canonicalSymbol = cs(textCursor());
if (canonicalSymbol) {
m_modelManager->findUsages(canonicalSymbol, cs.context());
} else if (const Macro *macro = findCanonicalMacro(textCursor(), info.doc)) {
m_modelManager->findMacroUsages(*macro);
}
}
......@@ -920,7 +938,10 @@ void CPPEditor::hideRenameNotification()
void CPPEditor::renameUsagesNow()
{
if (Symbol *canonicalSymbol = markSymbols()) {
const SemanticInfo info = m_lastSemanticInfo;
FindCanonicalSymbol cs(this, info);
if (Symbol *canonicalSymbol = cs(textCursor())) {
if (canonicalSymbol->identifier() != 0) {
if (showWarningMessage()) {
Core::EditorManager::instance()->showEditorInfoBar(QLatin1String("CppEditor.Rename"),
......@@ -929,12 +950,12 @@ void CPPEditor::renameUsagesNow()
this, SLOT(hideRenameNotification()));
}
m_modelManager->renameUsages(m_lastSemanticInfo.doc, canonicalSymbol);
m_modelManager->renameUsages(canonicalSymbol, cs.context());
}
}
}
Symbol *CPPEditor::markSymbols()
void CPPEditor::markSymbols(Symbol *canonicalSymbol, const SemanticInfo &info)
{
//updateSemanticInfo(m_semanticHighlighter->semanticInfo(currentSource()));
......@@ -942,13 +963,11 @@ Symbol *CPPEditor::markSymbols()
QList<QTextEdit::ExtraSelection> selections;
const SemanticInfo info = m_lastSemanticInfo;
Symbol *canonicalSymbol = findCanonicalSymbol(textCursor(), info.doc, info.snapshot);
if (canonicalSymbol) {
TranslationUnit *unit = info.doc->translationUnit();
const QList<int> references = m_modelManager->references(canonicalSymbol, info.doc, info.snapshot);
LookupContext context(info.doc, info.snapshot); // ### remove me
const QList<int> references = m_modelManager->references(canonicalSymbol, context);
foreach (int index, references) {
unsigned line, column;
unit->getTokenPosition(index, &line, &column);
......@@ -970,7 +989,6 @@ Symbol *CPPEditor::markSymbols()
}
setExtraSelections(CodeSemanticsSelection, selections);
return canonicalSymbol;
}
void CPPEditor::renameSymbolUnderCursor()
......@@ -1938,8 +1956,10 @@ void CPPEditor::updateSemanticInfo(const SemanticInfo &semanticInfo)
if (! m_renameSelections.isEmpty())
setExtraSelections(CodeSemanticsSelection, m_renameSelections); // ###
else
markSymbols();
else {
FindCanonicalSymbol cs(this, semanticInfo);
markSymbols(cs(textCursor()), semanticInfo);
}
m_lastSemanticInfo.forced = false; // clear the forced flag
}
......
......@@ -227,9 +227,6 @@ protected:
virtual bool isInComment(const QTextCursor &cursor) const;
CPlusPlus::Symbol *findCanonicalSymbol(const QTextCursor &cursor,
CPlusPlus::Document::Ptr doc,
const CPlusPlus::Snapshot &snapshot) const;
const CPlusPlus::Macro *findCanonicalMacro(const QTextCursor &cursor,
CPlusPlus::Document::Ptr doc) const;
......@@ -253,7 +250,7 @@ private:
bool showWarningMessage() const;
void setShowWarningMessage(bool showWarningMessage);
CPlusPlus::Symbol *markSymbols();
void markSymbols(CPlusPlus::Symbol *canonicalSymbol, const SemanticInfo &info);
bool sortedMethodOverview() const;
CPlusPlus::Symbol *findDefinition(CPlusPlus::Symbol *symbol, const CPlusPlus::Snapshot &snapshot);
virtual void indentBlock(QTextDocument *doc, QTextBlock block, QChar typedChar);
......
......@@ -167,13 +167,11 @@ CppFindReferences::~CppFindReferences()
{
}
QList<int> CppFindReferences::references(Symbol *symbol,
Document::Ptr doc,
const Snapshot& snapshot) const
QList<int> CppFindReferences::references(Symbol *symbol, const LookupContext &context) const
{
QList<int> references;
FindUsages findUsages(doc, snapshot);
FindUsages findUsages(context);
findUsages(symbol);
references = findUsages.references();
......@@ -182,9 +180,8 @@ QList<int> CppFindReferences::references(Symbol *symbol,
static void find_helper(QFutureInterface<Usage> &future,
const CppTools::CppModelManagerInterface::WorkingCopy workingCopy,
Snapshot snapshot,
Document::Ptr symbolDocument,
DependencyTable dependencyTable,
const LookupContext context,
const DependencyTable dependencyTable,
Symbol *symbol)
{
QTime tm;
......@@ -197,7 +194,7 @@ static void find_helper(QFutureInterface<Usage> &future,
QStringList files(sourceFile);
if (symbol->isClass() || symbol->isForwardClassDeclaration()) {
foreach (const Document::Ptr &doc, snapshot) {
foreach (const Document::Ptr &doc, context.snapshot()) {
if (doc->fileName() == sourceFile)
continue;
......@@ -214,7 +211,7 @@ static void find_helper(QFutureInterface<Usage> &future,
future.setProgressRange(0, files.size());
ProcessFile process(workingCopy, snapshot, symbolDocument, symbol);
ProcessFile process(workingCopy, context.snapshot(), context.thisDocument(), symbol);
UpdateUI reduce(&future);
QtConcurrent::blockingMappedReduced<QList<Usage> > (files, process, reduce);
......@@ -238,17 +235,17 @@ void CppFindReferences::updateDependencyTable()
m_depsFuture = QtConcurrent::run(&dependencyTable, m_deps, _modelManager->snapshot());
}
void CppFindReferences::findUsages(Document::Ptr symbolDocument, Symbol *symbol)
void CppFindReferences::findUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context)
{
Find::SearchResult *search = _resultWindow->startNewSearch(Find::SearchResultWindow::SearchOnly);
connect(search, SIGNAL(activated(Find::SearchResultItem)),
this, SLOT(openEditor(Find::SearchResultItem)));
findAll_helper(symbolDocument, symbol);
findAll_helper(symbol, context);
}
void CppFindReferences::renameUsages(Document::Ptr symbolDocument, Symbol *symbol)
void CppFindReferences::renameUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context)
{
if (const Identifier *id = symbol->identifier()) {
const QString textToReplace = QString::fromUtf8(id->chars(), id->size());
......@@ -262,11 +259,11 @@ void CppFindReferences::renameUsages(Document::Ptr symbolDocument, Symbol *symbo
connect(search, SIGNAL(replaceButtonClicked(QString,QList<Find::SearchResultItem>)),
SLOT(onReplaceButtonClicked(QString,QList<Find::SearchResultItem>)));
findAll_helper(symbolDocument, symbol);
findAll_helper(symbol, context);
}
}
void CppFindReferences::findAll_helper(Document::Ptr symbolDocument, Symbol *symbol)
void CppFindReferences::findAll_helper(Symbol *symbol, const LookupContext &context)
{
if (! (symbol && symbol->identifier()))
return;
......@@ -283,7 +280,7 @@ void CppFindReferences::findAll_helper(Document::Ptr symbolDocument, Symbol *sym
QFuture<Usage> result;
result = QtConcurrent::run(&find_helper, workingCopy, snapshot, symbolDocument, m_deps, symbol);
result = QtConcurrent::run(&find_helper, workingCopy, context, m_deps, symbol);
m_watcher.setFuture(result);
Core::FutureProgress *progress = progressManager->addTask(result, tr("Searching"),
......
......@@ -59,16 +59,14 @@ public:
CppFindReferences(CppModelManagerInterface *modelManager);
virtual ~CppFindReferences();
QList<int> references(CPlusPlus::Symbol *symbol,
CPlusPlus::Document::Ptr doc,
const CPlusPlus::Snapshot& snapshot) const;
QList<int> references(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context) const;
Q_SIGNALS:
void changed();
public:
void findUsages(CPlusPlus::Document::Ptr symbolDocument,CPlusPlus::Symbol *symbol);
void renameUsages(CPlusPlus::Document::Ptr symbolDocument,CPlusPlus::Symbol *symbol);
void findUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
void renameUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
void findMacroUses(const CPlusPlus::Macro &macro);
......@@ -80,7 +78,7 @@ private Q_SLOTS:
void updateDependencyTable();
private:
void findAll_helper(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol);
void findAll_helper(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
private:
QPointer<CppModelManagerInterface> _modelManager;
......
......@@ -785,23 +785,21 @@ void CppModelManager::removeEditorSupport(AbstractEditorSupport *editorSupport)
m_addtionalEditorSupport.remove(editorSupport);
}
QList<int> CppModelManager::references(CPlusPlus::Symbol *symbol,
CPlusPlus::Document::Ptr doc,
const CPlusPlus::Snapshot &snapshot)
QList<int> CppModelManager::references(CPlusPlus::Symbol *symbol, const LookupContext &context)
{
return m_findReferences->references(symbol, doc, snapshot);
return m_findReferences->references(symbol, context);
}
void CppModelManager::findUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol)
void CppModelManager::findUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context)
{
if (symbol->identifier())
m_findReferences->findUsages(symbolDocument, symbol);
m_findReferences->findUsages(symbol, context);
}
void CppModelManager::renameUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol)
void CppModelManager::renameUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context)
{
if (symbol->identifier())
m_findReferences->renameUsages(symbolDocument, symbol);
m_findReferences->renameUsages(symbol, context);
}
void CppModelManager::findMacroUsages(const CPlusPlus::Macro &macro)
......
......@@ -116,12 +116,10 @@ public:
virtual void addEditorSupport(AbstractEditorSupport *editorSupport);
virtual void removeEditorSupport(AbstractEditorSupport *editorSupport);
virtual QList<int> references(CPlusPlus::Symbol *symbol,
CPlusPlus::Document::Ptr doc,
const CPlusPlus::Snapshot &snapshot);
virtual QList<int> references(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
virtual void findUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol);
virtual void renameUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol);
virtual void renameUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
virtual void findUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context);
virtual void findMacroUsages(const CPlusPlus::Macro &macro);
......
......@@ -38,6 +38,10 @@
#include <QtCore/QStringList>
#include <QtCore/QFuture>
namespace CPlusPlus {
class LookupContext;
}
namespace ProjectExplorer {
class Project;
}
......@@ -119,11 +123,10 @@ public:
virtual void removeEditorSupport(AbstractEditorSupport *editorSupport) = 0;
virtual QList<int> references(CPlusPlus::Symbol *symbol,
CPlusPlus::Document::Ptr doc,
const CPlusPlus::Snapshot &snapshot) = 0;
const CPlusPlus::LookupContext &context) = 0;
virtual void renameUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol) = 0;
virtual void findUsages(CPlusPlus::Document::Ptr symbolDocument, CPlusPlus::Symbol *symbol) = 0;
virtual void renameUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context) = 0;
virtual void findUsages(CPlusPlus::Symbol *symbol, const CPlusPlus::LookupContext &context) = 0;
virtual void findMacroUsages(const CPlusPlus::Macro &macro) = 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment