[prev in list] [next in list] [prev in thread] [next in thread]
List: kde-commits
Subject: =?utf-8?q?=5Bkdev-python=5D_duchain=3A_Re-declaring_a_function_a?=
From: Sven Brauch <svenbrauch () googlemail ! com>
Date: 2011-06-20 23:06:52
Message-ID: 20110620230652.B5006A60A4 () git ! kde ! org
[Download RAW message or body]
Git commit 9e6cd846bf11813ef15ab40da1b7437055422990 by Sven Brauch.
Committed on 20/06/2011 at 23:13.
Pushed by brauch into branch 'master'.
Re-declaring a function as a non-function is now reported as an error.
We might want to support this later, but it's too difficult for now.
BUG:276100
M +25 -2 duchain/declarationbuilder.cpp
M +3 -13 duchain/expressionvisitor.cpp
M +15 -2 duchain/helpers.cpp
M +11 -1 duchain/helpers.h
http://commits.kde.org/kdev-python/9e6cd846bf11813ef15ab40da1b7437055422990
diff --git a/duchain/declarationbuilder.cpp b/duchain/declarationbuilder.cpp
index 20861e5..8a6f632 100644
--- a/duchain/declarationbuilder.cpp
+++ b/duchain/declarationbuilder.cpp
@@ -149,7 +149,7 @@ template<typename T> T* \
DeclarationBuilder::visitVariableDeclaration(Identifier* }
}
if ( existingDeclarations.length() ) {
- Declaration* d = existingDeclarations.last();
+ Declaration* d = existingDeclarations.first();
kDebug() << "last one: " << d << d->toString() << dynamic_cast<T*>(d) << \
wasEncountered(d); if ( dynamic_cast<T*>(d) && ! wasEncountered(d) ) {
kDebug() << "Opening previously existing declaration for " << \
d->toString(); @@ -161,6 +161,27 @@ template<typename T> T* \
DeclarationBuilder::visitVariableDeclaration(Identifier* }
}
+ if ( dec || ! existingDeclarations.isEmpty() ) {
+ Declaration* d = dec ? dec : existingDeclarations.first();
+ Q_ASSERT(d);
+ d = Helper::resolveAliasDeclaration(d);
+ if ( d && d->abstractType() && lastType() && lastType()->whichType() != \
AbstractType::TypeFunction && d->isFunctionDeclaration() ) { + kWarning() \
<< "Found re-declaration, reporting error"; + kDebug() << \
d->abstractType()->toString() << lastType()->toString() << \
d->abstractType()->whichType() << lastType()->whichType(); + // assigning \
e.g. an integral value to something that was a function definition previously + \
// is difficult to handle and most likely not what you want, so we just report an \
error. + KDevelop::Problem *p = new KDevelop::Problem();
+ p->setFinalLocation(DocumentRange(currentlyParsedDocument(), \
SimpleRange( + node->startLine, node->startCol, \
node->startLine, (node->startLine == node->endLine ? node->endCol + 1 : 100)))); + \
p->setSource(KDevelop::ProblemData::SemanticAnalysis); + \
p->setSeverity(KDevelop::ProblemData::Error); + \
p->setDescription(i18n("Re-declaration of \"" + node->value.toAscii() + "\" shadows a \
previous declaration with different type")); + ProblemPointer ptr(p);
+ topContext()->addProblem(ptr);
+ return 0;
+ }
+ }
+
kDebug() << "VARIABLE CONTEXT: " << currentContext()->scopeIdentifier() << \
currentContext()->range().castToSimpleRange() << currentContext()->type() << \
DUContext::Class;
bool noFittingDeclaration = existingDeclarations.isEmpty() || ( ! \
existingDeclarations.isEmpty() && ! dynamic_cast<T*>(existingDeclarations.last()) ); \
@@ -323,6 +344,7 @@ Declaration* \
DeclarationBuilder::createModuleImportDeclaration(QString dottedNam \
StructureType::Ptr moduleType(new StructureType()); openType(moduleType);
DUChainWriteLocker lock(DUChain::lock());
+ setLastType(AbstractType::Ptr(0));
resultingDeclaration = \
visitVariableDeclaration<Declaration>(declarationIdentifier, range); \
Q_ASSERT(resultingDeclaration); closeType();
@@ -439,7 +461,7 @@ void DeclarationBuilder::visitAssignment(AssignmentAst* node)
DUChainWriteLocker lock(DUChain::lock());
Declaration* dec = visitVariableDeclaration<Declaration>(target);
/** DEBUG **/
- if ( tupleElementType ) {
+ if ( tupleElementType && dec ) {
VariableLengthContainer* type = \
dynamic_cast<VariableLengthContainer*>(dec->abstractType().unsafeData());
kDebug() << "type is: " << dec->abstractType().unsafeData() << \
type << \
dynamic_cast<VariableLengthContainer*>(tupleElementType.unsafeData());
kDebug() << "indexed: " << tupleElementType->indexed().hash() << \
"<>" << dec->indexedType().hash(); @@ -625,6 +647,7 @@ void \
DeclarationBuilder::visitFunctionDefinition( FunctionDefinitionAst* node ) \
QList<Declaration*> existing;
FunctionDeclaration* dec = openDeclaration<FunctionDeclaration>( node->name, \
node ); + Q_ASSERT(dec->isFunctionDeclaration());
type = FunctionType::Ptr(new FunctionType());
type->setReturnType(AbstractType::Ptr(new \
IntegralType(IntegralType::TypeVoid)));
diff --git a/duchain/expressionvisitor.cpp b/duchain/expressionvisitor.cpp
index e03eff2..c1710d5 100644
--- a/duchain/expressionvisitor.cpp
+++ b/duchain/expressionvisitor.cpp
@@ -81,16 +81,6 @@ void ExpressionVisitor::unknownTypeEncountered() {
encounter(AbstractType::Ptr(new IntegralType(IntegralType::TypeMixed)));
}
-Declaration* ExpressionVisitor::resolveAliasDeclaration(Declaration* decl)
-{
- AliasDeclaration* alias = dynamic_cast<AliasDeclaration*>(decl);
- if ( alias ) {
- return alias->aliasedDeclaration().data();
- }
- else
- return decl;
-}
-
void ExpressionVisitor::setTypesForEventualCall(DeclarationPointer \
actualDeclaration, AttributeAst* node, bool extendUnsureTypes) {
// if it's a function call, the result of that call will be the return type
@@ -196,7 +186,7 @@ void ExpressionVisitor::visitAttribute(AttributeAst* node)
lock.unlock();
kDebug() << "Found declarations for dotted name import: " << found;
if ( ! found.isEmpty() ) {
- Declaration* real = resolveAliasDeclaration(found.last());
+ Declaration* real = Helper::resolveAliasDeclaration(found.last());
DeclarationPointer ptr = DeclarationPointer(real);
setLastAccessedDeclaration(ptr);
setLastAccessedAttributeDeclaration(ptr);
@@ -294,7 +284,7 @@ void ExpressionVisitor::visitAttribute(AttributeAst* node)
// Step 5: Construct the type of the declaration which was found.
DeclarationPointer actualDeclaration(0);
if ( foundDecls.length() > 0 ) {
- actualDeclaration = \
DeclarationPointer(resolveAliasDeclaration(foundDecls.last())); + \
actualDeclaration = DeclarationPointer(Helper::resolveAliasDeclaration(foundDecls.last()));
m_lastAccessedAttributeDeclaration = toSharedPtrList(foundDecls);
m_lastAccessedDeclaration = toSharedPtrList(foundDecls);
bool extendUnsure = false;
@@ -336,7 +326,7 @@ void ExpressionVisitor::visitCall(CallAst* node)
return unknownTypeEncountered();
}
else {
- Declaration* actualDeclaration = resolveAliasDeclaration(decls.last());
+ Declaration* actualDeclaration = \
Helper::resolveAliasDeclaration(decls.last());
kDebug() << "Resolved alias declaration: " << decls.last()->toString();
ClassDeclaration* classDecl = \
dynamic_cast<ClassDeclaration*>(actualDeclaration);
FunctionDeclaration* funcDecl = \
dynamic_cast<FunctionDeclaration*>(actualDeclaration);
diff --git a/duchain/helpers.cpp b/duchain/helpers.cpp
index 226737d..59cfcde 100644
--- a/duchain/helpers.cpp
+++ b/duchain/helpers.cpp
@@ -13,6 +13,7 @@
#include <language/duchain/duchainlock.h>
#include <language/duchain/duchain.h>
#include <language/duchain/classdeclaration.h>
+#include <language/duchain/aliasdeclaration.h>
using namespace KDevelop;
@@ -20,7 +21,7 @@ namespace Python {
QList<KUrl> Helper::cachedSearchPaths;
-QList< DUContext* > Helper::inernalContextsForClass(StructureType::Ptr klassType, \
TopDUContext* context) +QList< DUContext* > \
Helper::inernalContextsForClass(StructureType::Ptr klassType, TopDUContext* context, \
int depth) {
QList<DUContext*> searchContexts;
if ( ! klassType ) {
@@ -36,11 +37,23 @@ QList< DUContext* > \
Helper::inernalContextsForClass(StructureType::Ptr klassType
StructureType::Ptr baseClassType = base.baseClass.type<StructureType>();
kDebug() << "Base class type: " << baseClassType;
// recursive call, because the base class will have more base classes \
eventually
- searchContexts.append(Helper::inernalContextsForClass(baseClassType, \
context)); + if ( depth < 10 ) {
+ searchContexts.append(Helper::inernalContextsForClass(baseClassType, \
context, depth + 1)); + }
}
}
return searchContexts;
}
+
+Declaration* Helper::resolveAliasDeclaration(Declaration* decl)
+{
+ AliasDeclaration* alias = dynamic_cast<AliasDeclaration*>(decl);
+ if ( alias ) {
+ return alias->aliasedDeclaration().data();
+ }
+ else
+ return decl;
+}
QList<KUrl> Helper::getSearchPaths(KUrl workingOnDocument)
{
diff --git a/duchain/helpers.h b/duchain/helpers.h
index 2cb5b42..6611046 100644
--- a/duchain/helpers.h
+++ b/duchain/helpers.h
@@ -12,6 +12,7 @@
#include <KDebug>
#include "pythonduchainexport.h"
+#include <language/duchain/declaration.h>
using namespace KDevelop;
@@ -46,7 +47,16 @@ public:
* @param context TopContext for finding the declarations for types
* @return list of contexts which were found
**/
- static QList<DUContext*> inernalContextsForClass(KDevelop::StructureType::Ptr \
klassType, TopDUContext* context); + static QList<DUContext*> \
inernalContextsForClass(KDevelop::StructureType::Ptr klassType, TopDUContext* \
context, int depth = 0); +
+ /**
+ * @brief Resolve the given declaration if it is an alias declaration.
+ *
+ * @param decl the declaration to resolve
+ * @return :Declaration* decl if not an alias declaration, \
decl->aliasedDeclaration().data otherwise + * DUChain must be read locked
+ **/
+ static Declaration* resolveAliasDeclaration(Declaration* decl);
};
}
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic