File indexing completed on 2024-05-12 04:38:01

0001 /*
0002     SPDX-FileCopyrightText: 2006 Hamish Rodda <rodda@kde.org>
0003     SPDX-FileCopyrightText: 2007-2008 David Nolden <david.nolden.kdevelop@art-master.de>
0004 
0005     SPDX-License-Identifier: LGPL-2.0-only
0006 */
0007 
0008 #include "forwarddeclaration.h"
0009 
0010 #include <KLocalizedString>
0011 
0012 #include "duchain.h"
0013 #include "duchainlock.h"
0014 #include "ducontext.h"
0015 #include "use.h"
0016 #include "duchainregister.h"
0017 #include "types/identifiedtype.h"
0018 
0019 using namespace KTextEditor;
0020 
0021 namespace KDevelop {
0022 REGISTER_DUCHAIN_ITEM(ForwardDeclaration);
0023 
0024 ForwardDeclaration::ForwardDeclaration(const ForwardDeclaration& rhs) : Declaration(*new ForwardDeclarationData(*rhs.
0025             d_func()))
0026 {
0027 }
0028 
0029 ForwardDeclaration::ForwardDeclaration(ForwardDeclarationData& data) : Declaration(data)
0030 {
0031 }
0032 
0033 ForwardDeclaration::ForwardDeclaration(const RangeInRevision& range, DUContext* context)
0034     : Declaration(*new ForwardDeclarationData, range)
0035 {
0036     d_func_dynamic()->setClassId(this);
0037     if (context)
0038         setContext(context);
0039 }
0040 
0041 ForwardDeclaration::~ForwardDeclaration()
0042 {
0043 }
0044 
0045 QString ForwardDeclaration::toString() const
0046 {
0047     if (context())
0048         return qualifiedIdentifier().toString();
0049     else
0050         return i18n("context-free forward-declaration %1", identifier().toString());
0051 }
0052 
0053 Declaration* ForwardDeclaration::resolve(const TopDUContext* topContext) const
0054 {
0055     ENSURE_CAN_READ
0056 
0057     //If we've got a type assigned, that counts as a way of resolution.
0058     AbstractType::Ptr t = abstractType();
0059     auto* idType = dynamic_cast<IdentifiedType*>(t.data());
0060     if (idType) {
0061         Declaration* decl = idType->declaration(topContext);
0062         if (decl && !decl->isForwardDeclaration())
0063             return decl;
0064         else
0065             return nullptr;
0066     }
0067 
0068     if (!topContext)
0069         topContext = this->topContext();
0070 
0071     QualifiedIdentifier globalIdentifier = qualifiedIdentifier();
0072     globalIdentifier.setExplicitlyGlobal(true);
0073 
0074     //We've got to use DUContext::DirectQualifiedLookup so C++ works correctly.
0075     const QList<Declaration*> declarations = topContext->findDeclarations(globalIdentifier,
0076                                                                           CursorInRevision::invalid(),
0077                                                                           AbstractType::Ptr(), nullptr,
0078                                                                           DUContext::DirectQualifiedLookup);
0079 
0080     for (Declaration* decl : declarations) {
0081         if (!decl->isForwardDeclaration())
0082             return decl;
0083     }
0084 
0085     return nullptr;
0086 }
0087 
0088 DUContext* ForwardDeclaration::logicalInternalContext(const TopDUContext* topContext) const
0089 {
0090     ENSURE_CAN_READ
0091     Declaration* resolved = resolve(topContext);
0092     if (resolved && resolved != this)
0093         return resolved->logicalInternalContext(topContext);
0094     else
0095         return Declaration::logicalInternalContext(topContext);
0096 }
0097 
0098 bool ForwardDeclaration::isForwardDeclaration() const
0099 {
0100     return true;
0101 }
0102 
0103 Declaration* ForwardDeclaration::clonePrivate() const
0104 {
0105     return new ForwardDeclaration(*this);
0106 }
0107 }