Path: utzoo!utgpu!jarvis.csri.toronto.edu!mailrus!csd4.milw.wisc.edu!leah!itsgw!steinmetz!uunet!auspex!guy From: guy@auspex.UUCP (Guy Harris) Newsgroups: comp.sources.d Subject: Re: gnu egrep - realloc of 0 bytes caused failure: Memory exhausted Message-ID: <1028@auspex.UUCP> Date: 17 Feb 89 06:04:12 GMT References: <1114@rlgvax.UUCP> Reply-To: guy@auspex.UUCP (Guy Harris) Organization: Auspex Systems, Santa Clara Lines: 58 >nor why it supposedly works on other machines >(assuming that realloc is called with 0 on other machines). Some implementations of C permit you to call "malloc" or "realloc" with a size of 0. Others do not. Since many implementations return e.g. a pointer to the "data" portion of a structure such as: +------------------+ | memory allocator | | header stuff | +------------------+ | data | <- pointer points here . . . . . . +------------------+ it *is* possible, in those implementations, to have "malloc"/"realloc" return something if you ask it for zero bytes. Since "realloc" can grow or shrink a block, it's not necessarily useless to ask for 0 bytes of storage; you can start out with a zero-byte block and grow it as necessary, without having to remember that you asked for 1 byte (or storage unit of whatever sort; e.g. array element, if you're stuffing an array into it) when you first got it. In some ways, it's the moral equivalent of a zero-length array in something such as: struct message { int length; char data[0]; }; where an N-byte message would require "sizeof (struct message) + N" bytes. Reasons have been given why zero-length arrays might not be a good idea (attempts to drag me into a debate on the merits of zero-length arrays will produce no responses, just a fair bit of annoyance - I've steered clear of that debate). Some of those reasons might apply to zero-length mallocated blocks, as well. Some implementations do, in fact, forbid them; the May 13, 1988 ANSI C draft says that an implementation can do one of two things when asked to allocate a zero-length block of storage: 1) return a null pointer; 2) return a "unique pointer", which presumably means "return a pointer to something that can be treated as a zero-length block of storage" - i.e., you can't store anything into it, but you can ask "realloc" to grow it and can ask "free" to free it. The SVID currently says it must return a null pointer. However, the standard "malloc" in S5 (which isn't SVID-compliant - only the one in "-lmalloc" is SVID-compliant) does 2); I seem to remember that at least one version of "dc" depended on 2) working. Bottom line: if you want your code to be portable, make sure you don't call "malloc", "realloc", etc. with a size of 0.