|
|
|
|
|
by hlandau
702 days ago
|
|
My own view on this is that a hardened allocator API should separate the functions of an allocation identifier/cookie and the actual pointer to the allocated memory: func alloc(numBytes: usize) -> (ptr: void *, cookie: uword) | Error
func free(cookie: uword, numBytes: usize) -> void
where free() maybe also should take ptr, strictly for validation purposes.A design like this encourages segregation of allocator metadata and the allocated memory, though it is possible to achieve such a design with the classic C malloc/free API. However, a design like this is even more helpful against use-after-free because cookies can be unique for the lifetime of a program, whereas pointers naturally get reused when a block of memory is reallocated. So the traditional API can never be fully resilient against UAF, whereas an API like this can. The underlying observation here is that malloc/free couples two different things (access to memory and identifying a previously made allocation) in a way that creates an API which is far less able to mitigate misuse in a safe way. IMO, these functions should be separated in new designs. |
|
What it solves is double-free, not use-after-free; potential corruption (even if not of the allocator state) is always gonna be a problem with any allocator that ever reuses memory.