nokogiri 1.6.7.2-x86-mingw32 → 1.6.8.rc1-x86-mingw32
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of nokogiri might be problematic. Click here for more details.
- checksums.yaml +4 -4
 - data/.travis.yml +12 -9
 - data/CHANGELOG.ja.rdoc +18 -0
 - data/CHANGELOG.rdoc +12 -7
 - data/CONTRIBUTING.md +42 -0
 - data/Gemfile +1 -1
 - data/Manifest.txt +6 -0
 - data/README.md +1 -1
 - data/Rakefile +1 -1
 - data/bin/nokogiri +2 -2
 - data/dependencies.yml +1 -1
 - data/ext/nokogiri/extconf.rb +3 -3
 - data/ext/nokogiri/nokogiri.c +0 -7
 - data/ext/nokogiri/nokogiri.h +1 -34
 - data/ext/nokogiri/xml_document.c +2 -4
 - data/ext/nokogiri/xml_namespace.c +56 -17
 - data/ext/nokogiri/xml_node.c +12 -36
 - data/ext/nokogiri/xml_node_set.c +169 -143
 - data/ext/nokogiri/xml_node_set.h +3 -4
 - data/ext/nokogiri/xml_sax_parser.c +2 -5
 - data/ext/nokogiri/xml_syntax_error.c +0 -4
 - data/ext/nokogiri/xml_syntax_error.h +0 -1
 - data/ext/nokogiri/xml_xpath_context.c +9 -18
 - data/lib/nokogiri.rb +3 -0
 - data/lib/nokogiri/1.9/nokogiri.so +0 -0
 - data/lib/nokogiri/2.0/nokogiri.so +0 -0
 - data/lib/nokogiri/2.1/nokogiri.so +0 -0
 - data/lib/nokogiri/2.2/nokogiri.so +0 -0
 - data/lib/nokogiri/css/parser.rb +8 -2
 - data/lib/nokogiri/css/parser.y +7 -2
 - data/lib/nokogiri/version.rb +1 -1
 - data/lib/nokogiri/xml/document.rb +7 -1
 - data/lib/nokogiri/xml/dtd.rb +4 -4
 - data/lib/nokogiri/xml/node.rb +2 -2
 - data/test/css/test_parser.rb +7 -1
 - data/test/files/GH_1042.html +18 -0
 - data/test/files/namespace_pressure_test.xml +1684 -0
 - data/test/files/tlm.html +2 -1
 - data/test/html/sax/test_parser.rb +2 -2
 - data/test/html/test_document.rb +18 -8
 - data/test/html/test_document_encoding.rb +46 -54
 - data/test/html/test_document_fragment.rb +21 -22
 - data/test/html/test_node.rb +16 -0
 - data/test/html/test_node_encoding.rb +12 -14
 - data/test/namespaces/test_namespaces_in_parsed_doc.rb +14 -0
 - data/test/test_reader.rb +19 -0
 - data/test/test_xslt_transforms.rb +5 -3
 - data/test/xml/sax/test_parser.rb +36 -39
 - data/test/xml/test_document.rb +7 -2
 - data/test/xml/test_document_encoding.rb +14 -16
 - data/test/xml/test_dtd_encoding.rb +0 -2
 - data/test/xml/test_node_encoding.rb +78 -80
 - data/test/xml/test_reader_encoding.rb +100 -102
 - data/test/xslt/test_exception_handling.rb +1 -1
 - metadata +11 -7
 
    
        data/ext/nokogiri/xml_node.c
    CHANGED
    
    | 
         @@ -234,15 +234,7 @@ ok: 
     | 
|
| 
       234 
234 
     | 
    
         
             
                 *  reparent the actual reparentee, so we reparent a duplicate.
         
     | 
| 
       235 
235 
     | 
    
         
             
                 */
         
     | 
| 
       236 
236 
     | 
    
         
             
                nokogiri_root_node(reparentee);
         
     | 
| 
       237 
     | 
    
         
            -
             
     | 
| 
       238 
     | 
    
         
            -
                xmlResetLastError();
         
     | 
| 
       239 
     | 
    
         
            -
                xmlSetStructuredErrorFunc((void *)rb_iv_get(DOC_RUBY_OBJECT(pivot->doc), "@errors"), Nokogiri_error_array_pusher);
         
     | 
| 
       240 
     | 
    
         
            -
             
     | 
| 
       241 
     | 
    
         
            -
                reparentee = xmlDocCopyNode(reparentee, pivot->doc, 1) ;
         
     | 
| 
       242 
     | 
    
         
            -
             
     | 
| 
       243 
     | 
    
         
            -
                xmlSetStructuredErrorFunc(NULL, NULL);
         
     | 
| 
       244 
     | 
    
         
            -
             
     | 
| 
       245 
     | 
    
         
            -
                if (! reparentee) {
         
     | 
| 
      
 237 
     | 
    
         
            +
                if (!(reparentee = xmlDocCopyNode(reparentee, pivot->doc, 1))) {
         
     | 
| 
       246 
238 
     | 
    
         
             
                  rb_raise(rb_eRuntimeError, "Could not reparent node (xmlDocCopyNode)");
         
     | 
| 
       247 
239 
     | 
    
         
             
                }
         
     | 
| 
       248 
240 
     | 
    
         
             
              }
         
     | 
| 
         @@ -481,13 +473,7 @@ static VALUE duplicate_node(int argc, VALUE *argv, VALUE self) 
     | 
|
| 
       481 
473 
     | 
    
         | 
| 
       482 
474 
     | 
    
         
             
              Data_Get_Struct(self, xmlNode, node);
         
     | 
| 
       483 
475 
     | 
    
         | 
| 
       484 
     | 
    
         
            -
              xmlResetLastError();
         
     | 
| 
       485 
     | 
    
         
            -
              xmlSetStructuredErrorFunc(NULL, Nokogiri_error_silencer);
         
     | 
| 
       486 
     | 
    
         
            -
             
     | 
| 
       487 
476 
     | 
    
         
             
              dup = xmlDocCopyNode(node, node->doc, (int)NUM2INT(level));
         
     | 
| 
       488 
     | 
    
         
            -
             
     | 
| 
       489 
     | 
    
         
            -
              xmlSetStructuredErrorFunc(NULL, NULL);
         
     | 
| 
       490 
     | 
    
         
            -
             
     | 
| 
       491 
477 
     | 
    
         
             
              if(dup == NULL) return Qnil;
         
     | 
| 
       492 
478 
     | 
    
         | 
| 
       493 
479 
     | 
    
         
             
              nokogiri_root_node(dup);
         
     | 
| 
         @@ -778,19 +764,11 @@ static VALUE namespaced_key_eh(VALUE self, VALUE attribute, VALUE namespace) 
     | 
|
| 
       778 
764 
     | 
    
         
             
             *
         
     | 
| 
       779 
765 
     | 
    
         
             
             * Set the +property+ to +value+
         
     | 
| 
       780 
766 
     | 
    
         
             
             */
         
     | 
