3 ms·
I think the part where your reasoning is invalid is this part: > so its generation number is undefined With e.g. a random C compiler and a random malloc, that
by jsnell 3y ago
I think the part where your reasoning is invalid is this part:
> so its generation number is undefined
With e.g. a random C compiler and a random malloc, that's true. But why couldn't the language and runtime cooperate to ensure it is defined?
For example deallocation can write a predictable value to that slot, which is never used as a legit generation index. The memory allocator can make sure that a memory address that ever contained a generation can never contain anything else than generation ids for the entire runtime of the program (e.g. by ensuring that for a given page, all objects are the same size and the allocations are aligned to that size). The language can make sure that nothing else can get written to such a memory address by enforcing bounds checks.
- deleted 3y ago[deleted]
- ajb 3y agoOk but then aren't you going to get memory fragmentation? If you allocate and then deallocate a billion 1kB objects, you can't then coalesce them to allocate larger units because the generation number locations before each 1kB can't be given back to user code.
- verdagon 3y agoIn the basic generational references approach that was a drawback, and the reason it couldn't release memory back to the OS. We planned to use something like MESH [0] to reduce the fragmentation. We created two newer approaches since then, which let any memory be reused for any purpose: * Random generational references, where it's fine if generations overlap with other data. * Side-table generations, which is slower but we keep the generations in a side-table. It's can be seen in old 0.1 versions as the "resilient-v2" mode, and I plan on resurrecting it for unrelated reasons. The former will be the default, and the latter we'll be adding back in as an option. Hope that helps! [0] https://arxiv.org/pdf/1902.04738.pdf https://arxiv.org/pdf/1902.04738.pdf
- verdagon 3y agoYep, this is the correct answer. Accessing released memory is undefined in C, but well-defined in Vale. The goal is to ensure that the user predictably+safely gets either a segmentation fault or an assertion failure. We have a future improvement planned here too: for unrelated reasons (to support generation pre-checking) the random generational references implementation will soon not even unmap any virtual address space, instead remapping it to a central page, so we won't even get any segmentation faults, just assertion failures.