2 #ifndef _FUNCTION_NODE_CPP_
3 #define _FUNCTION_NODE_CPP_
5 #ifndef _MADARA_NO_KARL_
20 #ifdef _MADARA_PYTHON_CALLBACKS_
22 #include <boost/python/call.hpp>
29 #include "madara_jni.h"
42 function_(context.retrieve_function(name))
71 if (nodes_.size() > 0)
72 compiled_args_.
resize(nodes_.size());
74 for (ComponentNodes::size_type i = 0; i < nodes_.size(); ++i)
76 bool arg_can_change =
false;
77 result = nodes_[i]->prune(arg_can_change);
79 if (!arg_can_change &&
dynamic_cast<LeafNode*
>(nodes_[i]) == 0)
82 nodes_[i] =
new LeafNode(*(this->logger_), result);
87 std::stringstream buffer;
90 compiled_args_[i] =
context_.get_record(buffer.str());
106 args.
resize(nodes_.size());
110 for (ComponentNodes::iterator i = nodes_.begin(); i != nodes_.end(); ++i, ++j)
112 args[j] = (*i)->evaluate(settings);
113 *(compiled_args_[j]) = args[j];
120 "Function %s is being called with %d args.\n", this->name_.c_str(),
124 if (function_->is_extern_named())
125 result = function_->extern_named(name_.c_str(), args, variables);
128 else if (function_->is_extern_unnamed())
129 result = function_->extern_unnamed(args, variables);
132 else if (function_->is_java_callable())
135 JNIEnv* env = jvm.
env;
142 madara::utility::java::find_class(env,
"ai/madara/knowledge/Variables");
143 jclass jlistClass = madara::utility::java::find_class(
144 env,
"ai/madara/knowledge/KnowledgeList");
146 jmethodID fromPointerCall = env->GetStaticMethodID(
147 jvarClass,
"fromPointer",
"(J)Lai/madara/knowledge/Variables;");
148 jobject jvariables = env->CallStaticObjectMethod(
149 jvarClass, fromPointerCall, (jlong)&variables);
152 jmethodID listConstructor = env->GetMethodID(jlistClass,
"<init>",
"([J)V");
154 jlongArray ret = env->NewLongArray((jsize)args.size());
155 jlong* tmp =
new jlong[(jsize)args.size()];
157 for (
unsigned int x = 0; x < args.size(); x++)
159 tmp[x] = (jlong)args[x].clone();
162 env->SetLongArrayRegion(ret, 0, (jsize)args.size(), tmp);
166 jobject jlist = env->NewObject(jlistClass, listConstructor, ret);
169 jclass filterClass = env->GetObjectClass(function_->java_object);
172 jmethodID filterMethod = env->GetMethodID(filterClass,
"filter",
173 "(Lai/madara/knowledge/KnowledgeList;"
174 "Lai/madara/knowledge/Variables;)Lai/madara/knowledge/"
178 jobject jresult = env->CallObjectMethod(
179 function_->java_object, filterMethod, jlist, jvariables);
181 jmethodID getPtrMethod =
182 env->GetMethodID(env->GetObjectClass(jresult),
"getCPtr",
"()J");
183 jlong cptr = env->CallLongMethod(jresult, getPtrMethod);
187 jvm.
env->DeleteLocalRef(jresult);
188 jvm.
env->DeleteLocalRef(filterClass);
189 jvm.
env->DeleteLocalRef(jlist);
190 jvm.
env->DeleteLocalRef(ret);
191 jvm.
env->DeleteLocalRef(jvariables);
192 jvm.
env->DeleteWeakGlobalRef(jlistClass);
193 jvm.
env->DeleteWeakGlobalRef(jvarClass);
197 #ifdef _MADARA_PYTHON_CALLBACKS_
198 else if (function_->is_python_callable())
199 return boost::python::call<madara::knowledge::KnowledgeRecord>(
200 function_->python_function.ptr(), boost::ref(args),
201 boost::ref(variables));
204 else if (function_->is_uninitialized())
207 "CompositeFunctionNode:"
208 "KARL RUNTIME EXCEPTION: "
209 "Attempt at calling an undefined function\n");
212 "KARL RUNTIME EXCEPTION: "
213 "Attempt at calling an undefined function");
218 result = function_->function_contents.evaluate();
227 visitor.
visit(*
this);
#define madara_logger_ptr_log(loggering, level,...)
Fast version of the madara::logger::log method for Logger pointers.
const ThreadSafeContext * context_
An exception for unrecoverable KaRL compilation issues.
virtual madara::knowledge::KnowledgeRecord evaluate(const madara::knowledge::KnowledgeUpdateSettings &settings)
Evaluates the expression tree.
virtual madara::knowledge::KnowledgeRecord prune(bool &can_change)
Prunes the expression tree of unnecessary nodes.
virtual void accept(Visitor &visitor) const
Accepts a visitor subclassed from the Visitor class.
virtual madara::knowledge::KnowledgeRecord item(void) const
Returns the printable character of the node.
virtual ~CompositeFunctionNode(void)
Destructor.
CompositeFunctionNode(const std::string &name, madara::knowledge::ThreadSafeContext &context, const ComponentNodes &nodes)
Constructor.
Defines a node that contains a madara::knowledge::KnowledgeRecord::Integer value.
Abstract base class for all visitors to all classes that derive from ComponentNode.
virtual void visit(const LeafNode &node)=0
Visit a LeafNode.
This class encapsulates an entry in a KnowledgeBase.
void set_value(const KnowledgeRecord &new_value)
Sets the value from another KnowledgeRecord, does not copy toi, clock, and write_quality.
void deep_copy(const KnowledgeRecord &source)
Creates a deep copy of the knowledge record.
void resize(size_t new_size)
resizes an array to a new size
Settings for applying knowledge updates.
This class stores variables and their values for use by any entity needing state information in a thr...
Provides an interface for external functions into the MADARA KaRL variable settings.
ThreadSafeContext * context_
Variables context that is directly used by the KaRL engine.
This class encapsulates attaching and detaching to a VM.
JNIEnv * env
The Java environment.
std::deque< ComponentNode * > ComponentNodes
a vector of Component Nodes
std::vector< KnowledgeRecord > FunctionArguments