2 ms·
I'm not a C++ programmer but I noticed this conflict. C++ is adding features like coroutines that perform hidden allocations, while at the same time shifting aw
by wahern 7y ago
I'm not a C++ programmer but I noticed this conflict. C++ is adding features like coroutines that perform hidden allocations, while at the same time shifting away from exceptions. You can't have it both ways.
You can have hidden allocations, you just need an exception mechanism. It sounds like Postgres does this with setjmp/longjmp. That's typical. I do that with my JSON C library--https://github.com/wahern/json/blob/master/src/json.h#L72 https://github.com/wahern/json/blob/master/src/json.h#L72 And setjmp/longjmp is how Lua implements its exceptions.
Lua is interesting in that it's a dynamically-typed scripting language that permits recovery from memory allocation failures in a rigorous manner. It doesn't add much if any complexity to the Lua implementation--if anything the discipline arguably helps keep things simpler. But it does require the Lua VM authors to always be mindful about maintaining consistency of the VM state. In particular it means they have to make sure all dynamically allocated memory is properly anchored in the object graph. This type of discipline isn't something you can refactor for after the fact, but it's not as difficult as it seems if you start out this way (modulo the lack of compiler enforcement). The Lua C API is also carefully designed--most routines are implemented and documented to not do any hidden allocations. And unlike any other scripting language with a C API I've used or examined, Lua provides a plethora of convenient abstractions for keeping foreign data pointers anchored in the object graph, as well as the mechanisms and semantics that permit both C and Lua code to catch and reliably recovery from exceptions, including allocation exceptions.
By contrast, while Go conceptually could provide OOM recovery--it has an exception mechanism almost identical to Lua's, and likewise uses non-copying GC--but much of the implementation makes the assumption that allocation never fails. As a practical matter correct, reliable, and consistent recovery from OOM isn't possible for Go. As I said, it's not the type of thing you can add after the fact. So instead you see a recapitulation of decades of myths[1] and contrivances[2] focused on "managing" memory. I only pick on Go because massive concurrency, and in particular massively concurrent network sessions, is it's niche. Even at "web scale" where you have the same Go process running on dozens or hundreds of other machines, this neglect to tackle allocation failure has resulted in often times exceptionally poor quality of service for Go apps. Without proper allocation failure recovery, "managing" memory becomes a black art rather than a science, with predictable results in terms of consistency and stability.
It's a shame to see C++ gleefully going down this road, seemingly having finally drunk the Kool-Aid and adopted the myth that handling allocation failure to too difficult and too error prone; that it's not your problem and something else higher up the stack will solve the problem for you. :(
[1] E.g. big allocations are more likely to fail
[2] E.g. reserving large blocks to be released according to some imaginative heuristic intended to predict and forestall allocation failure
- anarazel 7y ago> It's a shame to see C++ gleefully going down this road, seemingly having finally drunk the Kool-Aid and adopted the myth that handling allocation failure to too difficult and too error prone; that it's not your problem and something else higher up the stack will solve the problem for you. :( I think the reasoning behind this part of the C++ proposal at hand is a bit more complicated than that. It's imo worth reading section 4.3 specifically about the memory allocation issue, and the motivation for the whole exception overhaul in in section 2 (although that's a bit longer). The reasoning isn't itself that it's too difficult or such, it's that the overhead required by something like the current exception handling is high, and that it's quite desirable to makr a lot more of the standard library as not throwing exceptions - and the only cause a lot of them throw, is OOM. http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p0709r0.pdf http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p070...