> On Sun, September 24, 2006 22:19, Bart Samwel wrote:
>
>> It looks like connection_base::RemoveTrigger() is failing. I guess we
>> have R.second = R.first = m_Triggers.end(), in which case this line:
>>
>> const TriggerList::iterator i = find(R.first, R.second, E);
>>
>> may fail in some implementations, but definitely this one:
>>
>> if (m_Conn && (R.second == ++R.first))
>> Exec(("UNLISTEN \"" + T->name() + "\"").c_str(), 0);
>>
>> Jeroen? Any idea if this can ever happen?
>
> Good work... I'm not sure though: why should that find() fail if R.first
> and R.second are both equal to m_Triggers.end()? AFAICS find(x, x, y) is
> a find() on an empty range, and so should always return x without it ever
> being dereferenced or incremented. Shouldn't behaviour be perfectly
> well-defined even if x is an end()?
I ran the test in the visual studio debugger and find() goes past without
problem. Of course in the test R.first is not end() so it's not a test if
find() will fail when both argument is end(), although I'm inclined to agree
with the accessment above.
> So Zhao (or Xiaofeng, which should I use?), could you test this fix for
> src/connection_base.cxx, lines 591-597?
Xiaofeng will do.
>
> {
> // Erase first; otherwise a notification for the same trigger may yet
> come
> // in and wreak havoc. Thanks Dragan Milenkovic.
> + const bool gone = (m_Conn && (R.second == ++R.first));
> m_Triggers.erase(i);
>
> - if (m_Conn && (R.second == ++R.first))
> + if (gone)
> Exec(("UNLISTEN \"" + T->name() + "\"").c_str(), 0);
> }
>
> All that that does is move the computation of the "if" condition up before
> the erase(). If our analysis is correct, that should fix the problem.
>
Bravo, That fixed it!
Xiaofeng
_______________________________________________
Libpqxx-general mailing list
[email protected]
http://gborg.postgresql.org/mailman/listinfo/libpqxx-general