File indexing completed on 2024-05-19 04:39:14
0001 /* 0002 SPDX-FileCopyrightText: 2008 David Nolden <david.nolden.kdevelop@art-master.de> 0003 0004 SPDX-License-Identifier: LGPL-2.0-only 0005 */ 0006 0007 #include "functiondefinition.h" 0008 #include "duchainregister.h" 0009 #include "definitions.h" 0010 0011 namespace KDevelop { 0012 REGISTER_DUCHAIN_ITEM(FunctionDefinition); 0013 0014 FunctionDefinition::FunctionDefinition(FunctionDefinitionData& data) : FunctionDeclaration(data) 0015 { 0016 } 0017 0018 FunctionDefinition::FunctionDefinition(const RangeInRevision& range, DUContext* context) 0019 : FunctionDeclaration(*new FunctionDefinitionData, range) 0020 { 0021 d_func_dynamic()->setClassId(this); 0022 setDeclarationIsDefinition(true); 0023 if (context) 0024 setContext(context); 0025 } 0026 0027 FunctionDefinition::FunctionDefinition(const FunctionDefinition& rhs) : FunctionDeclaration(*new FunctionDefinitionData( 0028 *rhs.d_func())) 0029 { 0030 } 0031 0032 FunctionDefinition::~FunctionDefinition() 0033 { 0034 if (!topContext()->isOnDisk()) 0035 DUChain::definitions()->removeDefinition(d_func()->m_declaration, this); 0036 } 0037 0038 Declaration* FunctionDefinition::declaration(const TopDUContext* topContext) const 0039 { 0040 ENSURE_CAN_READ 0041 0042 const KDevVarLengthArray<Declaration*> declarations = d_func()->m_declaration.declarations( 0043 topContext ? topContext : this->topContext()); 0044 0045 for (Declaration* decl : declarations) { 0046 if (!dynamic_cast<FunctionDefinition*>(decl)) 0047 return decl; 0048 } 0049 0050 return nullptr; 0051 } 0052 0053 bool FunctionDefinition::hasDeclaration() const 0054 { 0055 return d_func()->m_declaration.isValid(); 0056 } 0057 0058 void FunctionDefinition::setDeclaration(Declaration* declaration) 0059 { 0060 ENSURE_CAN_WRITE 0061 0062 if (declaration) { 0063 DUChain::definitions()->addDefinition(declaration->id(), this); 0064 d_func_dynamic()->m_declaration = declaration->id(); 0065 } else { 0066 if (d_func()->m_declaration.isValid()) { 0067 DUChain::definitions()->removeDefinition(d_func()->m_declaration, this); 0068 d_func_dynamic()->m_declaration = DeclarationId(); 0069 } 0070 } 0071 } 0072 0073 Declaration* FunctionDefinition::definition(const Declaration* decl) 0074 { 0075 ENSURE_CHAIN_READ_LOCKED 0076 if (!decl) { 0077 return nullptr; 0078 } 0079 0080 if (decl->isFunctionDeclaration() && decl->isDefinition()) { 0081 return const_cast<Declaration*>(decl); 0082 } 0083 0084 const KDevVarLengthArray<IndexedDeclaration> allDefinitions = DUChain::definitions()->definitions(decl->id()); 0085 for (const IndexedDeclaration decl : allDefinitions) { 0086 if (decl.data()) ///@todo Find better ways of deciding which definition to use 0087 return decl.data(); 0088 } 0089 0090 return nullptr; 0091 } 0092 0093 Declaration* FunctionDefinition::clonePrivate() const 0094 { 0095 return new FunctionDefinition(*new FunctionDefinitionData(*d_func())); 0096 } 0097 }