On Wed, Oct 08, 2014 at 11:23:51PM +0200, Lennart Poettering wrote:
> On Wed, 08.10.14 23:07, Zbigniew Jędrzejewski-Szmek (zbys...@in.waw.pl) wrote:
> 
> > > > > > A related thing: there's a mapping bus-error <-> errno implemented,
> > > > > > but it only works for the errors defined in the library itself. It
> > > > > > would be nice to extend this mapping to the "user" defined errors,
> > > > > > e.g. in core/.  Would you be amenable to adding a mechianism to
> > > > > > register additional mappings like bus-error-mapping.gperf so that 
> > > > > > they
> > > > > > are used by the library?
> > > > > 
> > > > > Maybe have internal versions of the conversion calls that allow
> > > > > passing in an additional table?
> > > > That is not as convenient. E.g. sd_bus_error_set
> > > > internally calls bus_error_name_to_errno. Currently, this always
> > > > returns EIO for errors unknown to the library, and then the caller
> > > > does it own lookup (e.g. looking at 
> > > > transaction_add_job_and_dependencies()).
> > > 
> > > What precisely are you proposing instead?
> > 
> > typedef const name_error_mapping*
> > (*bus_error_mapping_lookup_t) (const char *str, size_t len);
> > 
> > int bus_error_add_mapping(bus_error_mapping_lookup_t mapping);
> > 
> > This could be used to register a custom function similar to our
> > bus_error_mapping_lookup(). It would get stored in a global table (of
> > fixed size?), and bus_error_mapping_lookup would be the first slot in
> > this table and the calls to bus_error_mapping_lookup would be
> > replace by a function which iterates over this table and
> > returns the first successful lookup.
> 
> I am really not a fan of global variables for things like this... If
> it would be marked as TLS I'd feel a bit more comfortable though...
> 
> I wonder what it would take to make this work without any registration
> code. i.e. we could use some executbale section tricks hidden in some
> macros to allow any module to register mappings, and simply by being
> compiled in we'd find them. 
> 
> In such a scheme the registration race and scope issues should go
> away, since everything is always registered in all threads.
> 
> To define a map array, in as many .c files as desired:
> 
> __attribute((__section__("errnomap"))) __attribute((__used__)) const struct 
> struct my_errno_map[] = { .... };
> 
> And then, use this to find the section:
> 
>     extern struct my_errno_map[] __start_errnomap;
>     extern struct my_errno_map[] __stop_errnomap;
> 
> gcc supposedly maps this automatically to the start and end of the
> section we defined above (yes, __start_ and __stop_ is magic), and
> then we can just enumerate through them. And any .c module that
> defines more maps transparently is found.
That would be lovely. Last time I checked, a custom linker
script was also necessary, but this was a long time ago, so maybe
things have changed.

Zbyszek
_______________________________________________
systemd-devel mailing list
systemd-devel@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/systemd-devel

Reply via email to