Qore Programming Language  0.9.3
CallReferenceNode.h
1 /* -*- mode: c++; indent-tabs-mode: nil -*- */
2 /*
3  CallReferenceNode.h
4 
5  Qore Programming Language
6 
7  Copyright (C) 2003 - 2018 Qore Technologies, s.r.o.
8 
9  Permission is hereby granted, free of charge, to any person obtaining a
10  copy of this software and associated documentation files (the "Software"),
11  to deal in the Software without restriction, including without limitation
12  the rights to use, copy, modify, merge, publish, distribute, sublicense,
13  and/or sell copies of the Software, and to permit persons to whom the
14  Software is furnished to do so, subject to the following conditions:
15 
16  The above copyright notice and this permission notice shall be included in
17  all copies or substantial portions of the Software.
18 
19  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22  AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
24  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
25  DEALINGS IN THE SOFTWARE.
26 
27  Note that the Qore library is released under a choice of three open-source
28  licenses: MIT (as above), LGPL 2+, or GPL 2+; see README-LICENSE for more
29  information.
30 */
31 
32 #ifndef _QORE_INTERN_FUNCTIONREFERENCENODE_H
33 
34 #define _QORE_INTERN_FUNCTIONREFERENCENODE_H
35 
36 #include <string>
37 
39 
40 hashdecl CallReferenceNodeLocation {
41  const QoreProgramLocation* loc;
42 
43  DLLLOCAL CallReferenceNodeLocation(const QoreProgramLocation* loc) : loc(loc) {
44  }
45 };
46 
47 class AbstractCallReferenceNodeIntern : public AbstractCallReferenceNode, public CallReferenceNodeLocation {
48 public:
49  DLLLOCAL AbstractCallReferenceNodeIntern(const QoreProgramLocation* loc, bool n_needs_eval) :
50  AbstractCallReferenceNode(n_needs_eval), CallReferenceNodeLocation(loc) {
51  }
52 };
53 
54 class ResolvedCallReferenceNodeIntern : public ResolvedCallReferenceNode, public CallReferenceNodeLocation {
55 public:
56  DLLLOCAL ResolvedCallReferenceNodeIntern(const QoreProgramLocation* loc, bool n_needs_eval = false) :
57  ResolvedCallReferenceNode(n_needs_eval), CallReferenceNodeLocation(loc) {
58  }
59 };
60 
61 class AbstractUnresolvedCallReferenceNode : public AbstractCallReferenceNodeIntern {
62 public:
63  DLLLOCAL AbstractUnresolvedCallReferenceNode(const QoreProgramLocation* loc, bool n_needs_eval) : AbstractCallReferenceNodeIntern(loc, n_needs_eval) {
64  }
65 };
66 
68 class UnresolvedProgramCallReferenceNode : public AbstractUnresolvedCallReferenceNode {
69 public:
70  char* str;
71 
72  DLLLOCAL UnresolvedProgramCallReferenceNode(const QoreProgramLocation* loc, char* n_str);
73 
74  DLLLOCAL virtual ~UnresolvedProgramCallReferenceNode();
75 
76  DLLLOCAL virtual void parseInit(QoreValue& val, LocalVar* oflag, int pflag, int& lvids, const QoreTypeInfo*& typeInfo);
77 };
78 
79 class UnresolvedCallReferenceNode : public UnresolvedProgramCallReferenceNode {
80 public:
81  DLLLOCAL UnresolvedCallReferenceNode(const QoreProgramLocation* loc, char* n_str) : UnresolvedProgramCallReferenceNode(loc, n_str) {
82  }
83 
84  DLLLOCAL virtual void parseInit(QoreValue& val, LocalVar* oflag, int pflag, int& lvids, const QoreTypeInfo*& typeInfo);
85 };
86 
88 class LocalStaticMethodCallReferenceNode : public ResolvedCallReferenceNodeIntern {
89 protected:
90  const QoreMethod* method;
91 
92  // constructor for subclasses
93  DLLLOCAL LocalStaticMethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod* n_method, bool n_needs_eval) : ResolvedCallReferenceNodeIntern(loc, n_needs_eval), method(n_method) {
94  }
95 
96  DLLLOCAL virtual QoreValue evalImpl(bool &needs_deref, ExceptionSink* xsink) const;
97 
98 public:
99  DLLLOCAL LocalStaticMethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod* n_method) : ResolvedCallReferenceNodeIntern(loc, true), method(n_method) {
100  //printd(5, "LocalStaticMethodCallReferenceNode::LocalStaticMethodCallReferenceNode() this: %p %s::%s() pgm: %p\n", this, method->getClass()->getName(), method->getName(), pgm);
101  }
102 
103  DLLLOCAL virtual ~LocalStaticMethodCallReferenceNode() {
104  }
105 
106  DLLLOCAL virtual bool is_equal_soft(const AbstractQoreNode* v, ExceptionSink* xsink) const {
108  }
109 
110  DLLLOCAL virtual bool is_equal_hard(const AbstractQoreNode* v, ExceptionSink* xsink) const;
111 
112  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
113 
114  DLLLOCAL virtual QoreFunction* getFunction();
115 };
116 
117 class StaticMethodCallReferenceNode : public LocalStaticMethodCallReferenceNode {
118 protected:
119  QoreProgram* pgm;
120  const qore_class_private* class_ctx;
121 
122  DLLLOCAL virtual bool derefImpl(ExceptionSink* xsink);
123 
124 public:
125  DLLLOCAL StaticMethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod *n_method, QoreProgram *n_pgm, const qore_class_private* n_class_ctx);
126 
127  DLLLOCAL ~StaticMethodCallReferenceNode() {
128  assert(!pgm);
129  }
130 
131  DLLLOCAL virtual QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const;
132 };
133 
136 protected:
137  DLLLOCAL virtual QoreValue evalImpl(bool &needs_deref, ExceptionSink* xsink) const;
138 
139  DLLLOCAL LocalMethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod* n_method, bool n_needs_eval) : LocalStaticMethodCallReferenceNode(loc, n_method, n_needs_eval) {
140  //printd(5, "LocalMethodCallReferenceNode::LocalStaticMethodCallReferenceNode() this: %p %s::%s() pgm: %p\n", this, method->getClass()->getName(), method->getName(), pgm);
141  }
142 
143 public:
144  DLLLOCAL LocalMethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod* n_method) : LocalStaticMethodCallReferenceNode(loc, n_method) {
145  //printd(5, "LocalMethodCallReferenceNode::LocalStaticMethodCallReferenceNode() this: %p %s::%s() pgm: %p\n", this, method->getClass()->getName(), method->getName(), pgm);
146  }
147 
148  DLLLOCAL virtual ~LocalMethodCallReferenceNode() {
149  }
150 
151  DLLLOCAL virtual bool is_equal_soft(const AbstractQoreNode* v, ExceptionSink* xsink) const {
153  }
154 
155  DLLLOCAL virtual bool is_equal_hard(const AbstractQoreNode* v, ExceptionSink* xsink) const;
156 
157  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
158 };
159 
160 class MethodCallReferenceNode : public LocalMethodCallReferenceNode {
161 protected:
162  QoreObject* obj;
163 
164  DLLLOCAL virtual bool derefImpl(ExceptionSink* xsink);
165 
166 public:
167  DLLLOCAL MethodCallReferenceNode(const QoreProgramLocation* loc, const QoreMethod* n_method, QoreProgram* n_pgm);
168 
169  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
170 };
171 
173 class LocalFunctionCallReferenceNode : public ResolvedCallReferenceNodeIntern {
174 public:
175  DLLLOCAL LocalFunctionCallReferenceNode(const QoreProgramLocation* loc, const QoreFunction* n_uf);
176 
177  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
178 
179  DLLLOCAL virtual bool is_equal_soft(const AbstractQoreNode* v, ExceptionSink* xsink) const {
181  }
182 
183  DLLLOCAL virtual bool is_equal_hard(const AbstractQoreNode* v, ExceptionSink* xsink) const;
184 
185  DLLLOCAL virtual QoreFunction* getFunction() {
186  return const_cast<QoreFunction*>(uf);
187  }
188 
189 protected:
190  const QoreFunction* uf;
191 
192  // constructor for subclasses
193  DLLLOCAL LocalFunctionCallReferenceNode(const QoreProgramLocation* loc, const QoreFunction* n_uf, bool n_needs_eval);
194 
195  DLLLOCAL virtual QoreValue evalImpl(bool &needs_deref, ExceptionSink* xsink) const;
196 };
197 
200 protected:
201  QoreProgram* pgm;
202 
203  DLLLOCAL virtual bool derefImpl(ExceptionSink* xsink);
204 
205 public:
206  DLLLOCAL FunctionCallReferenceNode(const QoreProgramLocation* loc, const QoreFunction* n_uf, QoreProgram* n_pgm) : LocalFunctionCallReferenceNode(loc, n_uf, false), pgm(n_pgm) {
207  assert(pgm);
208  // make a weak reference to the Program - a strong reference (QoreProgram::ref()) could cause a recursive reference
209  pgm->depRef();
210  }
211 
212  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
213 };
214 
216 class UnresolvedStaticMethodCallReferenceNode : public AbstractUnresolvedCallReferenceNode {
217 protected:
218  NamedScope* scope;
219 
220 public:
221  DLLLOCAL UnresolvedStaticMethodCallReferenceNode(const QoreProgramLocation* loc, NamedScope* n_scope);
222 
223  DLLLOCAL virtual ~UnresolvedStaticMethodCallReferenceNode();
224 
226  DLLLOCAL void deref() {
227  if (ROdereference())
228  delete this;
229  }
230 
231  DLLLOCAL virtual void parseInit(QoreValue& val, LocalVar* oflag, int pflag, int& lvids, const QoreTypeInfo*& typeInfo);
232 };
233 
234 class ImportedFunctionEntry;
235 
237 class RunTimeObjectMethodReferenceNode : public ResolvedCallReferenceNodeIntern {
238 private:
239  QoreObject* obj;
240  std::string method;
241  const qore_class_private* qc;
242 
243  DLLLOCAL virtual ~RunTimeObjectMethodReferenceNode();
244 
245 public:
246  DLLLOCAL RunTimeObjectMethodReferenceNode(const QoreProgramLocation* loc, QoreObject* n_obj, const char* n_method);
247 
248  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
249 
250  DLLLOCAL virtual QoreProgram* getProgram() const;
251 
252  DLLLOCAL virtual bool is_equal_soft(const AbstractQoreNode* v, ExceptionSink* xsink) const {
254  }
255 
256  DLLLOCAL virtual bool is_equal_hard(const AbstractQoreNode* v, ExceptionSink* xsink) const;
257 
258  DLLLOCAL virtual QoreFunction* getFunction() {
259  // FIXME: implement type checking and method matching in ParseObjectMethodReferenceNode::parseInit()
260  return 0;
261  }
262 };
263 
265 // is known when the method reference node object is created
266 class RunTimeResolvedMethodReferenceNode : public ResolvedCallReferenceNodeIntern {
267 private:
268  QoreObject* obj;
269  const QoreMethod* method;
270  const qore_class_private* qc;
271 
272  DLLLOCAL virtual ~RunTimeResolvedMethodReferenceNode();
273 
274 public:
275  DLLLOCAL RunTimeResolvedMethodReferenceNode(const QoreProgramLocation* loc, QoreObject* n_obj, const QoreMethod* n_method);
276 
277  DLLLOCAL virtual QoreValue execValue(const QoreListNode* args, ExceptionSink* xsink) const;
278 
279  DLLLOCAL virtual QoreProgram* getProgram() const;
280 
281  DLLLOCAL virtual bool is_equal_soft(const AbstractQoreNode* v, ExceptionSink* xsink) const {
283  }
284 
285  DLLLOCAL virtual bool is_equal_hard(const AbstractQoreNode* v, ExceptionSink* xsink) const;
286 
287  DLLLOCAL virtual QoreFunction* getFunction();
288 };
289 
290 #endif
a run-time call reference to a method of a particular object
Definition: CallReferenceNode.h:237
virtual DLLLOCAL bool is_equal_soft(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
Definition: CallReferenceNode.h:281
DLLEXPORT void depRef()
incremements the weak reference count for the program object
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
virtual DLLLOCAL QoreFunction * getFunction()
Returns the internal function object, if any; can return nullptr.
virtual DLLLOCAL QoreFunction * getFunction()
Returns the internal function object, if any; can return nullptr.
virtual DLLLOCAL QoreValue evalImpl(bool &needs_deref, ExceptionSink *xsink) const
this function should never be called for function references; this function should never be called di...
a call reference to a static user method
Definition: CallReferenceNode.h:135
virtual DLLLOCAL bool is_equal_hard(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
virtual DLLLOCAL bool is_equal_soft(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
Definition: CallReferenceNode.h:252
The base class for all value and parse types in Qore expression trees.
Definition: AbstractQoreNode.h:54
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
virtual DLLLOCAL QoreValue evalImpl(bool &needs_deref, ExceptionSink *xsink) const
this function should never be called for function references; this function should never be called di...
virtual DLLEXPORT bool derefImpl(ExceptionSink *xsink)
decrements the reference count
virtual DLLLOCAL bool is_equal_soft(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
Definition: CallReferenceNode.h:151
virtual DLLLOCAL bool is_equal_hard(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
virtual DLLLOCAL QoreProgram * getProgram() const
returns a pointer to the QoreProgram object associated with this reference (can be nullptr)
virtual DLLLOCAL QoreFunction * getFunction()
Returns the internal function object, if any; can return nullptr.
Definition: CallReferenceNode.h:258
base class for call references, reference-counted, dynamically allocated only
Definition: CallReferenceNode.h:39
DLLEXPORT bool ROdereference() const
atomically decrements the reference count
virtual DLLLOCAL bool derefImpl(ExceptionSink *xsink)
decrements the reference count
virtual DLLLOCAL bool is_equal_soft(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
Definition: CallReferenceNode.h:179
a run-time call reference to a method of a particular object where the method's class
Definition: CallReferenceNode.h:266
This is the list container type in Qore, dynamically allocated only, reference counted.
Definition: QoreListNode.h:52
a call reference to a user function from within the same QoreProgram object
Definition: CallReferenceNode.h:173
virtual DLLLOCAL bool is_equal_hard(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
virtual DLLLOCAL bool is_equal_hard(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
virtual DLLLOCAL QoreFunction * getFunction()
Returns the internal function object, if any; can return nullptr.
Definition: CallReferenceNode.h:185
The main value class in Qore, designed to be passed by value.
Definition: QoreValue.h:262
supports parsing and executing Qore-language code, reference counted, dynamically-allocated only
Definition: QoreProgram.h:126
the implementation of Qore's object data type, reference counted, dynamically-allocated only
Definition: QoreObject.h:61
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
container for holding Qore-language exception information and also for registering a "thread_exit" ca...
Definition: ExceptionSink.h:46
virtual DLLLOCAL bool is_equal_hard(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
DLLEXPORT void deref(ExceptionSink *xsink)
decrements the reference count and calls derefImpl() if there_can_be_only_one is false,...
an unresolved call reference, only present temporarily in the parse tree
Definition: CallReferenceNode.h:68
an unresolved static method call reference, only present temporarily in the parse tree
Definition: CallReferenceNode.h:216
a call reference to a static user method
Definition: CallReferenceNode.h:88
base class for resolved call references
Definition: CallReferenceNode.h:105
virtual DLLLOCAL QoreProgram * getProgram() const
returns a pointer to the QoreProgram object associated with this reference (can be nullptr)
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
virtual DLLLOCAL void parseInit(QoreValue &val, LocalVar *oflag, int pflag, int &lvids, const QoreTypeInfo *&typeInfo)
for use by parse types to initialize them for execution during stage 1 parsing; not exported in the l...
virtual DLLLOCAL bool is_equal_soft(const AbstractQoreNode *v, ExceptionSink *xsink) const
returns true if the other node is the same value
Definition: CallReferenceNode.h:106
a method in a QoreClass
Definition: QoreClass.h:123
virtual DLLLOCAL QoreValue execValue(const QoreListNode *args, ExceptionSink *xsink) const
pure virtual function for executing the function reference
virtual DLLLOCAL QoreValue evalImpl(bool &needs_deref, ExceptionSink *xsink) const
this function should never be called for function references; this function should never be called di...
a call reference to a user function
Definition: CallReferenceNode.h:199
virtual DLLLOCAL void parseInit(QoreValue &val, LocalVar *oflag, int pflag, int &lvids, const QoreTypeInfo *&typeInfo)
for use by parse types to initialize them for execution during stage 1 parsing; not exported in the l...