https://issues.dlang.org/show_bug.cgi?id=15056
--- Comment #7 from Marco Leise <marco.le...@gmx.de> --- (In reply to Kenji Hara from comment #5) > Today, in Win64 and all Posix platforms, dmd uses exception handling table, > and it doesn't support using alloca in a function that contains try-finally > statement. I don't know how exactly exception handling works in D and my mental image currently is that as long as there is a dtor call pending that needs to run when an Exception interrupts the function's execution, alloca() must not be in effect. Under the premise that my assumptions hold alloca() would work in following cases: A) No statement could throw while the dtor call is pending. In fact the function is 'nothrow': ------------------------------- import core.stdc.stdlib; struct S { ~this() nothrow {} } S foo() nothrow { return S(); } void main() nothrow // Worked in 2.067, regressed in 2.068 { void* p = alloca(1234); foo(); } ------------------------------- B) The dtors have already been run, by the time alloca() is reached: ------------------------------- import core.stdc.stdlib; struct S { ~this() {} } S foo() { return S(); } void main() // Worked in 2.067, regressed in 2.068 { { foo(); } void* p = alloca(1234); } ------------------------------- (In reply to Walter Bright from comment #6) > The fact that this was compiling on early compilers doesn't mean it was > working. No doubt there is a reason for this fix that introduced the regression. It's just not my code :D. I still believe that for my use case 2.067 did the right thing, otherwise I would have dealt with segfaults earlier, right? For example take this line here that broke in 2.068: https://github.com/mleise/fast/blob/v0.2.1/source/fast/internal.d#L136 `wcharPtr` has as a default parameter an alloca() call and returns a struct with a dtor. From this struct I extract a character and return immediately. At no time can an exception be thrown, so - I assume - no try-finally is ever inserted and therefore no warning about mixing exception handling with alloca(). You can run this code (tested on Linux/amd64) with dmd-2.067.1 and dub by typing "dub fetch fast && dub run fast". (In reply to Martin Nowak from comment #4) > You could pass in a buffer to avoid alloca. > ... Yes, but dynamic stack memory allocation is an entirely different thing. Sure one could always return blocks of 1, 2 or 4 KiB, but then you quickly move into cold cache and eat stack space faster than necessary. Now when working with strings the requirement is often only a few bytes, but alloca may be feasible for up to, say 1024. The way I use it is to set a limit for it and switch to malloc like this (simplified): `required > 1024 ? malloc(required) : alloca(required)` With the changes in 2.068, alloca() can't easily be used in functions that use RAII and return something, which is frequent in D. P.S.: I could fix the offending line in my code by changing it like this: // BEFORE benchmark ("cstring.wcharPtr", () { return wcharPtr!pathname.ptr[pathnameWStringLength]; }) benchmark ("cstring.wcharPtr", () { wchar result; { auto buf = wcharPtr!pathname; result = buf.ptr[pathnameWStringLength]; } return result; }) // AFTER But this was supposed to be an concise/efficient way to provide 0-terminated whcar* to external libraries, not an exercise in obfuscated coding!</rant> --