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=-0.8 required=5.0 tests=BAYES_00,INVALID_DATE, MSGID_SHORT autolearn=no autolearn_force=no version=3.4.4 Path: utzoo!utgpu!watmath!clyde!att!osu-cis!tut.cis.ohio-state.edu!cwjcc!mailrus!cornell!batcomputer!itsgw!steinmetz!uunet!mcvax!enea!sommar From: sommar@enea.se (Erland Sommarskog) Newsgroups: comp.lang.ada Subject: Re: Garbage Collection Message-ID: <4206@enea.se> Date: 31 Dec 88 00:04:32 GMT Organization: ENEA DATA AB, Sweden List-Id: I'm trying to get Bill Wolfe to explain how he his deallocation-on- block-exit scheme would work in an example I had. For brevity I deleted my example in my last article. Apparently that was a fatal mistake, because the answer I got wasn't even close the question. So, my apologies, I repeat the exmample with some clarifcations. We have: Generic Data_type is limited private; Procedure -- Assign, "<" and ">" Package Tree_handler Tree_type is private; Assume further that we instantiate this package with Some_access_type, it could be an imported limited type, it could be a locally defined. Then we have the procedure: Procedure Insert_data_to_tree(Tree : in out Tree_type; Data_of_some_sort : in Any_type); Reference : Some_access_type; Begin Reference := new Some_type; -- Or subprogram call for external type Prepare(Reference, Data_of_some_sort); Insert(Tree, Reference); End Insert_data_to_tree; The Assign procedure which we provide when we instantiate the tree handler is simply: Procedure Assign(A : in out Some_access_type; B : in Some_access_type) is Begin A := B; End Assign; Now, what happens with Reference.all on exit of Insert_to_data_tree, with your scheme? (Assume there is no user-written DESTROY procedure.) Would Reference.all be deallocated although there still is a living reference to it in Tree? Or will it be ignored in any case? Or are you having a reference count hidden somewhere to save you? Another interesting issue is: When Tree drops from the stack what happens with our little object at this occassion? The Tree's DESTROY procedure cannot know anything about it, so we have to traverse the tree and deallocate all referd objects ourselves. (And pray we haven't inserted some of them in a queue somewhere else too!) With garbage collection... >> I forgot: When the system chokes with "heap full" and you as a maintainer >> is trying to find where all space is being wasted. With garbage collection >> you at least know that all this memory is being used. Without, you don't >> know if it is just memory leakage or real overuse. > > Advanced debugging tools should be used to address this issue. So why can't these "advanced debugging tools" be used to "pin down the exact state of the system" when we have garbage collection? > I'm quite aware of Eiffel, and I have just shown (in another article) > how reliance upon garbage collection is a sure way to get your ADT > rejected by users who are programming critical applications. This I assume with critical mean time-critical here. If the issue is reliability or space, garbage collection is only there to help you. There is good chance that your ADT will be rejected anyway. The critical developper looks at you and says: "You use Unchecked_dellocation? Sorry, then I can't use your ADT. Memory fragmention will cause too great a time penalty when the system have lived for a while." So you return and implement a free-list and try again. The developper looks at you: "You have an internal task for the free-list?" "Eh, no" "You must have that, else all will be a mess if two tasks access the list simultaneously." So you end up with with adding this task, and your critical developper is satisfied. (Reservation: My experience of tasking in Ada is not that great. Possibly the SHARED pragma could help, but I doubt.) Then you come to me who is writing an interactive data-base application for VAX/VMS and give me your ADT. It looks nice so I use it. Some time later my users complains: the reponse time is too long. What have you done? Being equipped with good tools I re-link the system with PCA (a profiler for VMS) to find the bottle-neck. And I to my surprise I find that rendez-vous are taking place in the system. "Ah, that why it's slow, but where do they come from?" Soon your ADT is found to be guilty. And just a little later your ADT is edited to be taskless, and my users are happy again. (Until they get dumps because memory is full, because I forgot to call one of your damned Destroy routines somewhere.) The lesson to learn is that it is very hard to satisfy everyone. And you end up with two versions anyway. Given that there are many shops who never will write an application were garbage collection is unacceptable, ADTs relying on its presence will still have a wide use. Probably more use than ADTs using tasks to protect free lists. (I have reponse times to think of, but garbage collection is no problem. With the collector running as coroutine like in the Eiffel system, it can work while I'm waiting for input.) There is a solution that gives us a possibility to use the same implementation of the ADT above. And that solution is, yes you guessed it: garbage collection. You provide your ADT with a Destroy procedure that your critical developper uses. (As long your block-exit scheme doesn't work properly, he has to call it explicitly. I doubt he would accept your idea anyway.) I, in my turn, give a damn about it. All I want is that the task should not be used, which you can have a special call for. Then I just set the garbage_collection flag in my system configuration file. -- Erland Sommarskog ENEA Data, Stockholm This signature is not to be quoted. sommar@enea.se