From: Steve B. <Ste...@zv...> - 2003-06-29 11:26:44
|
Hi Roy, I've been working on TclXML v3.0 and trying to incorporate some new ideas on document and node management. In particular, your request to have implicit document destruction has been implemented. However, I'm now at the point where I just cannot get it to work reliably. What I have at the moment is this; documents are managed by TclXML - the libxml2 wrapper (TclXML/libxml2) parses a document and a Tcl object is stored inside the parser instance that references the document. The 'get document' method may be used to retrieve that object. There is now an internal TclDOM command, 'dom::libxml2::adoptdocument', that takes the document object and layers DOM structures on top of it. When TclDOM "adopts" a document it also creates a Tcl command that has a reference to that document as its clientData. The docObj module in TclXML/libxml2 maintains a list of which Tcl_Obj's have their internal representation referring to the document. Every time a Tcl_Obj frees its reference that object is removed from the list. When the list becomes empty, the document is destroyed (ie. implicit destruction). In other words, the document is reference counted but instead of a simple count a list is used. The reason for this is that if the document id *explicitly* destroyed then all Tcl_Obj's that reference the document must have their internal representation invalidated (to avoid inadvertant core dumps). Consider the following script: package require dom::libxml2 set p [xml::parser] $p parse <Test/> # parser instance $p now contains the xmlDoc set d [$p get document] # variable $d now also references the xmlDoc $p free # parser instance, along with its reference to the # document, has been destroyed. However, $d still # references the document so it remains in memory. set doc [dom::libxml2::adoptdocument $d] # $doc also references the object and it is now a Tcl command $doc cget -implementation # the new alternative to 'dom::document cget $doc -implementation' # [1] dom::serialize $doc # Should return the original XML text # [2] ### end of script That last command *should* succeed but, alas, it fails. This is because prior to [1] there is a single Tcl_Obj that references the xmlDoc. At various times the Tcl_Obj has a reference count of 2 or 3, corresponding to $p, $d and $doc. However, at [1] the *internal representation* of the Tcl_Obj is changed to something else, since the Tcl_Obj has been used as a command reference. Now the docObj module is informed that the internal rep has been freed and it notices that there are now no references to the xmlDoc to it is destroyed. The Tcl command at [2] returns the error message "no such document", because by that time it has been destroyed. My conclusion is that object shimmering defeats any attempt to have mutable objects automatically garbage collected. It is not enough to retain a reference to the Tcl_Obj to keep the document alive - somehow you must prevent the internal rep from being changed. It would seem that the design of the Tcl object system does not support this. At this point there is a choice: don't define document node commands (ie. stay with the v2.x TclDOM API) or require explicit destruction of documents. At this stage my preference is for the latter. All comments are welcome, Steve Ball -- Steve Ball | XSLT Standard Library | Training & Seminars Zveno Pty Ltd | Web Tcl Complete | XML XSL Schemas http://www.zveno.com/ | TclXML TclDOM | Tcl, Web Development Ste...@zv... +---------------------------+--------------------- Ph. +61 2 6242 4099 | Mobile (0413) 594 462 | Fax +61 2 6242 4099 |
From: Joe E. <jen...@fl...> - 2003-06-29 19:28:57
|
Steve Ball wrote: > > I've been working on TclXML v3.0 and trying to incorporate > some new ideas on document and node management. In particular, > your request to have implicit document destruction has > been implemented. However, I'm now at the point where > I just cannot get it to work reliably. [... explanation deleted ...] > My conclusion is that object shimmering defeats any attempt > to have mutable objects automatically garbage collected. That's a correct conclusion. This sort of thing just isn't possible in Tcl. Of course some extensions do it anyway, but there is no way to make it 100% reliable. > At this point there is a choice: don't define document node commands > (ie. stay with the v2.x TclDOM API) or require explicit > destruction of documents. At this stage my preference is for > the latter. Even if you don't define document node commands, there are still other opportunities for shimmering. ([eval] is probably the main one; there are many others.) It's possible, with great care, to write code that avoids shimmering altogether, but IMO that places too large a burden on application programmers. I'm strongly in agreement with Steve's preference for explicit destruction. --Joe English jen...@fl... |