23 #include <blackboard/blackboard.h>
24 #include <config/config.h>
25 #include <interface/interface.h>
26 #include <logging/logger.h>
27 #include <lua/context.h>
28 #include <lua/interface_importer.h>
58 blackboard_ = blackboard;
64 interfaces_pushed_ =
false;
83 LuaInterfaceImporter::open_interfaces(std::string &prefix, InterfaceMap &imap,
bool write)
90 if (strcmp(vi->
type(),
"string") != 0) {
92 "but found value of type %s",
100 if (uid.find(
"::") == std::string::npos) {
102 throw Exception(
"Interface UID '%s' at %s is not valid, missing double colon",
106 std::string varname = std::string(vi->
path()).substr(prefix.length());
107 std::string iftype = uid.substr(0, uid.find(
"::"));
108 std::string ifname = uid.substr(uid.find(
"::") + 2);
110 if (reading_ifs_.find(varname) != reading_ifs_.end()) {
112 throw Exception(
"Reading interface with varname %s already opened", varname.c_str());
114 if (reading_multi_ifs_.find(varname) != reading_multi_ifs_.end()) {
116 throw Exception(
"Reading multi interface with varname %s already opened", varname.c_str());
118 if (writing_ifs_.find(varname) != writing_ifs_.end()) {
120 throw Exception(
"Writing interface with varname %s already opened", varname.c_str());
123 if (ifname.find_first_of(
"*?[") == std::string::npos) {
124 logger_->
log_info(
"LuaInterfaceImporter",
125 "Adding %s interface %s::%s with name %s",
126 write ?
"writing" :
"reading",
140 imap[varname] = iface;
141 }
catch (Exception &e) {
148 throw Exception(
"Illegal config entry %s=%s, multiple interfaces can "
149 "only be opened for reading",
153 logger_->
log_info(
"LuaInterfaceImporter",
154 "Adding multiple %s interfaces %s::%s with in table %s",
155 write ?
"writing" :
"reading",
160 std::list<Interface *> interfaces =
162 reading_multi_ifs_[varname] = interfaces;
163 InterfaceObserver *observer =
164 new InterfaceObserver(
this, varname, iftype.c_str(), ifname.c_str());
165 observers_[varname] = observer;
178 open_interfaces(prefix, reading_ifs_,
false);
187 open_interfaces(prefix, writing_ifs_,
true);
203 ext_wifs_[varname] = interface;
205 ext_rifs_[varname] = interface;
210 LuaInterfaceImporter::add_observed_interface(std::string varname,
const char *type,
const char *
id)
213 if (reading_multi_ifs_.find(varname) == reading_multi_ifs_.end()) {
214 throw Exception(
"Notified about unknown interface varname %s", varname.c_str());
217 context_->
add_package((std::string(
"interfaces.") + iface->type()).c_str());
218 reading_multi_ifs_[varname].push_back(iface);
221 context_->
get_field(-1, varname.c_str());
223 context_->
raw_seti(-2, reading_multi_ifs_[varname].size());
227 }
catch (Exception &e) {
228 logger_->
log_warn(
"LuaInterfaceImporter",
229 "Failed to add observed interface "
230 "%s:%s, exception follows",
233 logger_->
log_warn(
"LuaInterfaceImporter", e);
241 for (InterfaceMap::iterator i = reading_ifs_.begin(); i != reading_ifs_.end(); ++i) {
242 blackboard_->
close(i->second);
244 reading_ifs_.clear();
246 for (ObserverMap::iterator o = observers_.begin(); o != observers_.end(); ++o) {
252 for (InterfaceListMap::iterator i = reading_multi_ifs_.begin(); i != reading_multi_ifs_.end();
254 for (std::list<Interface *>::iterator j = i->second.begin(); j != i->second.end(); ++j) {
255 blackboard_->
close(*j);
258 reading_multi_ifs_.clear();
265 for (InterfaceMap::iterator i = writing_ifs_.begin(); i != writing_ifs_.end(); ++i) {
266 blackboard_->
close(i->second);
268 writing_ifs_.clear();
293 for (InterfaceMap::iterator i = reading_ifs_.begin(); i != reading_ifs_.end(); ++i) {
303 InterfaceMap::iterator i;
305 for (i = reading_ifs_.begin(); i != reading_ifs_.end(); ++i) {
306 i->second->resize_buffers(1);
310 for (i = reading_ifs_.begin(); i != reading_ifs_.end(); ++i) {
311 i->second->copy_shared_to_buffer(0);
323 throw Exception(
"LuaInterfaceImporter: trying to read buffer witout "
324 "previous read_to_buffer()");
326 InterfaceMap::iterator i;
327 for (i = reading_ifs_.begin(); i != reading_ifs_.end(); ++i) {
328 i->second->read_from_buffer(0);
336 for (InterfaceMap::iterator i = writing_ifs_.begin(); i != writing_ifs_.end(); ++i) {
340 e.
append(
"Failed to write interface %s, ignoring.", i->second->uid());
347 LuaInterfaceImporter::push_interfaces_varname(
LuaContext *context, InterfaceMap &imap)
349 InterfaceMap::iterator imi;
350 for (imi = imap.begin(); imi != imap.end(); ++imi) {
351 context->
add_package((std::string(
"interfaces.") + imi->second->type()).c_str());
352 context->
push_usertype(imi->second, imi->second->type(),
"fawkes");
358 LuaInterfaceImporter::push_multi_interfaces_varname(LuaContext *context, InterfaceListMap &imap)
360 InterfaceListMap::iterator imi;
361 for (imi = imap.begin(); imi != imap.end(); ++imi) {
362 context->create_table(0, imi->second.size());
364 for (std::list<Interface *>::iterator i = imi->second.begin(); i != imi->second.end(); ++i) {
365 context->add_package((std::string(
"interfaces.") + (*i)->type()).c_str());
366 context->push_usertype(*i, (*i)->type(),
"fawkes");
367 context->raw_seti(-2, ++idx);
368 context->push_usertype(*i, (*i)->type(),
"fawkes");
369 context->set_field((*i)->uid(), -2);
371 context->set_field(imi->first.c_str());
376 LuaInterfaceImporter::push_interfaces_uid(LuaContext *context, InterfaceMap &imap)
378 InterfaceMap::iterator imi;
379 for (imi = imap.begin(); imi != imap.end(); ++imi) {
380 context->add_package((std::string(
"interfaces.") + imi->second->type()).c_str());
381 context->push_usertype(imi->second, imi->second->type(),
"fawkes");
382 context->set_field(imi->second->uid());
390 context->create_table(0, 4);
392 context->create_table(0, reading_ifs_.size() + ext_rifs_.size());
393 push_interfaces_varname(context, reading_ifs_);
394 push_interfaces_varname(context, ext_rifs_);
395 push_multi_interfaces_varname(context, reading_multi_ifs_);
396 context->set_field(
"reading");
398 context->create_table(0, reading_ifs_.size() + ext_rifs_.size());
399 push_interfaces_uid(context, reading_ifs_);
400 push_interfaces_uid(context, ext_rifs_);
401 context->set_field(
"reading_by_uid");
403 context->create_table(0, writing_ifs_.size() + ext_wifs_.size());
404 push_interfaces_varname(context, writing_ifs_);
405 push_interfaces_varname(context, ext_wifs_);
406 context->set_field(
"writing");
408 context->create_table(0, writing_ifs_.size());
409 push_interfaces_uid(context, writing_ifs_);
410 push_interfaces_uid(context, ext_wifs_);
411 context->set_field(
"writing_by_uid");
413 context->set_global(
"interfaces");
424 interfaces_pushed_ =
true;
432 if (interfaces_pushed_) {
436 logger_->
log_warn(
"LuaInterfaceImporter",
"Failed to re-push interfacs, exception follows");
437 logger_->
log_warn(
"LuaInterfaceImporter", e);
451 const char * id_pattern)
456 bbio_add_observed_create(type, id_pattern);
460 LuaInterfaceImporter::InterfaceObserver::bb_interface_created(
const char *type,
461 const char *
id)
throw()
463 lii_->add_observed_interface(varname_, type,
id);
The BlackBoard abstract class.
virtual void unregister_observer(BlackBoardInterfaceObserver *observer)
Unregister BB interface observer.
virtual Interface * open_for_reading(const char *interface_type, const char *identifier, const char *owner=NULL)=0
Open interface for reading.
virtual void register_observer(BlackBoardInterfaceObserver *observer)
Register BB interface observer.
virtual Interface * open_for_writing(const char *interface_type, const char *identifier, const char *owner=NULL)=0
Open interface for writing.
virtual std::list< Interface * > open_multiple_for_reading(const char *type_pattern, const char *id_pattern="*", const char *owner=NULL)=0
Open multiple interfaces for reading.
virtual void close(Interface *interface)=0
Close interface.
Iterator interface to iterate over config values.
virtual const char * path() const =0
Path of value.
virtual bool next()=0
Check if there is another element and advance to this if possible.
virtual const char * type() const =0
Type of value.
virtual std::string get_string() const =0
Get string value.
Interface for configuration handling.
virtual ValueIterator * search(const char *path)=0
Iterator with search results.
Base class for exceptions in Fawkes.
void print_trace()
Prints trace to stderr.
void append(const char *format,...)
Append messages to the message list.
Base class for all Fawkes BlackBoard interfaces.
void resize_buffers(unsigned int num_buffers)
Resize buffer array.
bool is_writer() const
Check if this is a writing instance.
virtual void log_warn(const char *component, const char *format,...)=0
Log warning message.
virtual void log_info(const char *component, const char *format,...)=0
Log informational message.
void get_global(const char *name)
Get global variable.
void remove_watcher(LuaContextWatcher *watcher)
Remove a context watcher.
void set_field(const char *key, int t_index=-2)
Set field of a table.
void push_usertype(void *data, const char *type_name, const char *name_space=0)
Push usertype on top of stack.
void raw_seti(int idx, int n)
Set indexed value without invoking meta methods.
void pop(int n)
Pop value(s) from stack.
void add_watcher(LuaContextWatcher *watcher)
Add a context watcher.
void add_package(const char *package)
Add a default package.
void get_field(int idx, const char *k)
Get named value from table.
LuaInterfaceImporter::InterfaceMap & reading_interfaces()
Get interface map of reading interfaces.
~LuaInterfaceImporter()
Destructor.
void read()
Read from all reading interfaces.
void add_interface(std::string varname, Interface *interface)
Add a single interface to be pushed to the context.
LuaInterfaceImporter::InterfaceMap & writing_interfaces()
Get interface map of writing interfaces.
void close_writing_interfaces()
Close interfaces for writing.
LuaInterfaceImporter(LuaContext *context_, BlackBoard *blackboard, Configuration *config, Logger *logger)
Constructor.
void push_interfaces()
Push interfaces to Lua environment.
void lua_restarted(LuaContext *context)
Lua restart event.
void read_from_buffer()
Update interfaces from internal buffers.
void read_to_buffer()
Read from all reading interfaces into a buffer.
void open_writing_interfaces(std::string &prefix)
Open interfaces for writing.
void close_reading_interfaces()
Close interfaces for reading.
void write()
Write all writing interfaces.
void open_reading_interfaces(std::string &prefix)
Open interfaces for reading.
A NULL pointer was supplied where not allowed.
Fawkes library namespace.