Path: ...!weretis.net!feeder9.news.weretis.net!news.nk.ca!rocksolid2!i2pn2.org!.POSTED!not-for-mail From: Richard Damon Newsgroups: comp.lang.c Subject: Re: realloc() - frequency, conditions, or experiences about relocation? Date: Tue, 25 Jun 2024 07:21:42 -0400 Organization: i2pn2 (i2pn.org) Message-ID: References: <875xtyu0kk.fsf@nosuchdomain.example.com> <87frt1tk0z.fsf@nosuchdomain.example.com> MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit Injection-Date: Tue, 25 Jun 2024 11:21:42 -0000 (UTC) Injection-Info: i2pn2.org; logging-data="1124393"; mail-complaints-to="usenet@i2pn2.org"; posting-account="diqKR1lalukngNWEqoq9/uFtbkm5U+w3w6FQ0yesrXg"; User-Agent: Mozilla Thunderbird Content-Language: en-US In-Reply-To: <87frt1tk0z.fsf@nosuchdomain.example.com> X-Spam-Checker-Version: SpamAssassin 4.0.0 Bytes: 3727 Lines: 65 On 6/25/24 6:05 AM, Keith Thompson wrote: > Lawrence D'Oliveiro writes: >> On Mon, 24 Jun 2024 02:55:39 -0700, Keith Thompson wrote: >>> Lawrence D'Oliveiro writes: >>>> The usual way I use realloc is to maintain separate counts of the >>>> number of array elements I have allocated, and the number I am actually >>>> using. A realloc call is only needed when the latter hits the former. >>>> Every time I call realloc, I will extend by some minimum number of >>>> array elements (e.g. 128), roughly comparable to the sort of array size >>>> I typically end up with. >>>> >>>> And then when the structure is complete, I do a final realloc call to >>>> shrink it down so the size is actually that used. Is it safe to assume >>>> such a call will never fail? Hmm ... >>> >>> It's not safe to assume that a shrinking realloc call will never fail. >>> It's possible that it will never fail in any existing implementation, >>> but the standard makes no such guarantee. >>> >>> ... >>> >>> Having said all that, if realloc fails (indicated by returning a null >>> pointer), you still have the original pointer to the object. >> >> In other words, it’s safe to ignore any error from that last shrinking >> realloc? That’s good enough for me. ;) > > What? No, that's not what I said at all. > > Suppose you do something like: > > some_type *p = malloc(BIG_VALUE); > // ... > p = realloc(p, SMALL_VALUE); > > If the realloc() succeeds and doesn't relocate and copy the object, > you're fine. If realloc() succeeds and *does* relocate the object, p > still points to memory that has now been deallocated, and you don't have > a pointer to the newly allocated memory. If realloc() fails, it returns > a null pointer, but the original memory is still valid -- but again, the > assignment clobbers your only pointer to it. > > I presume you can write code that handles all three possibilities, but > you can't just ignore any errors. > The idiom I always learned for realloc was something like: some_type *p = malloc(size); if (!p) { // allocation failed, do something about it. (might be just abort) } .... some_type *np = realloc(p, new_size); if (np) { p = np; } else { // p still points to old buffer, but you didn't get the new size // so do what you can to handle the situation. } // p here points to the current buffer, // might be the old size or the new.