const QoreMethod* pseudo_classes_find_method(qore_type_t t, const char *mname, QoreClass* &qc) { QoreClass* nqc = pseudo_get_class(t); const QoreMethod* m = nqc->findMethod(mname); if (m) qc = nqc; return m; }
//----------------------------------------------------------------------------- QoreClass* initBuiltinInheritanceTestBaseClass() { QoreClass* tst = new QoreClass("BuiltinInheritanceTestBase", QDOM_PROCESS); CID_BUILTININHERITANCETESTBASE = tst->getID(); tst->setConstructor((q_constructor_t)BUILTININHERITANCETESTBASE_constructor); tst->setDestructor((q_destructor_t)BUILTININHERITANCETESTBASE_destructor); tst->addMethod("getnum", (q_method_t)BUILTININHERITANCETESTBASE_getnum); return tst; }
//----------------------------------------------------------------------------- // override getnum() QoreClass* initBuiltinInheritanceTestDescendant4(QoreClass* base) { QoreClass* tst = new QoreClass("BuiltinInheritanceTestDescendant4", QDOM_PROCESS); CID_BUILTININHERITANCETESTDESCENDANT4 = tst->getID(); tst->addDefaultBuiltinBaseClass(base); tst->addMethod("getnum", (q_method_t)BUILTININHERITANCETESTDESCENDANT4_getnum); return tst; }
void QoreProgram::runClass(const char* classname, ExceptionSink* xsink) { // find class QoreClass* qc = qore_root_ns_private::runtimeFindClass(*priv->RootNS, classname); if (!qc) { xsink->raiseException("CLASS-NOT-FOUND", "cannot find any class '%s' in any namespace", classname); return; } //printd(5, "QoreProgram::runClass(%s)\n", classname); ProgramThreadCountContextHelper tch(xsink, this, true); if (!*xsink) discard(qc->execConstructor(0, xsink), xsink); }
//----------------------------------------------------------------------------- QoreClass* initBuiltinInheritanceTestDescendantMulti(QoreClass* base, QoreClass* base2) { QoreClass* tst = new QoreClass("BuiltinInheritanceTestDescendantMulti", QDOM_PROCESS); CID_BUILTININHERITANCETESTDESCENDANT_MULTI = tst->getID(); // we have a method (getnum) below, but no constructor to set our own private data, // therefore we have to call addDefaultBuiltinBaseClass() on one of the base classes // to have some private data... //tst->addBuiltinBaseClass(base); tst->addBuiltinBaseClass(base2); // OTOH simple inheritance works tst->addDefaultBuiltinBaseClass(base); tst->addMethod("getnum", (q_method_t)BUILTININHERITANCETESTDESCENDANT_MULTI_getnum); return tst; }
AbstractQoreNode* UnresolvedStaticMethodCallReferenceNode::parseInit(LocalVar* oflag, int pflag, int& lvids, const QoreTypeInfo*& typeInfo) { typeInfo = callReferenceTypeInfo; QoreClass* qc = qore_root_ns_private::parseFindScopedClassWithMethod(*scope, false); if (!qc) { // see if this is a function call to a function defined in a namespace const QoreFunction* f = qore_root_ns_private::parseResolveFunction(*scope); if (f) { LocalFunctionCallReferenceNode* fr = new LocalFunctionCallReferenceNode(f); deref(); return fr->parseInit(oflag, pflag, lvids, typeInfo); } parse_error("reference to undefined class '%s' in '%s()'", scope->get(scope->size() - 2), scope->ostr); return this; } const QoreMethod* qm = 0; // try to find a pointer to a non-static method if parsing in the class' context // and bare references are enabled if (oflag && parse_check_parse_option(PO_ALLOW_BARE_REFS) && oflag->getTypeInfo()->getUniqueReturnClass()->parseCheckHierarchy(qc)) { bool m_priv = false; qm = qore_class_private::parseFindMethodTree(*qc, scope->getIdentifier(), m_priv); assert(!qm || !qm->isStatic()); } if (!qm) { bool m_priv = false; qm = qore_class_private::parseFindStaticMethodTree(*qc, scope->getIdentifier(), m_priv); if (!qm) { parseException("INVALID-METHOD", "class '%s' has no static method '%s'", qc->getName(), scope->getIdentifier()); return this; } assert(qm->isStatic()); } // check class capabilities against parse options if (qore_program_private::parseAddDomain(getProgram(), qc->getDomain())) { parseException("class '%s' implements capabilities that are not allowed by current parse options", qc->getName()); return this; } AbstractQoreNode* rv = qm->isStatic() ? new LocalStaticMethodCallReferenceNode(qm) : new LocalMethodCallReferenceNode(qm); deref(); return rv; }
void QoreSmokeBinding::deleted(Smoke::Index classId, void *obj) { assert(obj); QoreClass *qc; QoreObject *o = getQoreObject(classId, obj, qc); //printd(5, "QoreSmokeBinding::deleted() %s::~%s qobject=%p qore obj=%p\n", className(classId), className(classId), obj, o); if (o) { ExceptionSink xsink; // mark private data as cleared PrivateDataRefHolder<QoreSmokePrivate> qsd(o, qc->getID(), &xsink); // printd(0, "QoreSmokeBinding::deleted() external delete Qore class %s (Qt class %s) (qsd=%p)\n", o->getClassName(), className(classId), *qsd); if (qsd) qsd->externalDelete(o, &xsink); else // mark qore object as externally deleted o->externalDelete(qc->getID(), &xsink); } }
//----------------------------------------------------------------------------- // override constructor, destructor, getnum() QoreClass* initBuiltinInheritanceTestDescendant2(QoreClass* base) { QoreClass* tst = new QoreClass("BuiltinInheritanceTestDescendant2", QDOM_PROCESS); CID_BUILTININHERITANCETESTDESCENDANT2 = tst->getID(); tst->addDefaultBuiltinBaseClass(base); tst->setConstructor((q_constructor_t)BUILTININHERITANCETESTDESCENDANT2_constructor); tst->setDestructor((q_destructor_t)BUILTININHERITANCETESTDESCENDANT2_destructor); tst->addMethod("getnum", (q_method_t)BUILTININHERITANCETESTDESCENDANT2_getnum); return tst; }
// create pseudo-class for type static QoreClass* do_type_code(const char *name, q_method_int64_t f) { QoreClass* qc = new QoreClass(name); qc->addBuiltinVirtualBaseClass(QC_PSEUDOVALUE); qc->addMethodExtended3("typeCode", f, false, QC_CONSTANT, QDOM_DEFAULT, bigIntTypeInfo); return qc; }
AbstractQoreNode *QoreDotEvalOperatorNode::parseInitImpl(LocalVar *oflag, int pflag, int &lvids, const QoreTypeInfo *&returnTypeInfo) { assert(!returnTypeInfo); const QoreTypeInfo* typeInfo = 0; left = left->parseInit(oflag, pflag, lvids, typeInfo); QoreClass* qc = const_cast<QoreClass*>(typeInfo->getUniqueReturnClass()); const QoreMethod* meth = 0; const char* mname = m->getName(); if (!qc) { // if the left side has a type and it's not an object, then we try to match pseudo-methods if (typeInfo->hasType() && !objectTypeInfo->parseAccepts(typeInfo)) { // check for pseudo-methods bool possible_match; meth = pseudo_classes_find_method(typeInfo, mname, qc, possible_match); if (meth) { m->setPseudo(); // save method for optimizing calls later m->parseSetClassAndMethod(qc, meth); // check parameters, if any lvids += m->parseArgs(oflag, pflag, meth->getFunction(), returnTypeInfo); return this; } else if (!possible_match && !hashTypeInfo->parseAccepts(typeInfo)) { // issue an error if there was no match and it's not a hash QoreStringNode* edesc = new QoreStringNode; edesc->sprintf("no pseudo-method <%s>.%s() can be found", typeInfo->getName(), mname); qore_program_private::makeParseException(getProgram(), loc, "PARSE-TYPE-ERROR", edesc); } } #ifdef DEBUG typeInfo = 0; AbstractQoreNode* n = m->parseInit(oflag, pflag, lvids, typeInfo); assert(n == m); #else m->parseInit(oflag, pflag, lvids, typeInfo); #endif return this; } // make sure method arguments and return types are resolved qore_class_private::parseInitPartial(*qc); if (!m) return this; bool m_priv = false; meth = qore_class_private::parseFindMethodTree(*qc, mname, m_priv); //printd(5, "QoreDotEvalOperatorNode::parseInitImpl() %s::%s() method: %p (%s) (private: %s)\n", qc->getName(), mname, meth, meth ? meth->getClassName() : "n/a", m_priv ? "true" : "false"); // FIXME const QoreListNode* args = m->getArgs(); if (!strcmp(mname, "copy")) { if (args && args->size()) parse_error(loc, "no arguments may be passed to copy methods (%d argument%s given in call to %s::copy())", args->size(), args->size() == 1 ? "" : "s", qc->getName()); if (meth && meth->parseIsPrivate() && (!oflag || !qore_class_private::parseCheckCompatibleClass(*qc, *(getParseClass())))) parse_error(loc, "illegal call to private %s::copy() method", qc->getName()); // do not save method pointer for copy methods returnTypeInfo = qc->getTypeInfo(); #ifdef DEBUG typeInfo = 0; AbstractQoreNode *n = m->parseInit(oflag, pflag, lvids, typeInfo); assert(n == m); #else m->parseInit(oflag, pflag, lvids, typeInfo); #endif return this; } // if a normal method is not found, then look for a static method if (!meth) meth = qore_class_private::parseFindStaticMethodTree(*qc, mname, m_priv); if (!meth) { if (!qc->parseHasMethodGate()) { // check if it could be a pseudo-method call meth = pseudo_classes_find_method(NT_OBJECT, mname, qc); if (meth) m->setPseudo(); else raiseNonExistentMethodCallWarning(qc, mname); } if (!meth) { #ifdef DEBUG typeInfo = 0; AbstractQoreNode *n = m->parseInit(oflag, pflag, lvids, typeInfo); assert(n == m); #else m->parseInit(oflag, pflag, lvids, typeInfo); #endif return this; } } if (m_priv && !qore_class_private::parseCheckPrivateClassAccess(*qc)) parse_error(loc, "illegal call to private method %s::%s()", qc->getName(), mname); else // save method for optimizing calls later m->parseSetClassAndMethod(qc, meth); // check parameters, if any lvids += m->parseArgs(oflag, pflag, meth->getFunction(), returnTypeInfo); printd(5, "QoreDotEvalOperatorNode::parseInitImpl() %s::%s() method=%p (%s::%s()) (private=%s, static=%s) rv=%s\n", qc->getName(), mname, meth, meth ? meth->getClassName() : "n/a", mname, meth && meth->parseIsPrivate() ? "true" : "false", meth->isStatic() ? "true" : "false", returnTypeInfo->getName()); return this; }