| 
       781 
     | 
    
         
            -
            static VALUE set(VALUE  
     | 
| 
      
 767 
     | 
    
         
            +
            static VALUE set(VALUE self, VALUE property, VALUE value)
         
     | 
| 
       782 
768 
     | 
    
         
             
            {
         
     | 
| 
       783 
769 
     | 
    
         
             
              xmlNodePtr node, cur;
         
     | 
| 
       784 
     | 
    
         
            -
               
     | 
| 
       785 
     | 
    
         
            -
               
     | 
| 
       786 
     | 
    
         
            -
             
     | 
| 
       787 
     | 
    
         
            -
              Data_Get_Struct(node_rb, xmlNode, node);
         
     | 
| 
       788 
     | 
    
         
            -
             
     | 
| 
       789 
     | 
    
         
            -
              if (node->type != XML_ELEMENT_NODE) {
         
     | 
| 
       790 
     | 
    
         
            -
                return(Qnil); // TODO: would raising an exception be more appropriate?
         
     | 
| 
       791 
     | 
    
         
            -
              }
         
     | 
| 
       792 
     | 
    
         
            -
             
     | 
| 
       793 
     | 
    
         
            -
              property_name = (xmlChar *)StringValuePtr(property_name_rb);
         
     | 
| 
      
 770 
     | 
    
         
            +
              xmlAttrPtr prop;
         
     | 
| 
      
 771 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNode, node);
         
     | 
| 
       794 
772 
     | 
    
         | 
| 
       795 
773 
     | 
    
         
             
              /* If a matching attribute node already exists, then xmlSetProp will destroy
         
     | 
| 
       796 
774 
     | 
    
         
             
               * the existing node's children. However, if Nokogiri has a node object
         
     | 
| 
         @@ -798,9 +776,11 @@ static VALUE set(VALUE node_rb, VALUE property_name_rb, VALUE property_value_rb) 
     | 
|
| 
       798 
776 
     | 
    
         
             
               *
         
     | 
| 
       799 
777 
     | 
    
         
             
               * We can avoid this by unlinking these nodes first.
         
     | 
| 
       800 
778 
     | 
    
         
             
               */
         
     | 
| 
       801 
     | 
    
         
            -
               
     | 
| 
       802 
     | 
    
         
            -
             
     | 
| 
       803 
     | 
    
         
            -
             
     | 
| 
      
 779 
     | 
    
         
            +
              if (node->type != XML_ELEMENT_NODE)
         
     | 
| 
      
 780 
     | 
    
         
            +
                return(Qnil);
         
     | 
| 
      
 781 
     | 
    
         
            +
              prop = xmlHasProp(node, (xmlChar *)StringValuePtr(property));
         
     | 
| 
      
 782 
     | 
    
         
            +
              if (prop && prop->children) {
         
     | 
| 
      
 783 
     | 
    
         
            +
                for (cur = prop->children; cur; cur = cur->next) {
         
     | 
| 
       804 
784 
     | 
    
         
             
                  if (cur->_private) {
         
     | 
| 
       805 
785 
     | 
    
         
             
                    nokogiri_root_node(cur);
         
     | 
| 
       806 
786 
     | 
    
         
             
                    xmlUnlinkNode(cur);
         
     | 
| 
         @@ -808,14 +788,10 @@ static VALUE set(VALUE node_rb, VALUE property_name_rb, VALUE property_value_rb) 
     | 
|
| 
       808 
788 
     | 
    
         
             
                }
         
     | 
| 
       809 
789 
     | 
    
         
             
              }
         
     | 
| 
       810 
790 
     | 
    
         | 
| 
       811 
     | 
    
         
            -
               
     | 
| 
       812 
     | 
    
         
            -
             
     | 
| 
       813 
     | 
    
         
            -
             
     | 
| 
       814 
     | 
    
         
            -
              xmlSetProp(node, property_name, (xmlChar *)StringValuePtr(property_value_rb));
         
     | 
| 
       815 
     | 
    
         
            -
             
     | 
| 
       816 
     | 
    
         
            -
              xmlSetStructuredErrorFunc(NULL, NULL);
         
     | 
| 
      
 791 
     | 
    
         
            +
              xmlSetProp(node, (xmlChar *)StringValuePtr(property),
         
     | 
| 
      
 792 
     | 
    
         
            +
                  (xmlChar *)StringValuePtr(value));
         
     | 
| 
       817 
793 
     | 
    
         | 
| 
       818 
     | 
    
         
            -
              return  
     | 
| 
      
 794 
     | 
    
         
            +
              return value;
         
     | 
| 
       819 
795 
     | 
    
         
             
            }
         
     | 
| 
       820 
796 
     | 
    
         | 
| 
       821 
797 
     | 
    
         
             
            /*
         
     | 
    
        data/ext/nokogiri/xml_node_set.c
    CHANGED
    
    | 
         @@ -1,62 +1,42 @@ 
     | 
|
| 
       1 
1 
     | 
    
         
             
            #include <xml_node_set.h>
         
     | 
| 
      
 2 
     | 
    
         
            +
            #include <xml_namespace.h>
         
     | 
| 
       2 
3 
     | 
    
         
             
            #include <libxml/xpathInternals.h>
         
     | 
| 
       3 
4 
     | 
    
         | 
| 
       4 
5 
     | 
    
         
             
            static ID decorate ;
         
     | 
| 
      
 6 
     | 
    
         
            +
            static void xpath_node_set_del(xmlNodeSetPtr cur, xmlNodePtr val);
         
     | 
| 
       5 
7 
     | 
    
         | 
| 
       6 
     | 
    
         
            -
             
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
            static void Check_Node_Set_Node_Type(VALUE node)
         
     | 
| 
       7 
10 
     | 
    
         
             
            {
         
     | 
| 
       8 
     | 
    
         
            -
              if ( 
     | 
| 
       9 
     | 
    
         
            -
             
     | 
| 
       10 
     | 
    
         
            -
             
     | 
| 
       11 
     | 
    
         
            -
             
     | 
| 
       12 
     | 
    
         
            -
              xmlFree(ns);
         
     | 
| 
       13 
     | 
    
         
            -
              return ST_CONTINUE;
         
     | 
| 
      
 11 
     | 
    
         
            +
              if (!(rb_obj_is_kind_of(node, cNokogiriXmlNode) ||
         
     | 
| 
      
 12 
     | 
    
         
            +
                    rb_obj_is_kind_of(node, cNokogiriXmlNamespace))) {
         
     | 
| 
      
 13 
     | 
    
         
            +
                rb_raise(rb_eArgError, "node must be a Nokogiri::XML::Node or Nokogiri::XML::Namespace");
         
     | 
| 
      
 14 
     | 
    
         
            +
              }
         
     | 
| 
       14 
15 
     | 
    
         
             
            }
         
     | 
| 
       15 
16 
     | 
    
         | 
| 
       16 
     | 
    
         
            -
             
     | 
| 
      
 17 
     | 
    
         
            +
             
     | 
| 
      
 18 
     | 
    
         
            +
            static void deallocate(xmlNodeSetPtr node_set)
         
     | 
| 
       17 
19 
     | 
    
         
             
            {
         
     | 
| 
       18 
20 
     | 
    
         
             
              /*
         
     | 
| 
       19 
     | 
    
         
            -
               *  xmlXPathFreeNodeSet() contains an implicit assumption that it is being
         
     | 
| 
       20 
     | 
    
         
            -
               *  called before any of its pointed-to nodes have been free()d. this
         
     | 
| 
       21 
     | 
    
         
            -
               *  assumption lies in the operation where it dereferences nodeTab pointers
         
     | 
| 
       22 
     | 
    
         
            -
               *  while searching for namespace nodes to free.
         
     | 
| 
       23 
     | 
    
         
            -
               *
         
     | 
| 
       24 
     | 
    
         
            -
               *  however, since Ruby's GC mechanism cannot guarantee the strict order in
         
     | 
| 
       25 
     | 
    
         
            -
               *  which ruby objects will be GC'd, nodes may be garbage collected before a
         
     | 
| 
       26 
     | 
    
         
            -
               *  nodeset containing pointers to those nodes. (this is true regardless of
         
     | 
| 
       27 
     | 
    
         
            -
               *  how we declare dependencies between objects with rb_gc_mark().)
         
     | 
| 
       28 
21 
     | 
    
         
             
               *
         
     | 
| 
       29 
     | 
    
         
            -
               *   
     | 
| 
       30 
     | 
    
         
            -
               *   
     | 
| 
      
 22 
     | 
    
         
            +
               *  since xpath queries return copies of the xmlNs structs,
         
     | 
| 
      
 23 
     | 
    
         
            +
               *  xmlXPathFreeNodeSet() frees those xmlNs structs that are in the
         
     | 
| 
      
 24 
     | 
    
         
            +
               *  NodeSet.
         
     | 
| 
       31 
25 
     | 
    
         
             
               *
         
     | 
| 
       32 
     | 
    
         
            -
               *   
     | 
| 
       33 
     | 
    
         
            -
               *   
     | 
| 
       34 
     | 
    
         
            -
               *  well as the NodeSet, without using the official xmlXPathFreeNodeSet().
         
     | 
| 
      
 26 
     | 
    
         
            +
               *  this is bad if someone is still trying to use the Namespace object wrapped
         
     | 
| 
      
 27 
     | 
    
         
            +
               *  around the xmlNs, so we need to avoid that.
         
     | 
| 
       35 
28 
     | 
    
         
             
               *
         
     | 
| 
       36 
     | 
    
         
            -
               *   
     | 
| 
       37 
     | 
    
         
            -
               *  single array, structs with different memory-ownership semantics. or more
         
     | 
| 
       38 
     | 
    
         
            -
               *  generally, a lesson about building an API in C/C++ that does not contain
         
     | 
| 
       39 
     | 
    
         
            -
               *  assumptions about the strict order in which memory will be released. hey,
         
     | 
| 
       40 
     | 
    
         
            -
               *  that sounds like a great idea for a blog post! get to it!
         
     | 
| 
      
 29 
     | 
    
         
            +
               *  here we reproduce xmlXPathFreeNodeSet() without the xmlNs logic.
         
     | 
| 
       41 
30 
     | 
    
         
             
               *
         
     | 
| 
       42 
     | 
    
         
            -
               *   
     | 
| 
      
 31 
     | 
    
         
            +
               *  this doesn't cause a leak because Namespace objects that are in an XPath
         
     | 
| 
      
 32 
     | 
    
         
            +
               *  query NodeSet are given their own lifecycle in
         
     | 
| 
      
 33 
     | 
    
         
            +
               *  Nokogiri_wrap_xml_namespace().
         
     | 
| 
       43 
34 
     | 
    
         
             
               */
         
     | 
| 
       44 
     | 
    
         
            -
              xmlNodeSetPtr node_set;
         
     | 
| 
       45 
     | 
    
         
            -
             
     | 
| 
       46 
     | 
    
         
            -
              node_set = tuple->node_set;
         
     | 
| 
       47 
     | 
    
         
            -
             
     | 
| 
       48 
     | 
    
         
            -
              if (!node_set)
         
     | 
| 
       49 
     | 
    
         
            -
                return;
         
     | 
| 
       50 
     | 
    
         
            -
             
     | 
| 
       51 
35 
     | 
    
         
             
              NOKOGIRI_DEBUG_START(node_set) ;
         
     | 
| 
       52 
     | 
    
         
            -
              st_foreach(tuple->namespaces, dealloc_namespace, 0);
         
     | 
| 
       53 
     | 
    
         
            -
             
     | 
| 
       54 
36 
     | 
    
         
             
              if (node_set->nodeTab != NULL)
         
     | 
| 
       55 
37 
     | 
    
         
             
                xmlFree(node_set->nodeTab);
         
     | 
| 
       56 
38 
     | 
    
         | 
| 
       57 
39 
     | 
    
         
             
              xmlFree(node_set);
         
     | 
| 
       58 
     | 
    
         
            -
              st_free_table(tuple->namespaces);
         
     | 
| 
       59 
     | 
    
         
            -
              free(tuple);
         
     | 
| 
       60 
40 
     | 
    
         
             
              NOKOGIRI_DEBUG_END(node_set) ;
         
     | 
| 
       61 
41 
     | 
    
         
             
            }
         
     | 
