From: Sanjeev B.A. <iam...@gm...> - 2011-11-15 21:18:43
|
On Tue, Nov 15, 2011 at 11:45 PM, Gustavo Sverzut Barbieri < bar...@pr...> wrote: > On Tue, Nov 15, 2011 at 11:53 AM, Enlightenment SVN > <no-...@en...> wrote: > > Log: > > Eina_xml based dbus introspection support. Thanks to Gustavo for the > parser. > ... > > +static void cb_introspect(void *data, DBusMessage *msg, DBusError > *error) > > +{ > > + DBusError e; > > + DBus *dbus = ((struct dbus_cache *)(data))->dbus; > > + const char *xml_str; > > + > > + if ((error) && (dbus_error_is_set(error))) > > + { > > + fprintf(stderr, "Error: DBus replied with error %s: %s\n", > > + error->name, error->message); > > convert it to eina log, create one domain for elv8 and other for > submodules such as elv8-dbus > Ok. > > > > + > > + struct DBus_Introspection_Parse_Ctxt *ctxt; > > + ctxt = (struct DBus_Introspection_Parse_Ctxt *)calloc(1, > sizeof(struct DBus_Introspection_Parse_Ctxt)); > > + if (!eina_simple_xml_parse(xml_str, strlen(xml_str), EINA_TRUE, > cb_parse, ctxt)) > > + { > > + fprintf(stderr, "Error: could not parse XML:\n%s\n", xml_str); > > leak of ctxt! > Will fix this. > > > > + return; > > + } > > + > > + std::pair<std::map<const char *,DBus_Introspection_Parse_Ctxt > *>::iterator,bool> ret; > > I'd not allocate ctxt, and would not make it into cache. > > As I've explained at IRC, the correct structure for this is: > > path => {interfaces, children} > children => [path1, path2, ...] > > interfaces = [interface1, interface2, ...] > interface = {methods, signals, properties} > > methods = [method1, method2, method3...] > method = {name, [argument1, argument2, ...]} > signals = [signal1, signal2, signal3...] > signal = {name, [argument1, argument2, ...]} > properties = [property1, property2, property3...] > property = {name, type} > Don't the existing structures do this already? Except for the addition of the DBus_Node? > > Usage is one of: > 1 - explicit: > var obj = bus.get_object(name, path); > var iface = obj.get_interface(iface_name); > iface.Method(p1, p2, p3); > 2 - implicit: > var obj = bus.get_object(name, path); > obj.Method(p1, p2, p3); > > I haven't yet decided on the best way to make dbus calls/signals simple for users. Let's discuss over IRC today. > The first case is simple: > iface = find_interface(iface_name) # mapping string => interface > structure > method = find_method(iface, signature) # mapping string => > method structure > > signature you need to compute for instance: > ai Method(o,s,i) > ai Method(o,s,name=value) # named values will be supported in > elev8? parameters in a hash/map? Must define a policy, like sort > alphabetically and put at the end. Likely will have to have multiple > signatures per method! > > The second case is bit more complex: > ifaces = get_all_interfaces(obj) # mapping path => list of iface > structures > methods = [] > for i in ifaces: > m = find_method(i, signature) # mapping string => method structure > if not m: > continue > methods.append(m) > if len(methods) > 1: > raise "Error: conflicting interfaces for " + signature + ": > " + ", ".join(ifaces) > else if len(methods) == 0: > raise "Error: unknown method" > method = methods[0] > > Cache: method lookup is likely expensive, then cache it as LRU per > object, with a limit of dozens so you don't leak memory. Test case > must not go the slow path after the first iteration: > > for (i = 0; i < 1000; i++) > obj.Method(i); > > Assuming that services are implemented correctly the interfaces are > unique globally, then you can have: > > global map interfaces: "interface name" string => interface > interface map methods: "method signature" string => method > object list interfaces: pair ("interface name" string, "interface > instance" interface) > object lru methods: pair ("method signature" string, "method > instance" method) > > > > =================================================================== > > --- trunk/PROTO/elev8/src/bin/dbus_library.h 2011-11-15 13:34:28 UTC > (rev 65263) > > +++ trunk/PROTO/elev8/src/bin/dbus_library.h 2011-11-15 13:53:27 UTC > (rev 65264) > > @@ -4,21 +4,100 @@ > > #include <v8.h> > > #include <dbus/dbus.h> > > #include <E_DBus.h> > > -#include "dbus_introspect.h" > > +#include <Eina.h> > > + > > #include <exception> > > -#include <sstream> > > +#include <map> > > #include <iostream> > > #include <fstream> > > > > +/* memory efficient structures to hold introspection information. > > + * maybe Eina_Inlist could be replaced with single array of structures > > + * (not to be confused with Eina_Array!!!!) > > + */ > > + > > +struct DBus_Method_Argument > > +{ > > + EINA_INLIST; > > + const char *type; > > + const char *name; > > + Eina_Bool is_output:1; > > +}; > > if you're using structs with malloc/free (C-like) then declare as > extern "C" {}, will avoid name marshling by C++ compiler, etc. > Yes, will fix this. > > -- > Gustavo Sverzut Barbieri > http://profusion.mobi embedded systems > -------------------------------------- > MSN: bar...@gm... > Skype: gsbarbieri > Mobile: +55 (19) 9225-2202 > > > ------------------------------------------------------------------------------ > RSA(R) Conference 2012 > Save $700 by Nov 18 > Register now > http://p.sf.net/sfu/rsa-sfdev2dev1 > _______________________________________________ > enlightenment-devel mailing list > enl...@li... > https://lists.sourceforge.net/lists/listinfo/enlightenment-devel > |