Hi,

I've been trying this problem these days.
For now I've not yet reached to an answer, but this may be a hint :

gdb told me that the problem is about memory allocation,
especially a double-freeing problem.

Changing optyk's script like this :

div2.each do |child|
  #c = child.clone
  c = child.copy(false)
  div1.child_add(c)
  exit  # <--------- add this
end

causes

*** glibc detected *** ruby: double free or corruption (fasttop): 0x088b5db0 ***
======= Backtrace: =========
/lib/libc.so.6[0x4f2c0f5d]
/lib/libc.so.6(cfree+0x90)[0x4f2c45b0]
/usr/lib/libxml2.so.2(xmlFreeNode+0x14b)[0x4fa1ce8b]
./xml/libxml_so.so(ruby_xml_node2_free+0x5f)[0x4865ef]
/usr/lib/libruby.so.1.8(rb_gc_call_finalizer_at_exit+0xa7)[0x457f4a87]
/usr/lib/libruby.so.1.8[0x457dad07]
/usr/lib/libruby.so.1.8(ruby_cleanup+0xf9)[0x457e2ad9]
/usr/lib/libruby.so.1.8(ruby_stop+0x1d)[0x457e2bbd]
/usr/lib/libruby.so.1.8[0x457edae1]
ruby[0x80485f2]
/lib/libc.so.6(__libc_start_main+0xdc)[0x4f270dec]
ruby[0x8048521]


Next, I found 'double-wrapping' in ruby_xml_node2_wrap().
It happened because xmlNode's member "_private"  was set to NULL by
xmlAddChild() function.
'_private' is used to store the xmlNode object's wrapper VALUE object
 (which is actually a Ruby object pointer).

you can see it by inserting following code in ruby_xml_node_child_set_aux()

  fprintf(stderr, "--- %p\n", chld->_private);
  ret = xmlAddChild(pnode->node, chld);
  fprintf(stderr, "--- %p\n", chld->_private);

==> (Run optyk's script)
--- 0xb7f8b9b8
--- (nil)

Just restoring '_private' value didn't fix the problem, but there may
be 'set-to-null problem'
elsewhere.
So, to conclude, I'm afraid it's not a good idea to store VALUE
pointer in '_private'.
libxml header file says its for internal use related to CORBA ... :-(

I'm glad if this could be a help for you, experts :-)

2007/11/27, optyk <[EMAIL PROTECTED]>:
> hello,
>
> I get segmentation fault when add the cloned/copied node to other
> node,
> script to problem reproduction below,
>
> segv appears when use clone and copy methods,
> what's interesting, with clone segv is thrown in div1.child_add(c)
> line (see script)
> but when use copy I get it in printf root statement, moreover copy
> seems to work wrong only for text nodes, when use 't3' div everything
> works fine
>
> I get this error on 0.5.2.0, 0.5.2.1 and 0.5.2.2 (latest svn) version
>
> it looks like fix is required in ruby-libxml code,
>
> BTW. it looks also like ruby_xml_node_copy() in ruby_xml_node.c calls
> xmlCopyNode() with wrong attributes, it should be 2 for shallow copy
> and 1 for deep copy
>
> regards,
> Piotrek
>
> -------------------- SCRIPT ---------------------
> require 'xml/libxml'
>
> str = <<-STR
> <html>
>     <body>
>         <div class="textarea" id="t1"
> style="STATIC">werwerwerwerwer                 </div>
>         <div class="textarea" id="t2" style="STATIC">
>             Quisque et diam dapibus nisi bibendum blandit.
>         </div>
>         <div class="textarea" id="t3" style="STATIC">
>             <p>aaaaaaaaa</p>
>         </div>
>     </body>
> </html>
> STR
>
>
> XML::Parser.default_keep_blanks = false
> xp = XML::Parser.new
> xp.string = str
> doc = xp.parse
>
> xpath = "//[EMAIL PROTECTED]'t1']"
> div1 = doc.find(xpath).to_a[0]
> printf "xxx div1: #{div1}\n"
>
> xpath = "//[EMAIL PROTECTED]'t2']"
> div2 = doc.find(xpath).to_a[0]
> printf "xxx div2: #{div2}\n"
>
>
> div2.each do |child|
>     #c = child.clone
>     c = child.copy(false)
>     div1.child_add(c)
> end
>
> printf "xxx root: #{doc.root}\n"
>
>
> _______________________________________________
> libxml-devel mailing list
> libxml-devel@rubyforge.org
> http://rubyforge.org/mailman/listinfo/libxml-devel
>


-- 
FUKUDA, Keisuke <福田圭祐>
http://d.hatena.ne.jp/keisukefukuda/
_______________________________________________
libxml-devel mailing list
libxml-devel@rubyforge.org
http://rubyforge.org/mailman/listinfo/libxml-devel

Reply via email to