3 ms·
> Plus, if we wanted to, we could certainly write our own wrapper for malloc that took two arguments and multiplied them together with overflow checking. And in
by ben_bai 10y ago
> Plus, if we wanted to, we could certainly write our own wrapper for malloc that took two arguments and multiplied them together with overflow checking. And in fact if we want an overflow-safe version of realloc, or if we don't want the memory to be zero-initialized, then... we still have to do that.
Like reallocarray(3) does?
buf = malloc(x * y);
// becomes
buf = reallocarray(NULL, x, y);
newbuf = realloc(buf, (x * y));
// becomes
newbuf = reallocarray(buf, x, y);
- syntheticnature 10y agoreallocarray(3) looks nifty, but until it's available on a wider, ideally more standard-driven basis than just OpenBSD and FreeBSD, it's likely to not see wide uptake.
- brynet 10y agoIt's already gaining adoption outside of the BSDs. OS X/iOS seem to have it as part of their libmalloc. Android Bionic libc has it as part of the code they sync from upstream OpenBSD. Many open source projects include their own, or simply bundle the OpenBSD implementation: * mandoc * flex * unbound and nsd * tor * tmux * libbsd * libressl * xorg-xserver * ... The list only continues to grow, several more examples to be found on GitHub.
- klodolph 10y agoDarwin (macOS / iOS) is often counted as "one of the BSDs", just a fairly weird one. Big chunks of the standard library are copied from FreeBSD with changes to work on top of Mach.
- achivetta 10y agoThere's code for it in Darwin's libmalloc, but it's not exposed as API. reallocarray() has some difficulties as an interface, mostly inherited from realloc(). I'm a bigger fan of reallocarr(), but that's NetBSD only. We (the operating systems community) need to find a consensus here, but I'm not convinced that reallocarray() is that consensus yet.
- ben_bai 10y agoreallocarray is a very thin layer around realloc. No surprises there. Simple find and replace to bring overflow checking into your code. reallocarr changes the semantics. Equally easy in new pieces of code and a little harder when converting existing code.
- deleted 10y ago[deleted]
- masklinn 10y agoreallocarray(3) is part of the portable OpenBSD compat layer[0], and clocks up at under 10 lines on top of realloc(3): #define MUL_NO_OVERFLOW ((size_t)1 << (sizeof(size_t) * 4)) void *reallocarray(void *optr, size_t nmemb, size_t size) { if ((nmemb >= MUL_NO_OVERFLOW || size >= MUL_NO_OVERFLOW) && nmemb > 0 && SIZE_MAX / nmemb < size) { errno = ENOMEM; return NULL; } return realloc(optr, size * nmemb); } [0] https://github.com/openssh/openssh-portable/blob/master/openbsd-compat/reallocarray.c https://github.com/openssh/openssh-portable/blob/master/open...