This is the mail archive of the
elfutils-devel@sourceware.org
mailing list for the elfutils project.
Re: dwarf_output overview
- From: Mark Wielaard <mjw at redhat dot com>
- To: elfutils-devel at lists dot fedorahosted dot org
- Date: Fri, 08 Oct 2010 16:12:58 +0200
- Subject: Re: dwarf_output overview
On Wed, 2010-10-06 at 13:55 -0700, Roland McGrath wrote:
> > template<typename input, typename arg_type>
> > const value_type *add (const input &v, arg_type &arg)
> > {
> > return add (value_type (v, arg));
> > }
> >
> > So it will always create a new value_type
>
> Right. That's because in practice the input is always of a different
> type, not the actual value_type. e.g., the input value argument will be
> a const char * or a const std::string, when the value_type is actually
> dwarf_output::value::value_string. The value_string template constructor
> handles those as input types.
Thanks for the concrete example. This is actually what I keep missing,
every time I try to match concepts to code. The actual types (after
template instantiation) of some of these argument. While trying to
follow the arguments going down I somehow missed we extracted the actual
value data and that this is the input type here. Which is obvious in
retrospect if you realize that the value_type must be a concrete
initializer which takes as argument the actual data payload (not the
original dwarf/dwarf_edit::value::value_xxx). Sigh. But then what is
this arg_type &arg?
> For example, dwarf_data::value_string is the element type inside the
> _m_strings set. A value_string is derived from std::string and its
> template constructor passes the input value argument to the normal
> std::string constructor. That takes a std::string or a const char *, so
> we just get the copied string. value_string::hasher uses more layers of
> subr::hash* stuff, so it turns into a normal string hash function
> (algorithm stolen from boost).
Why not use std::tr1::hash<std::string &> ?
> When it gets into the value_set, it's wrapped in a hashed_value<value_string>
> object, which is just the value_string with its precomputed hash value.
> The standard unordered_set logic then does the actual hash table insertion,
> but its "hash function" is just to fetch the stored _m_hash from the
> hashed_value<value_string>.
Aha. Sorry I was again confused about which hash function was being
used. But indeed we are using the hashed_value_type::hasher, not the
value_type::hasher. Doh.
> This is so that we aren't recomputing the
> string hash function of the elements inside each hash bucket to compare
> to the new element, just doing integer comparison on the saved _m_hash.
>
> The value_set::add method always returns the pointer to the object
> sitting in the hash bucket. If this value was already in the set,
> we haven't added anything. In either case, we just throw away the
> just-created value_type (e.g. value_string) object, because unordered_set
> stores its own copy.
That all makes sense, except for the throwing away. That seems wasteful,
but might be the best we can do when reusing the sdt unordered_set?
> All of this stuff is essentially uninteresting. It's just the layers of
> C++ hooey to keep a hash table for each value_something type, and return
> the const value_something * pointing into that hash table.
Yeah, sorry that I keep getting lost in the uninteresting stuff.
Thanks,
Mark