This is the mail archive of the
libstdc++@gcc.gnu.org
mailing list for the libstdc++ project.
Re: [PATCH] Remove volatile qualifiers from mt_allocator
On Wed, 30 Aug 2006, Paolo Carlini wrote:
> Richard Guenther wrote:
>
> >Well, in case we would allocate from one thread only and deallocate
> >from another thread we would need to check if
> >
> > unsigned long __remove = __bin._M_free[__thread_id];
> > __remove *= __options._M_freelist_headroom;
> > if (__remove >= __bin._M_used[__thread_id])
> > __remove -= __bin._M_used[__thread_id];
> > else
> > __remove = 0;
> >
> >__bin._M_free[__thread_id] * __options._M_freelist_headroom can
> >ever become bigger than __bin._M_used[__thread_id]. From looking at
> >the code it seems that __options._M_freelist_headroom is [0, 100],
> >still if __bin._M_used[__thread_id] would be never shrinking but only
> >growing we at some point would stop moving freed blocks back to the
> >global pool.
> >
> >Of course if we continue to allocate from the local pool always this
> >doesn't matter. But surely one can construct some artificial testcase
> >that would produce very unbalanced local free lists and require more
> >than usual total memory?
> >
> >
> Yes, probably that can happen, sigh... Please give me a couple of hours to
> refocus my mind to this issue, which I studied on and off a lot of time ago...
> Actually, I never benchmarked the hammer idea of working under a lock only
> when __block->_M_thread_id != __thread_id... Probably in the producer/consumer
> patterns that is the common case and the performance penalty huge. Unless we
> can skew favorably the heuristics.
You cannot only protect the __block->_M_thread_id != __thread_id with
a mutex, you would need to protect all _M_used readers/writers, but
then...
> Also, I think Benjamin benchmarked *all* the counters atomic, and the
> performance penalty was again big. We could try only _M_used atomic and now
> (with the new atomicity.h) that would affect only actually multithreaded code.
> Maybe we can go that route... What do you think?
...this would be the way to go. And yes, it would of course fix the
issue (making the _M_used elements atomic). One could think of more
trickier ways to avoid the use of atomic ops in the case where
__block->_M_thread_id == __thread_id by having two _M_used counters
per thread, one atomic and changed from threads != __thread_id, one
changed only from __thread_id which also merges both counters at
reclaim time. But this would change class layout.
Richard.
--
Richard Guenther <rguenther@suse.de>
Novell / SUSE Labs