| 
       62 
42 
     | 
    
         | 
| 
         @@ -74,12 +54,12 @@ static VALUE allocate(VALUE klass) 
     | 
|
| 
       74 
54 
     | 
    
         
             
             */
         
     | 
| 
       75 
55 
     | 
    
         
             
            static VALUE duplicate(VALUE self)
         
     | 
| 
       76 
56 
     | 
    
         
             
            {
         
     | 
| 
       77 
     | 
    
         
            -
               
     | 
| 
      
 57 
     | 
    
         
            +
              xmlNodeSetPtr node_set;
         
     | 
| 
       78 
58 
     | 
    
         
             
              xmlNodeSetPtr dupl;
         
     | 
| 
       79 
59 
     | 
    
         | 
| 
       80 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
      
 60 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       81 
61 
     | 
    
         | 
| 
       82 
     | 
    
         
            -
              dupl = xmlXPathNodeSetMerge(NULL,  
     | 
| 
      
 62 
     | 
    
         
            +
              dupl = xmlXPathNodeSetMerge(NULL, node_set);
         
     | 
| 
       83 
63 
     | 
    
         | 
| 
       84 
64 
     | 
    
         
             
              return Nokogiri_wrap_xml_node_set(dupl, rb_iv_get(self, "@document"));
         
     | 
| 
       85 
65 
     | 
    
         
             
            }
         
     | 
| 
         @@ -92,10 +72,11 @@ static VALUE duplicate(VALUE self) 
     | 
|
| 
       92 
72 
     | 
    
         
             
             */
         
     | 
| 
       93 
73 
     | 
    
         
             
            static VALUE length(VALUE self)
         
     | 
| 
       94 
74 
     | 
    
         
             
            {
         
     | 
| 
       95 
     | 
    
         
            -
               
     | 
| 
       96 
     | 
    
         
            -
              Data_Get_Struct(self, nokogiriNodeSetTuple, tuple);
         
     | 
| 
      
 75 
     | 
    
         
            +
              xmlNodeSetPtr node_set;
         
     | 
| 
       97 
76 
     | 
    
         | 
| 
       98 
     | 
    
         
            -
               
     | 
| 
      
 77 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 78 
     | 
    
         
            +
             
     | 
| 
      
 79 
     | 
    
         
            +
              return node_set ? INT2NUM(node_set->nodeNr) : INT2NUM(0);
         
     | 
| 
       99 
80 
     | 
    
         
             
            }
         
     | 
| 
       100 
81 
     | 
    
         | 
| 
       101 
82 
     | 
    
         
             
            /*
         
     | 
| 
         @@ -106,15 +87,16 @@ static VALUE length(VALUE self) 
     | 
|
| 
       106 
87 
     | 
    
         
             
             */
         
     | 
| 
       107 
88 
     | 
    
         
             
            static VALUE push(VALUE self, VALUE rb_node)
         
     | 
| 
       108 
89 
     | 
    
         
             
            {
         
     | 
| 
       109 
     | 
    
         
            -
               
     | 
| 
      
 90 
     | 
    
         
            +
              xmlNodeSetPtr node_set;
         
     | 
| 
       110 
91 
     | 
    
         
             
              xmlNodePtr node;
         
     | 
| 
       111 
92 
     | 
    
         | 
| 
       112 
     | 
    
         
            -
               
     | 
| 
       113 
     | 
    
         
            -
                rb_raise(rb_eArgError, "node must be a Nokogiri::XML::Node or Nokogiri::XML::Namespace");
         
     | 
| 
      
 93 
     | 
    
         
            +
              Check_Node_Set_Node_Type(rb_node);
         
     | 
| 
       114 
94 
     | 
    
         | 
| 
       115 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
      
 95 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       116 
96 
     | 
    
         
             
              Data_Get_Struct(rb_node, xmlNode, node);
         
     | 
| 
       117 
     | 
    
         
            -
             
     | 
| 
      
 97 
     | 
    
         
            +
             
     | 
| 
      
 98 
     | 
    
         
            +
              xmlXPathNodeSetAdd(node_set, node);
         
     | 
| 
      
 99 
     | 
    
         
            +
             
     | 
| 
       118 
100 
     | 
    
         
             
              return self;
         
     | 
| 
       119 
101 
     | 
    
         
             
            }
         
     | 
| 
       120 
102 
     | 
    
         | 
| 
         @@ -128,29 +110,19 @@ static VALUE push(VALUE self, VALUE rb_node) 
     | 
|
| 
       128 
110 
     | 
    
         
             
            static VALUE
         
     | 
| 
       129 
111 
     | 
    
         
             
            delete(VALUE self, VALUE rb_node)
         
     | 
| 
       130 
112 
     | 
    
         
             
            {
         
     | 
| 
       131 
     | 
    
         
            -
             
     | 
| 
       132 
     | 
    
         
            -
             
     | 
| 
       133 
     | 
    
         
            -
             
     | 
| 
       134 
     | 
    
         
            -
             
     | 
| 
       135 
     | 
    
         
            -
             
     | 
| 
       136 
     | 
    
         
            -
             
     | 
| 
       137 
     | 
    
         
            -
             
     | 
| 
       138 
     | 
    
         
            -
             
     | 
| 
       139 
     | 
    
         
            -
             
     | 
| 
       140 
     | 
    
         
            -
                 
     | 
| 
       141 
     | 
    
         
            -
                 
     | 
| 
       142 
     | 
    
         
            -
             
     | 
| 
       143 
     | 
    
         
            -
             
     | 
| 
       144 
     | 
    
         
            -
            	for (i = 0; i < cur->nodeNr; i++)
         
     | 
| 
       145 
     | 
    
         
            -
            	    if (cur->nodeTab[i] == node) break;
         
     | 
| 
       146 
     | 
    
         
            -
             
     | 
| 
       147 
     | 
    
         
            -
            	cur->nodeNr--;
         
     | 
| 
       148 
     | 
    
         
            -
            	for (;i < cur->nodeNr;i++)
         
     | 
| 
       149 
     | 
    
         
            -
            	    cur->nodeTab[i] = cur->nodeTab[i + 1];
         
     | 
| 
       150 
     | 
    
         
            -
            	cur->nodeTab[cur->nodeNr] = NULL;
         
     | 
| 
       151 
     | 
    
         
            -
            	return rb_node;
         
     | 
| 
       152 
     | 
    
         
            -
                }
         
     | 
| 
       153 
     | 
    
         
            -
                return Qnil ;
         
     | 
| 
      
 113 
     | 
    
         
            +
              xmlNodeSetPtr node_set;
         
     | 
| 
      
 114 
     | 
    
         
            +
              xmlNodePtr node;
         
     | 
| 
      
 115 
     | 
    
         
            +
             
     | 
| 
      
 116 
     | 
    
         
            +
              Check_Node_Set_Node_Type(rb_node);
         
     | 
| 
      
 117 
     | 
    
         
            +
             
     | 
| 
      
 118 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 119 
     | 
    
         
            +
              Data_Get_Struct(rb_node, xmlNode, node);
         
     | 
| 
      
 120 
     | 
    
         
            +
             
     | 
| 
      
 121 
     | 
    
         
            +
              if (xmlXPathNodeSetContains(node_set, node)) {
         
     | 
| 
      
 122 
     | 
    
         
            +
                xpath_node_set_del(node_set, node);
         
     | 
| 
      
 123 
     | 
    
         
            +
                return rb_node;
         
     | 
| 
      
 124 
     | 
    
         
            +
              }
         
     | 
| 
      
 125 
     | 
    
         
            +
              return Qnil ;
         
     | 
| 
       154 
126 
     | 
    
         
             
            }
         
     | 
