From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00 autolearn=ham autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 103376,cc05aeb5e0d8b475 X-Google-Attributes: gid103376,public X-Google-ArrivalTime: 2003-09-14 07:25:02 PST Path: archiver1.google.com!news1.google.com!sn-xit-02!sn-xit-06!sn-xit-08!supernews.com!news.tele.dk!news.tele.dk!small.news.tele.dk!newsgate.cistron.nl!skynet.be!skynet.be!louie!tlk!not-for-mail Sender: lbrenta@lbrenta Newsgroups: comp.lang.ada Subject: Re: Free-ing memory: not springing leaks? References: <2TM8b.1013$Nb6.297@newsfep4-winn.server.ntli.net> <9JY8b.1963$WI3.25442@newsfep4-glfd.server.ntli.net> From: Ludovic Brenta Date: 14 Sep 2003 16:24:36 +0200 Message-ID: User-Agent: Gnus/5.09 (Gnus v5.9.0) Emacs/21.2 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Organization: -= Belgacom Usenet Service =- NNTP-Posting-Host: 80.200.138.190 X-Trace: 1063549468 reader0.news.skynet.be 24177 80.200.138.190:53428 X-Complaints-To: usenet-abuse@skynet.be Xref: archiver1.google.com comp.lang.ada:42479 Date: 2003-09-14T16:24:36+02:00 List-Id: chris writes: > Matthew Heaney wrote: > > If you know it was malloc'd, then yes, just write a binding to free and > > call that. > > And if you don't, then it's hit and miss? ... it figures. I wonder > how C programmers deal with this :( This is supposedly documented by your library. Some libraries return "statically allocated" memory which you must not free. This is for example the case of readdir(3). In the particular case of dlerror(3), I've just had a look at the sources because the documentation is very evasive about this. As it turns out, dlerror() runs in one of two modes, thread-safe or not. In thread-safe mode, it allocates a dynamic block of memory for each thread. This block contains a pointer to the string returned. The function allocates and frees this pointer, and _you should not free the memory yourself_, because you cannot set the pointer to NULL (remember that C is pass-by-value only, so what you receive from dlerror() is a copy of the pointer). If for some reason, dlerror() cannot use thread-safe mode, it falls back to a thread-unsafe mode in which there is a single, statically allocated, block of memory containing the pointer to the error string. As before, dlerror() allocates and frees the memory for the string. If you wand to forcefully free the memory, your best bet is to call dlerror() twice, like this (I have not tried to compile this, mind you): Dynamic_Loader_Error : Exception; procedure Dl_Error is function dlerror returns Interfaces.C.Strings.chars_ptr; pragma Import (C, dlerror, "dlerror"); Error_Message : Interfaces.C.Strings.chars_ptr := dlerror; use type Interfaces.C.Strings.chars_ptr; begin if Error_Message /= Interfaces.C.Strings.Null_Ptr then declare S : String := Interfaces.C.Strings.Value (Error_Message); begin Error_Message := dlerror; -- ask it to free the memory Ada.Exceptions.Raise_Exception (Dynamic_Loader_Error'Identity, S); end if; end if; end Dl_Error; -- Ludovic Brenta.