Optimizer incorrectly assuming that it doesn't need to refetch the variable value from the structure since it doesn't understand that the i_stream_unref(&mail->data.stream) call actually modifies the whole mail->data structure...
Funny that both Gcc and Sun Studio seems to make the same assumptions in that case :-)
That is interesting.. I don't think I'm doing anything wrong there though. I'll see if I can reproduce this and then try to reduce the test case needed to catch this and then ask gcc people if it's really a bug.
I'm getting more and more sure that this is a C pointer aliasing optimization problem that occurs since the compiler thinks that the i_stream_unref() function doesn't modify the mail->data.destroying_stream flag (not surprising since i_stream_unref is passed a pointer to &mail->data.stream so it looks like it only modifies other parts of the mail->data structure).
Today I can't seem to reproduce it with the GCC compiler (only with the Sun Studio compiler). *Mind boggles*. What the...
Anyway, I've set up a small test case that tries to mimic the code in question (attached). Build with either of the following commands:
make gcc-64-alias make gcc-64-no-alias make gcc-32-alias make gcc-32-no-alias make cc-64-alias make cc-64-no-alias make cc-32-alias make cc-32-no-alias
All will generate two binaries t.all and t.sep. The difference is that t.sep is separately compiled source files, whereas t.all is a single compile of all the .c files concated (to allow the compiler to make better aliasing analysis).
For me t.sep built by cc-64-alias and cc-32-alias fails, all other works.
Btw. If I rebuild Dovecot 1.1.3 with Sun Studio 12, and then just rebuilds src/lib-storage/index/index-mail.c with "-xalias_level=any" so it can't assume that the unref call doesn't modify the destroying_stream flag then things work (no assert triggered).
What makes me a bit worried is if there are other parts of Dovecot that uses similar coding that might trigger similar problem again in the futured. Perhaps one should compile all the files in Dovecot with "-xalias_level=any" when compiling with the Studio compilers just in case. Hmmm...
- Peter