File indexing completed on 2024-04-14 04:31:13
0001 /* 0002 * This file is part of KDevelop 0003 * Copyright (C) 2012-2015 Miquel Sabaté Solà <mikisabate@gmail.com> 0004 * 0005 * This program is free software: you can redistribute it and/or modify 0006 * it under the terms of the GNU General Public License as published by 0007 * the Free Software Foundation, either version 3 of the License, or 0008 * (at your option) any later version. 0009 * 0010 * This program is distributed in the hope that it will be useful, 0011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 0012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 0013 * GNU General Public License for more details. 0014 * 0015 * You should have received a copy of the GNU General Public License 0016 * along with this program. If not, see <http://www.gnu.org/licenses/>. 0017 */ 0018 0019 #ifndef RUBY_EXPRESSION_VISITOR_H 0020 #define RUBY_EXPRESSION_VISITOR_H 0021 0022 #include <duchain/duchainexport.h> 0023 #include <duchain/helpers.h> 0024 #include <duchain/types/classtype.h> 0025 #include <parser/astvisitor.h> 0026 0027 namespace ruby { 0028 0029 class EditorIntegrator; 0030 0031 /** 0032 * @class ExpressionVisitor 0033 * 0034 * This class is used almost everywhere in the DUChain & Code Completion parts. 0035 * It's a visitor specialized in retrieving the types that can be extracted 0036 * for a particular AST. It also retrieves the last declaration that has been 0037 * found for a given expression. 0038 * 0039 * @note The DUChain should *never* be locked when calling a visit method of 0040 * this class. This class already takes care of locking issues. 0041 */ 0042 class KDEVRUBYDUCHAIN_EXPORT ExpressionVisitor : public AstVisitor 0043 { 0044 public: 0045 ExpressionVisitor(KDevelop::DUContext *ctx, EditorIntegrator *editor); 0046 explicit ExpressionVisitor(ExpressionVisitor *parent); 0047 0048 /// @returns the last type seen. 0049 inline KDevelop::AbstractType::Ptr lastType() const 0050 { 0051 return m_lastType; 0052 } 0053 0054 /// @returns true if the last expression was an alias, false otherwise. 0055 inline const bool & lastAlias() const 0056 { 0057 return m_alias; 0058 } 0059 0060 /// @returns the last declaration seen. 0061 inline const KDevelop::DeclarationPointer & lastDeclaration() const 0062 { 0063 return m_lastDeclaration; 0064 } 0065 0066 /// Set the internal context to @p ctx and reset all the other attributes. 0067 void setContext(KDevelop::DUContext *ctx); 0068 0069 /// Set whether the type for the last declaration. 0070 void setIsClassMethod(bool isClassMethod); 0071 0072 /// Set the declaration kind to @param kind. 0073 void setDeclarationKind(const DeclarationKind kind); 0074 0075 /// Re-implemented from AstVisitor. 0076 void visitParameter(Ast *node) override; 0077 0078 protected: 0079 /// Visitor methods re-implemented from AstVisitor. 0080 0081 bool declaredInContext(const QByteArray &name) const override; 0082 0083 void visitString(Ast *node) override; 0084 void visitRegexp(Ast *node) override; 0085 void visitNumeric(Ast *node) override; 0086 void visitTrue(Ast *node) override; 0087 void visitFalse(Ast *node) override; 0088 void visitNil(Ast *node) override; 0089 void visitLine(Ast *node) override; 0090 void visitFile(Ast *node) override; 0091 void visitEncoding(Ast *node) override; 0092 void visitSelf(Ast *node) override; 0093 void visitRange(Ast *node) override; 0094 void visitSymbol(Ast *node) override; 0095 void visitName(Ast *node) override; 0096 void visitArray(Ast *node) override; 0097 void visitHash(Ast *node) override; 0098 void visitArrayValue(Ast *node) override; 0099 void visitMethodCall(Ast *node) override; 0100 void visitSuper(Ast *node) override; 0101 void visitLambda(Ast *node) override; 0102 void visitWhileStatement(Ast *node) override; 0103 void visitForStatement(Ast *node) override; 0104 void visitBinary(Ast *node) override; 0105 void visitBoolean(Ast *node) override; 0106 void visitIfStatement(Ast *node) override; 0107 void visitCaseStatement(Ast *node) override; 0108 void visitMethodStatement(Ast *node) override; 0109 0110 private: 0111 /// Set the last type seen to @p type. 0112 inline void encounter(KDevelop::AbstractType::Ptr type) 0113 { 0114 m_lastType = type; 0115 } 0116 0117 /** 0118 * Get the ClassType that can be guessed from the given parameters. 0119 * @param ptr The container type. 0120 * @param node The container. Used to retrieve the contents type. 0121 * @param hasKey False by default. Set to true if the container has 0122 * key values (i.e. Hash). 0123 * @return the ClassType retrieved from the given parameters or nullptr. 0124 */ 0125 ClassType::Ptr getContainer(KDevelop::AbstractType::Ptr ptr, 0126 const Ast *node, 0127 bool hasKey = false); 0128 0129 /// Visit the last statement from @p node. Used for the implicit return. 0130 void visitLastStatement(Ast *node); 0131 0132 /// Visit the method call members from @p node. 0133 void visitMethodCallMembers(Ast *node); 0134 0135 private: 0136 /// The DUContext that the visitor will use to find declarations. 0137 KDevelop::DUContext *m_ctx; 0138 0139 /// The EditorIntegrator used to mess with the document. 0140 EditorIntegrator *m_editor; 0141 0142 /// The last found DUContext. Used by the method call visitor. 0143 KDevelop::DUContext *m_lastCtx; 0144 0145 /// The last AbstractType that has been found. 0146 KDevelop::AbstractType::Ptr m_lastType; 0147 0148 /// The last DeclarationPointer that has been found. 0149 KDevelop::DeclarationPointer m_lastDeclaration; 0150 0151 /// Tells us whether the last found declaration was an alias or not. 0152 bool m_alias; 0153 0154 /// The kind for the last declaration. 0155 DeclarationKind m_declarationKind; 0156 }; 0157 0158 } 0159 0160 #endif // RUBY_EXPRESSION_VISITOR_H