| 
       155 
127 
     | 
    
         | 
| 
       156 
128 
     | 
    
         | 
| 
         @@ -162,16 +134,16 @@ delete(VALUE self, VALUE rb_node) 
     | 
|
| 
       162 
134 
     | 
    
         
             
             */
         
     | 
| 
       163 
135 
     | 
    
         
             
            static VALUE intersection(VALUE self, VALUE rb_other)
         
     | 
| 
       164 
136 
     | 
    
         
             
            {
         
     | 
| 
       165 
     | 
    
         
            -
               
     | 
| 
      
 137 
     | 
    
         
            +
              xmlNodeSetPtr node_set, other ;
         
     | 
| 
       166 
138 
     | 
    
         
             
              xmlNodeSetPtr intersection;
         
     | 
| 
       167 
139 
     | 
    
         | 
| 
       168 
140 
     | 
    
         
             
              if(!rb_obj_is_kind_of(rb_other, cNokogiriXmlNodeSet))
         
     | 
| 
       169 
141 
     | 
    
         
             
                rb_raise(rb_eArgError, "node_set must be a Nokogiri::XML::NodeSet");
         
     | 
| 
       170 
142 
     | 
    
         | 
| 
       171 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       172 
     | 
    
         
            -
              Data_Get_Struct(rb_other,  
     | 
| 
      
 143 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 144 
     | 
    
         
            +
              Data_Get_Struct(rb_other, xmlNodeSet, other);
         
     | 
| 
       173 
145 
     | 
    
         | 
| 
       174 
     | 
    
         
            -
              intersection = xmlXPathIntersection( 
     | 
| 
      
 146 
     | 
    
         
            +
              intersection = xmlXPathIntersection(node_set, other);
         
     | 
| 
       175 
147 
     | 
    
         
             
              return Nokogiri_wrap_xml_node_set(intersection, rb_iv_get(self, "@document"));
         
     | 
| 
       176 
148 
     | 
    
         
             
            }
         
     | 
| 
       177 
149 
     | 
    
         | 
| 
         @@ -184,16 +156,15 @@ static VALUE intersection(VALUE self, VALUE rb_other) 
     | 
|
| 
       184 
156 
     | 
    
         
             
             */
         
     | 
| 
       185 
157 
     | 
    
         
             
            static VALUE include_eh(VALUE self, VALUE rb_node)
         
     | 
| 
       186 
158 
     | 
    
         
             
            {
         
     | 
| 
       187 
     | 
    
         
            -
               
     | 
| 
      
 159 
     | 
    
         
            +
              xmlNodeSetPtr node_set;
         
     | 
| 
       188 
160 
     | 
    
         
             
              xmlNodePtr node;
         
     | 
| 
       189 
161 
     | 
    
         | 
| 
       190 
     | 
    
         
            -
               
     | 
| 
       191 
     | 
    
         
            -
                rb_raise(rb_eArgError, "node must be a Nokogiri::XML::Node or Nokogiri::XML::Namespace");
         
     | 
| 
      
 162 
     | 
    
         
            +
              Check_Node_Set_Node_Type(rb_node);
         
     | 
| 
       192 
163 
     | 
    
         | 
| 
       193 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
      
 164 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       194 
165 
     | 
    
         
             
              Data_Get_Struct(rb_node, xmlNode, node);
         
     | 
| 
       195 
166 
     | 
    
         | 
| 
       196 
     | 
    
         
            -
              return (xmlXPathNodeSetContains( 
     | 
| 
      
 167 
     | 
    
         
            +
              return (xmlXPathNodeSetContains(node_set, node) ? Qtrue : Qfalse);
         
     | 
| 
       197 
168 
     | 
    
         
             
            }
         
     | 
| 
       198 
169 
     | 
    
         | 
| 
       199 
170 
     | 
    
         | 
| 
         @@ -206,17 +177,17 @@ static VALUE include_eh(VALUE self, VALUE rb_node) 
     | 
|
| 
       206 
177 
     | 
    
         
             
             */
         
     | 
| 
       207 
178 
     | 
    
         
             
            static VALUE set_union(VALUE self, VALUE rb_other)
         
     | 
| 
       208 
179 
     | 
    
         
             
            {
         
     | 
| 
       209 
     | 
    
         
            -
               
     | 
| 
      
 180 
     | 
    
         
            +
              xmlNodeSetPtr node_set, other;
         
     | 
| 
       210 
181 
     | 
    
         
             
              xmlNodeSetPtr new;
         
     | 
| 
       211 
182 
     | 
    
         | 
| 
       212 
183 
     | 
    
         
             
              if(!rb_obj_is_kind_of(rb_other, cNokogiriXmlNodeSet))
         
     | 
| 
       213 
184 
     | 
    
         
             
                rb_raise(rb_eArgError, "node_set must be a Nokogiri::XML::NodeSet");
         
     | 
| 
       214 
185 
     | 
    
         | 
| 
       215 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       216 
     | 
    
         
            -
              Data_Get_Struct(rb_other,  
     | 
| 
      
 186 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 187 
     | 
    
         
            +
              Data_Get_Struct(rb_other, xmlNodeSet, other);
         
     | 
| 
       217 
188 
     | 
    
         | 
| 
       218 
     | 
    
         
            -
              new = xmlXPathNodeSetMerge(NULL,  
     | 
| 
       219 
     | 
    
         
            -
              new = xmlXPathNodeSetMerge(new, other 
     | 
| 
      
 189 
     | 
    
         
            +
              new = xmlXPathNodeSetMerge(NULL, node_set);
         
     | 
| 
      
 190 
     | 
    
         
            +
              new = xmlXPathNodeSetMerge(new, other);
         
     | 
| 
       220 
191 
     | 
    
         | 
| 
       221 
192 
     | 
    
         
             
              return Nokogiri_wrap_xml_node_set(new, rb_iv_get(self, "@document"));
         
     | 
| 
       222 
193 
     | 
    
         
             
            }
         
     | 
| 
         @@ -230,19 +201,19 @@ static VALUE set_union(VALUE self, VALUE rb_other) 
     | 
|
| 
       230 
201 
     | 
    
         
             
             */
         
     | 
| 
       231 
202 
     | 
    
         
             
            static VALUE minus(VALUE self, VALUE rb_other)
         
     | 
| 
       232 
203 
     | 
    
         
             
            {
         
     | 
| 
       233 
     | 
    
         
            -
               
     | 
| 
      
 204 
     | 
    
         
            +
              xmlNodeSetPtr node_set, other;
         
     | 
| 
       234 
205 
     | 
    
         
             
              xmlNodeSetPtr new;
         
     | 
| 
       235 
206 
     | 
    
         
             
              int j ;
         
     | 
| 
       236 
207 
     | 
    
         | 
| 
       237 
208 
     | 
    
         
             
              if(!rb_obj_is_kind_of(rb_other, cNokogiriXmlNodeSet))
         
     | 
| 
       238 
209 
     | 
    
         
             
                rb_raise(rb_eArgError, "node_set must be a Nokogiri::XML::NodeSet");
         
     | 
| 
       239 
210 
     | 
    
         | 
| 
       240 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       241 
     | 
    
         
            -
              Data_Get_Struct(rb_other,  
     | 
| 
      
 211 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 212 
     | 
    
         
            +
              Data_Get_Struct(rb_other, xmlNodeSet, other);
         
     | 
| 
       242 
213 
     | 
    
         | 
| 
       243 
     | 
    
         
            -
              new = xmlXPathNodeSetMerge(NULL,  
     | 
| 
       244 
     | 
    
         
            -
              for (j = 0 ; j < other-> 
     | 
| 
       245 
     | 
    
         
            -
                 
     | 
| 
      
 214 
     | 
    
         
            +
              new = xmlXPathNodeSetMerge(NULL, node_set);
         
     | 
| 
      
 215 
     | 
    
         
            +
              for (j = 0 ; j < other->nodeNr ; ++j) {
         
     | 
| 
      
 216 
     | 
    
         
            +
                xpath_node_set_del(new, other->nodeTab[j]);
         
     | 
| 
       246 
217 
     | 
    
         
             
              }
         
     | 
| 
       247 
218 
     | 
    
         | 
| 
       248 
219 
     | 
    
         
             
              return Nokogiri_wrap_xml_node_set(new, rb_iv_get(self, "@document"));
         
     | 
| 
         @@ -252,31 +223,25 @@ static VALUE minus(VALUE self, VALUE rb_other) 
     | 
|
| 
       252 
223 
     | 
    
         
             
            static VALUE index_at(VALUE self, long offset)
         
     | 
| 
       253 
224 
     | 
    
         
             
            {
         
     | 
| 
       254 
225 
     | 
    
         
             
              xmlNodeSetPtr node_set;
         
     | 
| 
       255 
     | 
    
         
            -
              nokogiriNodeSetTuple *tuple;
         
     | 
| 
       256 
226 
     | 
    
         | 
| 
       257 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       258 
     | 
    
         
            -
              node_set = tuple->node_set;
         
     | 
| 
      
 227 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       259 
228 
     | 
    
         | 
| 
       260 
     | 
    
         
            -
              if (offset >= node_set->nodeNr || abs((int)offset) > node_set->nodeNr)
         
     | 
| 
      
 229 
     | 
    
         
            +
              if (offset >= node_set->nodeNr || abs((int)offset) > node_set->nodeNr) {
         
     | 
| 
       261 
230 
     | 
    
         
             
                return Qnil;
         
     | 
| 
      
 231 
     | 
    
         
            +
              }
         
     | 
| 
       262 
232 
     | 
    
         | 
| 
       263 
     | 
    
         
            -
              if (offset < 0)
         
     | 
| 
       264 
     | 
    
         
            -
                offset += node_set->nodeNr;
         
     | 
| 
      
 233 
     | 
    
         
            +
              if (offset < 0) { offset += node_set->nodeNr ; }
         
     | 
| 
       265 
234 
     | 
    
         | 
| 
       266 
     | 
    
         
            -
               
     | 
| 
       267 
     | 
    
         
            -
                return Nokogiri_wrap_xml_namespace2(rb_iv_get(self, "@document"), (xmlNsPtr)(node_set->nodeTab[offset]));
         
     | 
| 
       268 
     | 
    
         
            -
              return Nokogiri_wrap_xml_node(Qnil, node_set->nodeTab[offset]);
         
     | 
| 
      
 235 
     | 
    
         
            +
              return Nokogiri_wrap_xml_node_set_node(node_set->nodeTab[offset], self);
         
     | 
| 
       269 
236 
     | 
    
         
             
            }
         
     | 
| 
       270 
237 
     | 
    
         | 
| 
       271 
238 
     | 
    
         
             
            static VALUE subseq(VALUE self, long beg, long len)
         
     | 
| 
       272 
239 
     | 
    
         
             
            {
         
     | 
| 
       273 
240 
     | 
    
         
             
              long j;
         
     | 
| 
       274 
     | 
    
         
            -
              nokogiriNodeSetTuple *tuple;
         
     | 
| 
       275 
241 
     | 
    
         
             
              xmlNodeSetPtr node_set;
         
     | 
| 
       276 
242 
     | 
    
         
             
              xmlNodeSetPtr new_set ;
         
     | 
| 
       277 
243 
     | 
    
         | 
| 
       278 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       279 
     | 
    
         
            -
              node_set = tuple->node_set;
         
     | 
| 
      
 244 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       280 
245 
     | 
    
         | 
| 
       281 
246 
     | 
    
         
             
              if (beg > node_set->nodeNr) return Qnil ;
         
     | 
| 
       282 
247 
     | 
    
         
             
              if (beg < 0 || len < 0) return Qnil ;
         
     | 
| 
         @@ -312,9 +277,8 @@ static VALUE slice(int argc, VALUE *argv, VALUE self) 
     | 
|
| 
       312 
277 
     | 
    
         
             
              VALUE arg ;
         
     | 
| 
       313 
278 
     | 
    
         
             
              long beg, len ;
         
     | 
| 
       314 
279 
     | 
    
         
             
              xmlNodeSetPtr node_set;
         
     | 
| 
       315 
     | 
    
         
            -
             
     | 
| 
       316 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       317 
     | 
    
         
            -
              node_set = tuple->node_set;
         
     | 
| 
      
 280 
     | 
    
         
            +
             
     | 
| 
      
 281 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       318 
282 
     | 
    
         | 
| 
       319 
283 
     | 
    
         
             
              if (argc == 2) {
         
     | 
| 
       320 
284 
     | 
    
         
             
                beg = NUM2LONG(argv[0]);
         
     | 
| 
         @@ -333,7 +297,7 @@ static VALUE slice(int argc, VALUE *argv, VALUE self) 
     | 
|
| 
       333 
297 
     | 
    
         
             
              if (FIXNUM_P(arg)) {
         
     | 
| 
       334 
298 
     | 
    
         
             
                return index_at(self, FIX2LONG(arg));
         
     | 
| 
       335 
299 
     | 
    
         
             
              }
         
     | 
| 
       336 
     | 
    
         
            -
             
     | 
| 
      
 300 
     | 
    
         
            +
             
     | 
| 
       337 
301 
     | 
    
         
             
              /* if arg is Range */
         
     | 
| 
       338 
302 
     | 
    
         
             
              switch (rb_range_beg_len(arg, &beg, &len, (long)node_set->nodeNr, 0)) {
         
     | 
| 
       339 
303 
     | 
    
         
             
              case Qfalse:
         
     | 
| 
         @@ -356,26 +320,25 @@ static VALUE slice(int argc, VALUE *argv, VALUE self) 
     | 
|
| 
       356 
320 
     | 
    
         
             
             */
         
     | 
| 
       357 
321 
     | 
    
         
             
            static VALUE to_array(VALUE self, VALUE rb_node)
         
     | 
| 
       358 
322 
     | 
    
         
             
            {
         
     | 
| 
       359 
     | 
    
         
            -
              xmlNodeSetPtr  
     | 
| 
      
 323 
     | 
    
         
            +
              xmlNodeSetPtr node_set ;
         
     | 
| 
       360 
324 
     | 
    
         
             
              VALUE *elts;
         
     | 
| 
       361 
325 
     | 
    
         
             
              VALUE list;
         
     | 
| 
       362 
326 
     | 
    
         
             
              int i;
         
     | 
| 
       363 
     | 
    
         
            -
              nokogiriNodeSetTuple *tuple;
         
     | 
| 
       364 
327 
     | 
    
         | 
| 
       365 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       366 
     | 
    
         
            -
              set = tuple->node_set;
         
     | 
| 
      
 328 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
       367 
329 
     | 
    
         | 
| 
       368 
     | 
    
         
            -
              elts = calloc((size_t) 
     | 
| 
       369 
     | 
    
         
            -
              for(i = 0; i <  
     | 
| 
       370 
     | 
    
         
            -
                 
     | 
| 
       371 
     | 
    
         
            -
             
     | 
| 
       372 
     | 
    
         
            -
                else
         
     | 
| 
       373 
     | 
    
         
            -
                  elts[i] = Nokogiri_wrap_xml_node(Qnil, set->nodeTab[i]);
         
     | 
| 
      
 330 
     | 
    
         
            +
              elts = (VALUE *)calloc((size_t)(node_set->nodeNr), sizeof(VALUE));
         
     | 
| 
      
 331 
     | 
    
         
            +
              for(i = 0; i < node_set->nodeNr; i++) {
         
     | 
| 
      
 332 
     | 
    
         
            +
                elts[i] = Nokogiri_wrap_xml_node_set_node(node_set->nodeTab[i], self);
         
     | 
| 
      
 333 
     | 
    
         
            +
                rb_gc_register_address(&elts[i]);
         
     | 
| 
       374 
334 
     | 
    
         
             
              }
         
     | 
| 
       375 
335 
     | 
    
         | 
| 
       376 
     | 
    
         
            -
              list = rb_ary_new4((long) 
     | 
| 
      
 336 
     | 
    
         
            +
              list = rb_ary_new4((long)node_set->nodeNr, elts);
         
     | 
| 
       377 
337 
     | 
    
         | 
| 
       378 
     | 
    
         
            -
               
     | 
| 
      
 338 
     | 
    
         
            +
              for(i = 0; i < node_set->nodeNr; i++) {
         
     | 
| 
      
 339 
     | 
    
         
            +
                rb_gc_unregister_address(&elts[i]);
         
     | 
| 
      
 340 
     | 
    
         
            +
              }
         
     | 
| 
      
 341 
     | 
    
         
            +
              free(elts);
         
     | 
| 
       379 
342 
     | 
    
         | 
| 
       380 
343 
     | 
    
         
             
              return list;
         
     | 
| 
       381 
344 
     | 
    
         
             
            }
         
     | 
| 
         @@ -390,13 +353,12 @@ static VALUE unlink_nodeset(VALUE self) 
     | 
|
| 
       390 
353 
     | 
    
         
             
            {
         
     | 
| 
       391 
354 
     | 
    
         
             
              xmlNodeSetPtr node_set;
         
     | 
| 
       392 
355 
     | 
    
         
             
              int j, nodeNr ;
         
     | 
| 
       393 
     | 
    
         
            -
              nokogiriNodeSetTuple *tuple;
         
     | 
| 
       394 
356 
     | 
    
         | 
| 
       395 
     | 
    
         
            -
              Data_Get_Struct(self,  
     | 
| 
       396 
     | 
    
         
            -
             
     | 
| 
      
 357 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 358 
     | 
    
         
            +
             
     | 
| 
       397 
359 
     | 
    
         
             
              nodeNr = node_set->nodeNr ;
         
     | 
| 
       398 
360 
     | 
    
         
             
              for (j = 0 ; j < nodeNr ; j++) {
         
     | 
| 
       399 
     | 
    
         
            -
                if ( 
     | 
| 
      
 361 
     | 
    
         
            +
                if (! Nokogiri_namespace_eh(node_set->nodeTab[j])) {
         
     | 
| 
       400 
362 
     | 
    
         
             
                  VALUE node ;
         
     | 
| 
       401 
363 
     | 
    
         
             
                  xmlNodePtr node_ptr;
         
     | 
| 
       402 
364 
     | 
    
         
             
                  node = Nokogiri_wrap_xml_node(Qnil, node_set->nodeTab[j]);
         
     | 
| 
         @@ -408,39 +370,103 @@ static VALUE unlink_nodeset(VALUE self) 
     | 
|
| 
       408 
370 
     | 
    
         
             
              return self ;
         
     | 
| 
       409 
371 
     | 
    
         
             
            }
         
     | 
| 
       410 
372 
     | 
    
         | 
| 
      
 373 
     | 
    
         
            +
             
     | 
| 
      
 374 
     | 
    
         
            +
            static void reify_node_set_namespaces(VALUE self)
         
     | 
| 
      
 375 
     | 
    
         
            +
            {
         
     | 
| 
      
 376 
     | 
    
         
            +
              /*
         
     | 
| 
      
 377 
     | 
    
         
            +
               *  as mentioned in deallocate() above, xmlNs structs returned in an XPath
         
     | 
| 
      
 378 
     | 
    
         
            +
               *  NodeSet are duplicates, and we don't clean them up at deallocate() time.
         
     | 
| 
      
 379 
     | 
    
         
            +
               *
         
     | 
| 
      
 380 
     | 
    
         
            +
               *  as a result, we need to make sure the Ruby manages this memory. we do this
         
     | 
| 
      
 381 
     | 
    
         
            +
               *  by forcing the creation of a Ruby object wrapped around the xmlNs.
         
     | 
| 
      
 382 
     | 
    
         
            +
               *
         
     | 
| 
      
 383 
     | 
    
         
            +
               *  we also have to make sure that the NodeSet has a reference to the
         
     | 
| 
      
 384 
     | 
    
         
            +
               *  Namespace object, otherwise GC will kick in and the Namespace won't be
         
     | 
| 
      
 385 
     | 
    
         
            +
               *  marked.
         
     | 
| 
      
 386 
     | 
    
         
            +
               *
         
     | 
| 
      
 387 
     | 
    
         
            +
               *  we *could* do this safely with *all* the nodes in the NodeSet, but we only
         
     | 
| 
      
 388 
     | 
    
         
            +
               *  *need* to do it for xmlNs structs, and so you get the code we have here.
         
     | 
| 
      
 389 
     | 
    
         
            +
               */
         
     | 
| 
      
 390 
     | 
    
         
            +
              int j ;
         
     | 
| 
      
 391 
     | 
    
         
            +
              xmlNodeSetPtr node_set ;
         
     | 
| 
      
 392 
     | 
    
         
            +
              VALUE namespace_cache ;
         
     | 
| 
      
 393 
     | 
    
         
            +
             
     | 
| 
      
 394 
     | 
    
         
            +
              Data_Get_Struct(self, xmlNodeSet, node_set);
         
     | 
| 
      
 395 
     | 
    
         
            +
             
     | 
| 
      
 396 
     | 
    
         
            +
              namespace_cache = rb_iv_get(self, "@namespace_cache");
         
     | 
| 
      
 397 
     | 
    
         
            +
             
     | 
| 
      
 398 
     | 
    
         
            +
              for (j = 0 ; j < node_set->nodeNr ; j++) {
         
     | 
| 
      
 399 
     | 
    
         
            +
                if (Nokogiri_namespace_eh(node_set->nodeTab[j])) {
         
     | 
| 
      
 400 
     | 
    
         
            +
                  rb_ary_push(namespace_cache, Nokogiri_wrap_xml_node_set_node(node_set->nodeTab[j], self));
         
     | 
| 
      
 401 
     | 
    
         
            +
                }
         
     | 
| 
      
 402 
     | 
    
         
            +
              }
         
     | 
| 
      
 403 
     | 
    
         
            +
            }
         
     | 
| 
      
 404 
     | 
    
         
            +
             
     | 
| 
      
 405 
     | 
    
         
            +
             
     | 
| 
       411 
406 
     | 
    
         
             
            VALUE Nokogiri_wrap_xml_node_set(xmlNodeSetPtr node_set, VALUE document)
         
     | 
| 
       412 
407 
     | 
    
         
             
            {
         
     | 
| 
       413 
408 
     | 
    
         
             
              VALUE new_set ;
         
     | 
| 
       414 
     | 
    
         
            -
              int i;
         
     | 
| 
       415 
     | 
    
         
            -
              xmlNodePtr cur;
         
     | 
| 
       416 
     | 
    
         
            -
              xmlNsPtr ns;
         
     | 
| 
       417 
     | 
    
         
            -
              nokogiriNodeSetTuple *tuple;
         
     | 
| 
       418 
409 
     | 
    
         | 
| 
       419 
     | 
    
         
            -
               
     | 
| 
       420 
     | 
    
         
            -
             
     | 
| 
      
 410 
     | 
    
         
            +
              if (node_set == NULL) {
         
     | 
| 
      
 411 
     | 
    
         
            +
                node_set = xmlXPathNodeSetCreate(NULL);
         
     | 
| 
      
 412 
     | 
    
         
            +
              }
         
     | 
| 
       421 
413 
     | 
    
         | 
| 
       422 
     | 
    
         
            -
               
     | 
| 
       423 
     | 
    
         
            -
              tuple->namespaces = st_init_numtable();
         
     | 
| 
      
 414 
     | 
    
         
            +
              new_set = Data_Wrap_Struct(cNokogiriXmlNodeSet, 0, deallocate, node_set);
         
     | 
| 
       424 
415 
     | 
    
         | 
| 
       425 
416 
     | 
    
         
             
              if (!NIL_P(document)) {
         
     | 
| 
       426 
417 
     | 
    
         
             
                rb_iv_set(new_set, "@document", document);
         
     | 
| 
       427 
418 
     | 
    
         
             
                rb_funcall(document, decorate, 1, new_set);
         
     | 
| 
       428 
419 
     | 
    
         
             
              }
         
     | 
| 
       429 
420 
     | 
    
         | 
| 
       430 
     | 
    
         
            -
               
     | 
| 
       431 
     | 
    
         
            -
             
     | 
| 
       432 
     | 
    
         
            -
                  cur = node_set->nodeTab[i];
         
     | 
| 
       433 
     | 
    
         
            -
                  if (cur && cur->type == XML_NAMESPACE_DECL) {
         
     | 
| 
       434 
     | 
    
         
            -
                    ns = (xmlNsPtr)cur;
         
     | 
| 
       435 
     | 
    
         
            -
                    if (ns->next && ns->next->type != XML_NAMESPACE_DECL)
         
     | 
| 
       436 
     | 
    
         
            -
                      st_insert(tuple->namespaces, (st_data_t)cur, (st_data_t)0);
         
     | 
| 
       437 
     | 
    
         
            -
                  }
         
     | 
| 
       438 
     | 
    
         
            -
                }
         
     | 
| 
       439 
     | 
    
         
            -
              }
         
     | 
| 
      
 421 
     | 
    
         
            +
              rb_iv_set(new_set, "@namespace_cache", rb_ary_new());
         
     | 
| 
      
 422 
     | 
    
         
            +
              reify_node_set_namespaces(new_set);
         
     | 
| 
       440 
423 
     | 
    
         | 
| 
       441 
424 
     | 
    
         
             
              return new_set ;
         
     | 
| 
       442 
425 
     | 
    
         
             
            }
         
     | 
| 
       443 
426 
     | 
    
         | 
| 
      
 427 
     | 
    
         
            +
            VALUE Nokogiri_wrap_xml_node_set_node(xmlNodePtr node, VALUE node_set)
         
     | 
| 
      
 428 
     | 
    
         
            +
            {
         
     | 
| 
      
 429 
     | 
    
         
            +
              xmlDocPtr document ;
         
     | 
| 
      
 430 
     | 
    
         
            +
             
     | 
| 
      
 431 
     | 
    
         
            +
              if (Nokogiri_namespace_eh(node)) {
         
     | 
| 
      
 432 
     | 
    
         
            +
                Data_Get_Struct(rb_iv_get(node_set, "@document"), xmlDoc, document);
         
     | 
| 
      
 433 
     | 
    
         
            +
                return Nokogiri_wrap_xml_namespace(document, (xmlNsPtr)node);
         
     | 
| 
      
 434 
     | 
    
         
            +
              } else {
         
     | 
| 
      
 435 
     | 
    
         
            +
                return Nokogiri_wrap_xml_node(Qnil, node);
         
     | 
| 
      
 436 
     | 
    
         
            +
              }
         
     | 
| 
      
 437 
     | 
    
         
            +
            }
         
     | 
| 
      
 438 
     | 
    
         
            +
             
     | 
| 
      
 439 
     | 
    
         
            +
             
     | 
| 
      
 440 
     | 
    
         
            +
            static void xpath_node_set_del(xmlNodeSetPtr cur, xmlNodePtr val)
         
     | 
| 
      
 441 
     | 
    
         
            +
            {
         
     | 
| 
      
 442 
     | 
    
         
            +
              /*
         
     | 
| 
      
 443 
     | 
    
         
            +
               * as mentioned a few times above, we do not want to free xmlNs structs
         
     | 
| 
      
 444 
     | 
    
         
            +
               * outside of the Namespace lifecycle.
         
     | 
| 
      
 445 
     | 
    
         
            +
               *
         
     | 
| 
      
 446 
     | 
    
         
            +
               * xmlXPathNodeSetDel() frees xmlNs structs, and so here we reproduce that
         
     | 
| 
      
 447 
     | 
    
         
            +
               * function with the xmlNs logic.
         
     | 
| 
      
 448 
     | 
    
         
            +
               */
         
     | 
| 
      
 449 
     | 
    
         
            +
              int i;
         
     | 
| 
      
 450 
     | 
    
         
            +
             
     | 
| 
      
 451 
     | 
    
         
            +
              if (cur == NULL) return;
         
     | 
| 
      
 452 
     | 
    
         
            +
              if (val == NULL) return;
         
     | 
| 
      
 453 
     | 
    
         
            +
             
     | 
| 
      
 454 
     | 
    
         
            +
              /*
         
     | 
| 
      
 455 
     | 
    
         
            +
               * find node in nodeTab
         
     | 
| 
      
 456 
     | 
    
         
            +
               */
         
     | 
| 
      
 457 
     | 
    
         
            +
              for (i = 0;i < cur->nodeNr;i++)
         
     | 
| 
      
 458 
     | 
    
         
            +
                if (cur->nodeTab[i] == val) break;
         
     | 
| 
      
 459 
     | 
    
         
            +
             
     | 
| 
      
 460 
     | 
    
         
            +
              if (i >= cur->nodeNr) {	/* not found */
         
     | 
| 
      
 461 
     | 
    
         
            +
                return;
         
     | 
| 
      
 462 
     | 
    
         
            +
              }
         
     | 
| 
      
 463 
     | 
    
         
            +
              cur->nodeNr--;
         
     | 
| 
      
 464 
     | 
    
         
            +
              for (;i < cur->nodeNr;i++)
         
     | 
| 
      
 465 
     | 
    
         
            +
                cur->nodeTab[i] = cur->nodeTab[i + 1];
         
     | 
| 
      
 466 
     | 
    
         
            +
              cur->nodeTab[cur->nodeNr] = NULL;
         
     | 
| 
      
 467 
     | 
    
         
            +
            }
         
     | 
| 
      
 468 
     | 
    
         
            +
             
     | 
| 
      
 469 
     | 
    
         
            +
             
     | 
| 
       444 
470 
     | 
    
         
             
            VALUE cNokogiriXmlNodeSet ;
         
     | 
| 
       445 
471 
     | 
    
         
             
            void init_xml_node_set(void)
         
     | 
| 
       446 
472 
     | 
    
         
             
            {
         
     |