1/////////////////////////////////////////////////////////////////////////// 2// 3// Copyright (c) 2000-2003 Intel Corporation 4// All rights reserved. 5// 6// Redistribution and use in source and binary forms, with or without 7// modification, are permitted provided that the following conditions are met: 8// 9// * Redistributions of source code must retain the above copyright notice, 10// this list of conditions and the following disclaimer. 11// * Redistributions in binary form must reproduce the above copyright notice, 12// this list of conditions and the following disclaimer in the documentation 13// and/or other materials provided with the distribution. 14// * Neither name of Intel Corporation nor the names of its contributors 15// may be used to endorse or promote products derived from this software 16// without specific prior written permission. 17// 18// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 19// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 20// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 21// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR 22// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 23// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 24// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 25// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 26// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 27// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 28// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29// 30/////////////////////////////////////////////////////////////////////////// 31 32#include "ixmlparser.h" 33 34/*================================================================ 35* ixmlNode_init 36* Intializes a node. 37* External function. 38* 39*=================================================================*/ 40void 41ixmlNode_init( IN IXML_Node * nodeptr ) 42{ 43 assert( nodeptr != NULL ); 44 memset( nodeptr, 0, sizeof( IXML_Node ) ); 45 46} 47 48/*================================================================ 49* ixmlCDATASection_init 50* Initializes a CDATASection node. 51* External function. 52* 53*=================================================================*/ 54void 55ixmlCDATASection_init( IN IXML_CDATASection * nodeptr ) 56{ 57 memset( nodeptr, 0, sizeof( IXML_CDATASection ) ); 58} 59 60/*================================================================ 61* ixmlCDATASection_free 62* frees a CDATASection node. 63* External function. 64* 65*=================================================================*/ 66void 67ixmlCDATASection_free( IN IXML_CDATASection * nodeptr ) 68{ 69 if( nodeptr != NULL ) { 70 ixmlNode_free( ( IXML_Node * ) nodeptr ); 71 } 72} 73 74/*================================================================ 75* ixmlNode_freeSingleNode 76* frees a node content. 77* Internal to parser only. 78* 79*=================================================================*/ 80void 81ixmlNode_freeSingleNode( IN IXML_Node * nodeptr ) 82{ 83 IXML_Element *element = NULL; 84 85 if( nodeptr != NULL ) { 86 if( nodeptr->nodeName != NULL ) { 87 free( nodeptr->nodeName ); 88 } 89 90 if( nodeptr->nodeValue != NULL ) { 91 free( nodeptr->nodeValue ); 92 } 93 94 if( nodeptr->namespaceURI != NULL ) { 95 free( nodeptr->namespaceURI ); 96 } 97 98 if( nodeptr->prefix != NULL ) { 99 free( nodeptr->prefix ); 100 } 101 102 if( nodeptr->localName != NULL ) { 103 free( nodeptr->localName ); 104 } 105 106 if( nodeptr->nodeType == eELEMENT_NODE ) { 107 element = ( IXML_Element * ) nodeptr; 108 free( element->tagName ); 109 } 110 111 free( nodeptr ); 112 113 } 114} 115 116/*================================================================ 117* ixmlNode_free 118* Frees all nodes under nodeptr subtree. 119* External function. 120* 121*=================================================================*/ 122void 123ixmlNode_free( IN IXML_Node * nodeptr ) 124{ 125 if( nodeptr != NULL ) { 126 ixmlNode_free( nodeptr->firstChild ); 127 ixmlNode_free( nodeptr->nextSibling ); 128 ixmlNode_free( nodeptr->firstAttr ); 129 130 ixmlNode_freeSingleNode( nodeptr ); 131 } 132} 133 134/*================================================================ 135* ixmlNode_getNodeName 136* Returns the nodename(the qualified name) 137* External function. 138* 139*=================================================================*/ 140const DOMString 141ixmlNode_getNodeName( IN IXML_Node * nodeptr ) 142{ 143 144 if( nodeptr != NULL ) { 145 return ( nodeptr->nodeName ); 146 } 147 148 return NULL; 149} 150 151/*================================================================ 152* ixmlNode_getLocalName 153* Returns the node local name 154* External function. 155* 156*=================================================================*/ 157const DOMString 158ixmlNode_getLocalName( IN IXML_Node * nodeptr ) 159{ 160 161 if( nodeptr != NULL ) { 162 return ( nodeptr->localName ); 163 } 164 165 return NULL; 166} 167 168/*================================================================ 169* ixmlNode_setNamespaceURI 170* sets the namespace URI of the node. 171* Internal function. 172* Return: 173* IXML_SUCCESS or failure 174* 175*=================================================================*/ 176int 177ixmlNode_setNamespaceURI( IN IXML_Node * nodeptr, 178 IN char *namespaceURI ) 179{ 180 181 if( nodeptr == NULL ) { 182 return IXML_INVALID_PARAMETER; 183 } 184 185 if( nodeptr->namespaceURI != NULL ) { 186 free( nodeptr->namespaceURI ); 187 nodeptr->namespaceURI = NULL; 188 } 189 190 if( namespaceURI != NULL ) { 191 nodeptr->namespaceURI = strdup( namespaceURI ); 192 if( nodeptr->namespaceURI == NULL ) { 193 return IXML_INSUFFICIENT_MEMORY; 194 } 195 } 196 197 return IXML_SUCCESS; 198} 199 200/*================================================================ 201* ixmlNode_setPrefix 202* set the prefix of the node. 203* Internal to parser only. 204* Returns: 205* IXML_SUCCESS or failure. 206* 207*=================================================================*/ 208int 209ixmlNode_setPrefix( IN IXML_Node * nodeptr, 210 IN char *prefix ) 211{ 212 213 if( nodeptr == NULL ) { 214 return IXML_INVALID_PARAMETER; 215 } 216 217 if( nodeptr->prefix != NULL ) { 218 free( nodeptr->prefix ); 219 nodeptr->prefix = NULL; 220 } 221 222 if( prefix != NULL ) { 223 nodeptr->prefix = strdup( prefix ); 224 if( nodeptr->prefix == NULL ) { 225 return IXML_INSUFFICIENT_MEMORY; 226 } 227 } 228 229 return IXML_SUCCESS; 230 231} 232 233/*================================================================ 234* ixmlNode_setLocalName 235* set the localName of the node. 236* Internal to parser only. 237* Returns: 238* IXML_SUCCESS or failure. 239* 240*=================================================================*/ 241int 242ixmlNode_setLocalName( IN IXML_Node * nodeptr, 243 IN char *localName ) 244{ 245 246 assert( nodeptr != NULL ); 247 248 if( nodeptr->localName != NULL ) { 249 free( nodeptr->localName ); 250 nodeptr->localName = NULL; 251 } 252 253 if( localName != NULL ) { 254 nodeptr->localName = strdup( localName ); 255 if( nodeptr->localName == NULL ) { 256 return IXML_INSUFFICIENT_MEMORY; 257 } 258 } 259 260 return IXML_SUCCESS; 261} 262 263/*================================================================ 264* ixmlNode_getNodeNamespaceURI 265* Returns the node namespaceURI 266* External function. 267* Returns: 268* the namespaceURI of the node 269* 270*=================================================================*/ 271const DOMString 272ixmlNode_getNamespaceURI( IN IXML_Node * nodeptr ) 273{ 274 DOMString retNamespaceURI = NULL; 275 276 if( nodeptr != NULL ) { 277 retNamespaceURI = nodeptr->namespaceURI; 278 } 279 280 return retNamespaceURI; 281} 282 283/*================================================================ 284* ixmlNode_getPrefix 285* Returns the node prefix 286* External function. 287* Returns: 288* the prefix of the node. 289* 290*=================================================================*/ 291DOMString 292ixmlNode_getPrefix( IN IXML_Node * nodeptr ) 293{ 294 DOMString prefix = NULL; 295 296 if( nodeptr != NULL ) { 297 prefix = nodeptr->prefix; 298 } 299 300 return prefix; 301 302} 303 304/*================================================================ 305* ixmlNode_getNodeValue 306* Returns the nodeValue of this node 307* External function. 308* Return: 309* the nodeValue of the node. 310* 311*=================================================================*/ 312DOMString 313ixmlNode_getNodeValue( IN IXML_Node * nodeptr ) 314{ 315 316 if( nodeptr != NULL ) { 317 return ( nodeptr->nodeValue ); 318 } 319 320 return NULL; 321} 322 323/*================================================================ 324* ixmlNode_setNodeValue 325* Sets the nodeValue 326* Internal function. 327* Returns: 328* IXML_SUCCESS or failure 329* 330*=================================================================*/ 331int 332ixmlNode_setNodeValue( IN IXML_Node * nodeptr, 333 IN char *newNodeValue ) 334{ 335 int rc = IXML_SUCCESS; 336 337 if( nodeptr == NULL ) { 338 return IXML_INVALID_PARAMETER; 339 } 340 341 if( nodeptr->nodeValue != NULL ) { 342 free( nodeptr->nodeValue ); 343 nodeptr->nodeValue = NULL; 344 } 345 346 if( newNodeValue != NULL ) { 347 nodeptr->nodeValue = strdup( newNodeValue ); 348 if( nodeptr->nodeValue == NULL ) { 349 return IXML_INSUFFICIENT_MEMORY; 350 } 351 } 352 353 return rc; 354} 355 356/*================================================================ 357* ixmlNode_getNodeType 358* Gets the NodeType of this node 359* External function. 360* 361*=================================================================*/ 362const unsigned short 363ixmlNode_getNodeType( IN IXML_Node * nodeptr ) 364{ 365 if( nodeptr != NULL ) { 366 return ( nodeptr->nodeType ); 367 } else { 368 return ( eINVALID_NODE ); 369 } 370} 371 372/*================================================================ 373* ixmlNode_getParentNode 374* Get the parent node 375* External function. 376* Return: 377* 378*=================================================================*/ 379IXML_Node * 380ixmlNode_getParentNode( IN IXML_Node * nodeptr ) 381{ 382 383 if( nodeptr != NULL ) { 384 return nodeptr->parentNode; 385 } else { 386 return NULL; 387 } 388} 389 390/*================================================================ 391* ixmlNode_getFirstChild 392* Returns the first child of nodeptr. 393* External function. 394* 395*=================================================================*/ 396IXML_Node * 397ixmlNode_getFirstChild( IN IXML_Node * nodeptr ) 398{ 399 if( nodeptr != NULL ) { 400 return nodeptr->firstChild; 401 } else { 402 return NULL; 403 } 404} 405 406/*================================================================ 407* ixmlNode_getLastChild 408* Returns the last child of nodeptr. 409* External function. 410* 411*=================================================================*/ 412IXML_Node * 413ixmlNode_getLastChild( IN IXML_Node * nodeptr ) 414{ 415 IXML_Node *prev, 416 *next; 417 418 if( nodeptr != NULL ) { 419 prev = nodeptr; 420 next = nodeptr->firstChild; 421 422 while( next != NULL ) { 423 prev = next; 424 next = next->nextSibling; 425 } 426 return prev; 427 } else { 428 return NULL; 429 } 430 431} 432 433/*================================================================ 434* ixmlNode_getPreviousSibling 435* returns the previous sibling node of nodeptr. 436* External function. 437* 438*=================================================================*/ 439IXML_Node * 440ixmlNode_getPreviousSibling( IN IXML_Node * nodeptr ) 441{ 442 if( nodeptr != NULL ) { 443 return nodeptr->prevSibling; 444 } else { 445 return NULL; 446 } 447} 448 449/*================================================================ 450* ixmlNode_getNextSibling 451* Returns the next sibling node. 452* External function. 453* 454*=================================================================*/ 455IXML_Node * 456ixmlNode_getNextSibling( IN IXML_Node * nodeptr ) 457{ 458 459 if( nodeptr != NULL ) { 460 return nodeptr->nextSibling; 461 } else { 462 return NULL; 463 } 464 465} 466 467/*================================================================ 468* ixmlNode_getOwnerDocument 469* Returns the owner document node. 470* External function. 471* 472*=================================================================*/ 473IXML_Document * 474ixmlNode_getOwnerDocument( IN IXML_Node * nodeptr ) 475{ 476 if( nodeptr != NULL ) { 477 return ( IXML_Document * ) nodeptr->ownerDocument; 478 } else { 479 return NULL; 480 } 481} 482 483/*================================================================ 484* ixmlNode_isAncestor 485* check if ancestorNode is ancestor of toFind 486* Internal to parser only. 487* Returns: 488* TRUE or FALSE 489* 490*=================================================================*/ 491BOOL 492ixmlNode_isAncestor( IXML_Node * ancestorNode, 493 IXML_Node * toFind ) 494{ 495 496 BOOL found = FALSE; 497 498 if( ( ancestorNode != NULL ) && ( toFind != NULL ) ) { 499 if( toFind->parentNode == ancestorNode ) { 500 return TRUE; 501 } else { 502 found = 503 ixmlNode_isAncestor( ancestorNode->firstChild, toFind ); 504 if( found == FALSE ) { 505 found = 506 ixmlNode_isAncestor( ancestorNode->nextSibling, 507 toFind ); 508 } 509 } 510 } 511 512 return found; 513} 514 515/*================================================================ 516* ixmlNode_isParent 517* Check whether toFind is a children of nodeptr. 518* Internal to parser only. 519* Return: 520* TRUE or FALSE 521* 522*=================================================================*/ 523BOOL 524ixmlNode_isParent( IXML_Node * nodeptr, 525 IXML_Node * toFind ) 526{ 527 BOOL found = FALSE; 528 529 assert( nodeptr != NULL && toFind != NULL ); 530 if( toFind->parentNode == nodeptr ) { 531 found = TRUE; 532 } 533 534 return found; 535} 536 537/*================================================================ 538* ixmlNode_allowChildren 539* Check to see whether nodeptr allows children of type newChild. 540* Internal to parser only. 541* Returns: 542* TRUE, if nodeptr can have newChild as children 543* FALSE,if nodeptr cannot have newChild as children 544* 545*=================================================================*/ 546BOOL 547ixmlNode_allowChildren( IXML_Node * nodeptr, 548 IXML_Node * newChild ) 549{ 550 551 assert( nodeptr != NULL && newChild != NULL ); 552 switch ( nodeptr->nodeType ) { 553 case eATTRIBUTE_NODE: 554 case eTEXT_NODE: 555 case eCDATA_SECTION_NODE: 556 return FALSE; 557 break; 558 559 case eELEMENT_NODE: 560 if( ( newChild->nodeType == eATTRIBUTE_NODE ) || 561 ( newChild->nodeType == eDOCUMENT_NODE ) ) { 562 return FALSE; 563 } 564 break; 565 566 case eDOCUMENT_NODE: 567 if( newChild->nodeType != eELEMENT_NODE ) { 568 return FALSE; 569 } 570 571 default: 572 break; 573 } 574 575 return TRUE; 576} 577 578/*================================================================ 579* ixmlNode_compare 580* Compare two nodes to see whether they are the same node. 581* Parent, sibling and children node are ignored. 582* Internal to parser only. 583* Returns: 584* TRUE, the two nodes are the same. 585* FALSE, the two nodes are not the same. 586* 587*=================================================================*/ 588BOOL 589ixmlNode_compare( IXML_Node * srcNode, 590 IXML_Node * destNode ) 591{ 592 assert( srcNode != NULL && destNode != NULL ); 593 if( ( srcNode == destNode ) || 594 ( strcmp( srcNode->nodeName, destNode->nodeName ) == 0 && 595 strcmp( srcNode->nodeValue, destNode->nodeValue ) == 0 && 596 ( srcNode->nodeType == destNode->nodeType ) && 597 strcmp( srcNode->namespaceURI, destNode->namespaceURI ) == 0 && 598 strcmp( srcNode->prefix, destNode->prefix ) == 0 && 599 strcmp( srcNode->localName, destNode->localName ) == 0 ) ) { 600 return TRUE; 601 } else { 602 return FALSE; 603 } 604} 605 606/*================================================================ 607* ixmlNode_insertBefore 608* Inserts the node newChild before the existing child node refChild. 609* If refChild is null, insert newChild at the end of the list of 610* children. If the newChild is already in the tree, it is first 611* removed. 612* External function. 613* Parameters: 614* newChild: the node to insert. 615* Returns: 616* 617*=================================================================*/ 618int 619ixmlNode_insertBefore( IN IXML_Node * nodeptr, 620 IN IXML_Node * newChild, 621 IN IXML_Node * refChild ) 622{ 623 624 int ret = IXML_SUCCESS; 625 626 if( ( nodeptr == NULL ) || ( newChild == NULL ) ) { 627 return IXML_INVALID_PARAMETER; 628 } 629 // whether nodeptr allow children of the type of newChild 630 if( ixmlNode_allowChildren( nodeptr, newChild ) == FALSE ) { 631 return IXML_HIERARCHY_REQUEST_ERR; 632 } 633 // or if newChild is one of nodeptr's ancestors 634 if( ixmlNode_isAncestor( newChild, nodeptr ) == TRUE ) { 635 return IXML_HIERARCHY_REQUEST_ERR; 636 } 637 // if newChild was created from a different document 638 if( nodeptr->ownerDocument != newChild->ownerDocument ) { 639 return IXML_WRONG_DOCUMENT_ERR; 640 } 641 // if refChild is not a child of nodeptr 642 if( ixmlNode_isParent( nodeptr, refChild ) == FALSE ) { 643 return IXML_NOT_FOUND_ERR; 644 } 645 646 if( refChild != NULL ) { 647 if( ixmlNode_isParent( nodeptr, newChild ) == TRUE ) { 648 ixmlNode_removeChild( nodeptr, newChild, NULL ); 649 newChild->nextSibling = NULL; 650 newChild->prevSibling = NULL; 651 } 652 653 newChild->nextSibling = refChild; 654 if( refChild->prevSibling != NULL ) { 655 ( refChild->prevSibling )->nextSibling = newChild; 656 newChild->prevSibling = refChild->prevSibling; 657 } 658 659 refChild->prevSibling = newChild; 660 661 if( newChild->prevSibling == NULL ) { 662 nodeptr->firstChild = newChild; 663 } 664 665 newChild->parentNode = nodeptr; 666 667 } else { 668 ret = ixmlNode_appendChild( nodeptr, newChild ); 669 } 670 671 return ret; 672} 673 674/*================================================================ 675* ixmlNode_replaceChild 676* Replaces the child node oldChild with newChild in the list of children, 677* and returns the oldChild node. 678* External function. 679* Parameters: 680* newChild: the new node to put in the child list. 681* oldChild: the node being replaced in the list. 682* returnNode: the node replaced. 683* Return Value: 684* IXML_SUCCESS 685* IXML_INVALID_PARAMETER: if anyone of nodeptr, newChild or oldChild is NULL. 686* IXML_HIERARCHY_REQUEST_ERR: if the newChild is ancestor of nodeptr or nodeptr 687* is of a type that does not allow children of the 688* type of the newChild node. 689* IXML_WRONG_DOCUMENT_ERR: if newChild was created from a different document than 690* the one that created this node. 691* IXML_NOT_FOUND_ERR: if oldChild is not a child of nodeptr. 692* 693*=================================================================*/ 694int 695ixmlNode_replaceChild( IN IXML_Node * nodeptr, 696 IN IXML_Node * newChild, 697 IN IXML_Node * oldChild, 698 OUT IXML_Node ** returnNode ) 699{ 700 int ret = IXML_SUCCESS; 701 702 if( ( nodeptr == NULL ) || ( newChild == NULL ) 703 || ( oldChild == NULL ) ) { 704 return IXML_INVALID_PARAMETER; 705 } 706 // if nodetype of nodeptr does not allow children of the type of newChild 707 // needs to add later 708 709 // or if newChild is one of nodeptr's ancestors 710 if( ixmlNode_isAncestor( newChild, nodeptr ) == TRUE ) { 711 return IXML_HIERARCHY_REQUEST_ERR; 712 } 713 714 if( ixmlNode_allowChildren( nodeptr, newChild ) == FALSE ) { 715 return IXML_HIERARCHY_REQUEST_ERR; 716 } 717 // if newChild was created from a different document 718 if( nodeptr->ownerDocument != newChild->ownerDocument ) { 719 return IXML_WRONG_DOCUMENT_ERR; 720 } 721 // if refChild is not a child of nodeptr 722 if( ixmlNode_isParent( nodeptr, oldChild ) != TRUE ) { 723 return IXML_NOT_FOUND_ERR; 724 } 725 726 ret = ixmlNode_insertBefore( nodeptr, newChild, oldChild ); 727 if( ret != IXML_SUCCESS ) { 728 return ret; 729 } 730 731 ret = ixmlNode_removeChild( nodeptr, oldChild, returnNode ); 732 return ret; 733} 734 735/*================================================================ 736* ixmlNode_removeChild 737* Removes the child node indicated by oldChild from the list of 738* children, and returns it. 739* External function. 740* Parameters: 741* oldChild: the node being removed. 742* returnNode: the node removed. 743* Return Value: 744* IXML_SUCCESS 745* IXML_NOT_FOUND_ERR: if oldChild is not a child of this node. 746* IXML_INVALID_PARAMETER: if either oldChild or nodeptr is NULL 747* 748*=================================================================*/ 749int 750ixmlNode_removeChild( IN IXML_Node * nodeptr, 751 IN IXML_Node * oldChild, 752 OUT IXML_Node ** returnNode ) 753{ 754 755 if( ( nodeptr == NULL ) || ( oldChild == NULL ) ) { 756 return IXML_INVALID_PARAMETER; 757 } 758 759 if( ixmlNode_isParent( nodeptr, oldChild ) == FALSE ) { 760 return IXML_NOT_FOUND_ERR; 761 } 762 763 if( oldChild->prevSibling != NULL ) { 764 ( oldChild->prevSibling )->nextSibling = oldChild->nextSibling; 765 } 766 767 if( nodeptr->firstChild == oldChild ) { 768 nodeptr->firstChild = oldChild->nextSibling; 769 } 770 771 if( oldChild->nextSibling != NULL ) { 772 ( oldChild->nextSibling )->prevSibling = oldChild->prevSibling; 773 } 774 775 oldChild->nextSibling = NULL; 776 oldChild->prevSibling = NULL; 777 oldChild->parentNode = NULL; 778 779 if( returnNode != NULL ) { 780 *returnNode = oldChild; 781 } 782 return IXML_SUCCESS; 783} 784 785/*============================================================================= 786* ixmlNode_appendChild 787* Adds the node newChild to the end of the list of children of this node. 788* If the newChild is already in the tree, it is first removed. 789* External function. 790* Parameter: 791* newChild: the node to add. 792* Return Value: 793* IXML_SUCCESS 794* IXML_INVALID_PARAMETER: if either nodeptr or newChild is NULL 795* IXML_WRONG_DOCUMENT_ERR: if newChild was created from a different document than 796* the one that created nodeptr. 797* IXML_HIERARCHY_REQUEST_ERR: if newChild is ancestor of nodeptr or if nodeptr is of 798* a type that does not allow children of the type of the 799* newChild node. 800* 801*=================================================================*/ 802int 803ixmlNode_appendChild( IN IXML_Node * nodeptr, 804 IN IXML_Node * newChild ) 805{ 806 807 IXML_Node *prev = NULL, 808 *next = NULL; 809 810 if( ( nodeptr == NULL ) || ( newChild == NULL ) ) { 811 return IXML_INVALID_PARAMETER; 812 } 813 // if newChild was created from a different document 814 if( ( newChild->ownerDocument != NULL ) && 815 ( nodeptr->ownerDocument != newChild->ownerDocument ) ) { 816 return IXML_WRONG_DOCUMENT_ERR; 817 } 818 // if newChild is an ancestor of nodeptr 819 if( ixmlNode_isAncestor( newChild, nodeptr ) == TRUE ) { 820 return IXML_HIERARCHY_REQUEST_ERR; 821 } 822 // if nodeptr does not allow to have newChild as children 823 if( ixmlNode_allowChildren( nodeptr, newChild ) == FALSE ) { 824 return IXML_HIERARCHY_REQUEST_ERR; 825 } 826 827 if( ixmlNode_isParent( nodeptr, newChild ) == TRUE ) { 828 ixmlNode_removeChild( nodeptr, newChild, NULL ); 829 } 830 // set the parent node pointer 831 newChild->parentNode = nodeptr; 832 newChild->ownerDocument = nodeptr->ownerDocument; 833 834 //if the first child 835 if( nodeptr->firstChild == NULL ) { 836 nodeptr->firstChild = newChild; 837 } else { 838 prev = nodeptr->firstChild; 839 next = prev->nextSibling; 840 while( next != NULL ) { 841 prev = next; 842 next = prev->nextSibling; 843 } 844 prev->nextSibling = newChild; 845 newChild->prevSibling = prev; 846 } 847 848 return IXML_SUCCESS; 849} 850 851/*================================================================ 852* ixmlNode_cloneTextNode 853* Returns a clone of nodeptr 854* Internal to parser only. 855* 856*=================================================================*/ 857IXML_Node * 858ixmlNode_cloneTextNode( IN IXML_Node * nodeptr ) 859{ 860 IXML_Node *newNode = NULL; 861 862 assert( nodeptr != NULL ); 863 864 newNode = ( IXML_Node * ) malloc( sizeof( IXML_Node ) ); 865 if( newNode == NULL ) { 866 return NULL; 867 } else { 868 ixmlNode_init( newNode ); 869 870 ixmlNode_setNodeName( newNode, nodeptr->nodeName ); 871 ixmlNode_setNodeValue( newNode, nodeptr->nodeValue ); 872 newNode->nodeType = eTEXT_NODE; 873 } 874 875 return newNode; 876} 877 878/*================================================================ 879* ixmlNode_cloneCDATASect 880* Return a clone of CDATASection node. 881* Internal to parser only. 882* 883*=================================================================*/ 884IXML_CDATASection * 885ixmlNode_cloneCDATASect( IN IXML_CDATASection * nodeptr ) 886{ 887 IXML_CDATASection *newCDATA = NULL; 888 IXML_Node *newNode; 889 IXML_Node *srcNode; 890 891 assert( nodeptr != NULL ); 892 newCDATA = 893 ( IXML_CDATASection * ) malloc( sizeof( IXML_CDATASection ) ); 894 if( newCDATA != NULL ) { 895 newNode = ( IXML_Node * ) newCDATA; 896 ixmlNode_init( newNode ); 897 898 srcNode = ( IXML_Node * ) nodeptr; 899 ixmlNode_setNodeName( newNode, srcNode->nodeName ); 900 ixmlNode_setNodeValue( newNode, srcNode->nodeValue ); 901 newNode->nodeType = eCDATA_SECTION_NODE; 902 } 903 904 return newCDATA; 905} 906 907/*================================================================ 908* ixmlNode_cloneElement 909* returns a clone of element node 910* Internal to parser only. 911* 912*=================================================================*/ 913IXML_Element * 914ixmlNode_cloneElement( IN IXML_Element * nodeptr ) 915{ 916 IXML_Element *newElement; 917 IXML_Node *elementNode; 918 IXML_Node *srcNode; 919 int rc; 920 921 assert( nodeptr != NULL ); 922 923 newElement = ( IXML_Element * ) malloc( sizeof( IXML_Element ) ); 924 if( newElement == NULL ) { 925 return NULL; 926 } 927 928 ixmlElement_init( newElement ); 929 rc = ixmlElement_setTagName( newElement, nodeptr->tagName ); 930 if( rc != IXML_SUCCESS ) { 931 ixmlElement_free( newElement ); 932 } 933 934 elementNode = ( IXML_Node * ) newElement; 935 srcNode = ( IXML_Node * ) nodeptr; 936 rc = ixmlNode_setNodeName( elementNode, srcNode->nodeName ); 937 if( rc != IXML_SUCCESS ) { 938 ixmlElement_free( newElement ); 939 } 940 941 rc = ixmlNode_setNodeValue( elementNode, srcNode->nodeValue ); 942 if( rc != IXML_SUCCESS ) { 943 ixmlElement_free( newElement ); 944 } 945 946 rc = ixmlNode_setNamespaceURI( elementNode, srcNode->namespaceURI ); 947 if( rc != IXML_SUCCESS ) { 948 ixmlElement_free( newElement ); 949 } 950 951 rc = ixmlNode_setPrefix( elementNode, srcNode->prefix ); 952 if( rc != IXML_SUCCESS ) { 953 ixmlElement_free( newElement ); 954 } 955 956 rc = ixmlNode_setLocalName( elementNode, srcNode->localName ); 957 if( rc != IXML_SUCCESS ) { 958 ixmlElement_free( newElement ); 959 } 960 961 elementNode->nodeType = eELEMENT_NODE; 962 963 return newElement; 964 965} 966 967/*================================================================ 968* ixmlNode_cloneDoc 969* Returns a clone of document node 970* Internal to parser only. 971* 972*=================================================================*/ 973IXML_Document * 974ixmlNode_cloneDoc( IN IXML_Document * nodeptr ) 975{ 976 IXML_Document *newDoc; 977 IXML_Node *docNode; 978 int rc; 979 980 assert( nodeptr != NULL ); 981 newDoc = ( IXML_Document * ) malloc( sizeof( IXML_Document ) ); 982 if( newDoc == NULL ) { 983 return NULL; 984 } 985 986 ixmlDocument_init( newDoc ); 987 docNode = ( IXML_Node * ) newDoc; 988 989 rc = ixmlNode_setNodeName( docNode, DOCUMENTNODENAME ); 990 if( rc != IXML_SUCCESS ) { 991 ixmlDocument_free( newDoc ); 992 return NULL; 993 } 994 995 newDoc->n.nodeType = eDOCUMENT_NODE; 996 997 return newDoc; 998 999} 1000 1001/*================================================================ 1002* ixmlNode_cloneAttr 1003* Returns a clone of attribute node 1004* Internal to parser only 1005* 1006*=================================================================*/ 1007IXML_Attr * 1008ixmlNode_cloneAttr( IN IXML_Attr * nodeptr ) 1009{ 1010 IXML_Attr *newAttr; 1011 IXML_Node *attrNode; 1012 IXML_Node *srcNode; 1013 int rc; 1014 1015 assert( nodeptr != NULL ); 1016 newAttr = ( IXML_Attr * ) malloc( sizeof( IXML_Attr ) ); 1017 if( newAttr == NULL ) { 1018 return NULL; 1019 } 1020 1021 ixmlAttr_init( newAttr ); 1022 attrNode = ( IXML_Node * ) newAttr; 1023 srcNode = ( IXML_Node * ) nodeptr; 1024 1025 rc = ixmlNode_setNodeName( attrNode, srcNode->nodeName ); 1026 if( rc != IXML_SUCCESS ) { 1027 ixmlAttr_free( newAttr ); 1028 return NULL; 1029 } 1030 1031 rc = ixmlNode_setNodeValue( attrNode, srcNode->nodeValue ); 1032 if( rc != IXML_SUCCESS ) { 1033 ixmlAttr_free( newAttr ); 1034 return NULL; 1035 } 1036 //check to see whether we need to split prefix and localname for attribute 1037 rc = ixmlNode_setNamespaceURI( attrNode, srcNode->namespaceURI ); 1038 if( rc != IXML_SUCCESS ) { 1039 ixmlAttr_free( newAttr ); 1040 return NULL; 1041 } 1042 1043 rc = ixmlNode_setPrefix( attrNode, srcNode->prefix ); 1044 if( rc != IXML_SUCCESS ) { 1045 ixmlAttr_free( newAttr ); 1046 return NULL; 1047 } 1048 1049 rc = ixmlNode_setLocalName( attrNode, srcNode->localName ); 1050 if( rc != IXML_SUCCESS ) { 1051 ixmlAttr_free( newAttr ); 1052 return NULL; 1053 } 1054 1055 attrNode->nodeType = eATTRIBUTE_NODE; 1056 1057 return newAttr; 1058} 1059 1060/*================================================================ 1061* ixmlNode_cloneAttrDirect 1062* Return a clone of attribute node, with specified field set 1063* to TRUE. 1064* 1065*=================================================================*/ 1066IXML_Attr * 1067ixmlNode_cloneAttrDirect( IN IXML_Attr * nodeptr ) 1068{ 1069 1070 IXML_Attr *newAttr; 1071 1072 assert( nodeptr != NULL ); 1073 1074 newAttr = ixmlNode_cloneAttr( nodeptr ); 1075 if( newAttr != NULL ) { 1076 newAttr->specified = TRUE; 1077 } 1078 1079 return newAttr; 1080} 1081 1082void 1083ixmlNode_setSiblingNodesParent( IXML_Node * nodeptr ) 1084{ 1085 IXML_Node *parentNode = nodeptr->parentNode; 1086 IXML_Node *nextptr = nodeptr->nextSibling; 1087 1088 while( nextptr != NULL ) { 1089 nextptr->parentNode = parentNode; 1090 nextptr = nextptr->nextSibling; 1091 } 1092} 1093 1094/*================================================================ 1095* ixmlNode_cloneNodeTreeRecursive 1096* recursive functions that clones node tree of nodeptr. 1097* Internal to parser only. 1098* 1099*=================================================================*/ 1100IXML_Node * 1101ixmlNode_cloneNodeTreeRecursive( IN IXML_Node * nodeptr, 1102 IN BOOL deep ) 1103{ 1104 IXML_Node *newNode = NULL; 1105 IXML_Element *newElement; 1106 IXML_Attr *newAttr = NULL; 1107 IXML_CDATASection *newCDATA = NULL; 1108 IXML_Document *newDoc; 1109 IXML_Node *nextSib; 1110 1111 if( nodeptr != NULL ) { 1112 switch ( nodeptr->nodeType ) { 1113 case eELEMENT_NODE: 1114 newElement = 1115 ixmlNode_cloneElement( ( IXML_Element * ) nodeptr ); 1116 newElement->n.firstAttr = 1117 ixmlNode_cloneNodeTreeRecursive( nodeptr->firstAttr, 1118 deep ); 1119 if( deep ) { 1120 newElement->n.firstChild = 1121 ixmlNode_cloneNodeTreeRecursive( nodeptr-> 1122 firstChild, 1123 deep ); 1124 if( newElement->n.firstChild != NULL ) { 1125 ( newElement->n.firstChild )->parentNode = 1126 ( IXML_Node * ) newElement; 1127 ixmlNode_setSiblingNodesParent( newElement->n. 1128 firstChild ); 1129 } 1130 nextSib = 1131 ixmlNode_cloneNodeTreeRecursive( nodeptr-> 1132 nextSibling, 1133 deep ); 1134 newElement->n.nextSibling = nextSib; 1135 if( nextSib != NULL ) { 1136 nextSib->prevSibling = ( IXML_Node * ) newElement; 1137 } 1138 } 1139 1140 newNode = ( IXML_Node * ) newElement; 1141 break; 1142 1143 case eATTRIBUTE_NODE: 1144 newAttr = ixmlNode_cloneAttr( ( IXML_Attr * ) nodeptr ); 1145 nextSib = 1146 ixmlNode_cloneNodeTreeRecursive( nodeptr->nextSibling, 1147 deep ); 1148 newAttr->n.nextSibling = nextSib; 1149 1150 if( nextSib != NULL ) { 1151 nextSib->prevSibling = ( IXML_Node * ) newAttr; 1152 } 1153 newNode = ( IXML_Node * ) newAttr; 1154 break; 1155 1156 case eTEXT_NODE: 1157 newNode = ixmlNode_cloneTextNode( nodeptr ); 1158 break; 1159 1160 case eCDATA_SECTION_NODE: 1161 newCDATA = 1162 ixmlNode_cloneCDATASect( ( IXML_CDATASection * ) 1163 nodeptr ); 1164 newNode = ( IXML_Node * ) newCDATA; 1165 break; 1166 1167 case eDOCUMENT_NODE: 1168 newDoc = ixmlNode_cloneDoc( ( IXML_Document * ) nodeptr ); 1169 newNode = ( IXML_Node * ) newDoc; 1170 if( deep ) { 1171 newNode->firstChild = 1172 ixmlNode_cloneNodeTreeRecursive( nodeptr-> 1173 firstChild, 1174 deep ); 1175 if( newNode->firstChild != NULL ) { 1176 newNode->firstChild->parentNode = newNode; 1177 } 1178 } 1179 1180 break; 1181 1182 case eINVALID_NODE: 1183 case eENTITY_REFERENCE_NODE: 1184 case eENTITY_NODE: 1185 case ePROCESSING_INSTRUCTION_NODE: 1186 case eCOMMENT_NODE: 1187 case eDOCUMENT_TYPE_NODE: 1188 case eDOCUMENT_FRAGMENT_NODE: 1189 case eNOTATION_NODE: 1190 break; 1191 } 1192 } 1193 1194 return newNode; 1195} 1196 1197/*================================================================ 1198* ixmlNode_cloneNodeTree 1199* clones a node tree. 1200* Internal to parser only. 1201* 1202*=================================================================*/ 1203IXML_Node * 1204ixmlNode_cloneNodeTree( IN IXML_Node * nodeptr, 1205 IN BOOL deep ) 1206{ 1207 IXML_Node *newNode = NULL; 1208 IXML_Element *newElement; 1209 IXML_Node *childNode; 1210 1211 assert( nodeptr != NULL ); 1212 1213 switch ( nodeptr->nodeType ) { 1214 case eELEMENT_NODE: 1215 newElement = 1216 ixmlNode_cloneElement( ( IXML_Element * ) nodeptr ); 1217 newElement->n.firstAttr = 1218 ixmlNode_cloneNodeTreeRecursive( nodeptr->firstAttr, 1219 deep ); 1220 if( deep ) { 1221 newElement->n.firstChild = 1222 ixmlNode_cloneNodeTreeRecursive( nodeptr->firstChild, 1223 deep ); 1224 childNode = newElement->n.firstChild; 1225 while( childNode != NULL ) { 1226 childNode->parentNode = ( IXML_Node * ) newElement; 1227 childNode = childNode->nextSibling; 1228 } 1229 newElement->n.nextSibling = NULL; 1230 } 1231 1232 newNode = ( IXML_Node * ) newElement; 1233 break; 1234 1235 case eATTRIBUTE_NODE: 1236 case eTEXT_NODE: 1237 case eCDATA_SECTION_NODE: 1238 case eDOCUMENT_NODE: 1239 newNode = ixmlNode_cloneNodeTreeRecursive( nodeptr, deep ); 1240 break; 1241 1242 case eINVALID_NODE: 1243 case eENTITY_REFERENCE_NODE: 1244 case eENTITY_NODE: 1245 case ePROCESSING_INSTRUCTION_NODE: 1246 case eCOMMENT_NODE: 1247 case eDOCUMENT_TYPE_NODE: 1248 case eDOCUMENT_FRAGMENT_NODE: 1249 case eNOTATION_NODE: 1250 break; 1251 } 1252 1253 // by spec, the duplicate node has no parent 1254 newNode->parentNode = NULL; 1255 1256 return newNode; 1257} 1258 1259/*================================================================ 1260* ixmlNode_cloneNode 1261* Clones a node, if deep==TRUE, clones subtree under nodeptr. 1262* External function. 1263* Returns: 1264* the cloned node or NULL if error occurs. 1265* 1266*=================================================================*/ 1267IXML_Node * 1268ixmlNode_cloneNode( IN IXML_Node * nodeptr, 1269 IN BOOL deep ) 1270{ 1271 1272 IXML_Node *newNode; 1273 IXML_Attr *newAttrNode; 1274 1275 if( nodeptr == NULL ) { 1276 return NULL; 1277 } 1278 1279 switch ( nodeptr->nodeType ) { 1280 case eATTRIBUTE_NODE: 1281 newAttrNode = 1282 ixmlNode_cloneAttrDirect( ( IXML_Attr * ) nodeptr ); 1283 return ( IXML_Node * ) newAttrNode; 1284 break; 1285 1286 default: 1287 newNode = ixmlNode_cloneNodeTree( nodeptr, deep ); 1288 return newNode; 1289 break; 1290 } 1291 1292} 1293 1294/*================================================================ 1295* ixmlNode_getChildNodes 1296* Returns a IXML_NodeList of all the child nodes of nodeptr. 1297* External function. 1298* 1299*=================================================================*/ 1300IXML_NodeList * 1301ixmlNode_getChildNodes( IN IXML_Node * nodeptr ) 1302{ 1303 IXML_Node *tempNode; 1304 IXML_NodeList *newNodeList; 1305 int rc; 1306 1307 if( nodeptr == NULL ) { 1308 return NULL; 1309 } 1310 1311 newNodeList = ( IXML_NodeList * ) malloc( sizeof( IXML_NodeList ) ); 1312 if( newNodeList == NULL ) { 1313 return NULL; 1314 } 1315 1316 ixmlNodeList_init( newNodeList ); 1317 1318 tempNode = nodeptr->firstChild; 1319 while( tempNode != NULL ) { 1320 rc = ixmlNodeList_addToNodeList( &newNodeList, tempNode ); 1321 if( rc != IXML_SUCCESS ) { 1322 ixmlNodeList_free( newNodeList ); 1323 return NULL; 1324 } 1325 1326 tempNode = tempNode->nextSibling; 1327 } 1328 return newNodeList; 1329} 1330 1331/*================================================================ 1332* ixmlNode_getAttributes 1333* returns a namedNodeMap of attributes of nodeptr 1334* External function. 1335* Returns: 1336* 1337*=================================================================*/ 1338IXML_NamedNodeMap * 1339ixmlNode_getAttributes( IN IXML_Node * nodeptr ) 1340{ 1341 IXML_NamedNodeMap *returnNamedNodeMap = NULL; 1342 IXML_Node *tempNode; 1343 int rc; 1344 1345 if( nodeptr == NULL ) { 1346 return NULL; 1347 } 1348 1349 if( nodeptr->nodeType == eELEMENT_NODE ) { 1350 returnNamedNodeMap = 1351 ( IXML_NamedNodeMap * ) malloc( sizeof( IXML_NamedNodeMap ) ); 1352 if( returnNamedNodeMap == NULL ) { 1353 return NULL; 1354 } 1355 1356 ixmlNamedNodeMap_init( returnNamedNodeMap ); 1357 1358 tempNode = nodeptr->firstAttr; 1359 while( tempNode != NULL ) { 1360 rc = ixmlNamedNodeMap_addToNamedNodeMap( &returnNamedNodeMap, 1361 tempNode ); 1362 if( rc != IXML_SUCCESS ) { 1363 ixmlNamedNodeMap_free( returnNamedNodeMap ); 1364 return NULL; 1365 } 1366 1367 tempNode = tempNode->nextSibling; 1368 } 1369 return returnNamedNodeMap; 1370 } else { // if not an ELEMENT_NODE 1371 return NULL; 1372 } 1373} 1374 1375/*================================================================ 1376* ixmlNode_hasChildNodes 1377* External function. 1378* 1379*=================================================================*/ 1380BOOL 1381ixmlNode_hasChildNodes( IXML_Node * nodeptr ) 1382{ 1383 if( nodeptr == NULL ) { 1384 return FALSE; 1385 } 1386 1387 return ( nodeptr->firstChild != NULL ); 1388 1389} 1390 1391/*================================================================ 1392* ixmlNode_hasAttributes 1393* External function. 1394* 1395*=================================================================*/ 1396BOOL 1397ixmlNode_hasAttributes( IXML_Node * nodeptr ) 1398{ 1399 if( nodeptr != NULL ) { 1400 if( ( nodeptr->nodeType == eELEMENT_NODE ) 1401 && ( nodeptr->firstAttr != NULL ) ) { 1402 return TRUE; 1403 } 1404 } 1405 return FALSE; 1406 1407} 1408 1409/*================================================================ 1410* ixmlNode_getElementsByTagNameRecursive 1411* Recursively traverse the whole tree, search for element 1412* with the given tagname. 1413* Internal to parser. 1414* 1415*=================================================================*/ 1416void 1417ixmlNode_getElementsByTagNameRecursive( IN IXML_Node * n, 1418 IN char *tagname, 1419 OUT IXML_NodeList ** list ) 1420{ 1421 const char *name; 1422 1423 if( n != NULL ) { 1424 if( ixmlNode_getNodeType( n ) == eELEMENT_NODE ) { 1425 name = ixmlNode_getNodeName( n ); 1426 if( strcmp( tagname, name ) == 0 1427 || strcmp( tagname, "*" ) == 0 ) { 1428 ixmlNodeList_addToNodeList( list, n ); 1429 } 1430 } 1431 1432 ixmlNode_getElementsByTagNameRecursive( ixmlNode_getFirstChild 1433 ( n ), tagname, list ); 1434 ixmlNode_getElementsByTagNameRecursive( ixmlNode_getNextSibling 1435 ( n ), tagname, list ); 1436 } 1437 1438} 1439 1440/*================================================================ 1441* ixmlNode_getElementsByTagName 1442* Returns a nodeList of all descendant Elements with a given 1443* tagName, in the order in which they are encountered in a 1444* traversal of this element tree. 1445* External function. 1446* 1447*=================================================================*/ 1448void 1449ixmlNode_getElementsByTagName( IN IXML_Node * n, 1450 IN char *tagname, 1451 OUT IXML_NodeList ** list ) 1452{ 1453 const char *name; 1454 1455 assert( n != NULL && tagname != NULL ); 1456 1457 if( ixmlNode_getNodeType( n ) == eELEMENT_NODE ) { 1458 name = ixmlNode_getNodeName( n ); 1459 if( strcmp( tagname, name ) == 0 || strcmp( tagname, "*" ) == 0 ) { 1460 ixmlNodeList_addToNodeList( list, n ); 1461 } 1462 } 1463 1464 ixmlNode_getElementsByTagNameRecursive( ixmlNode_getFirstChild( n ), 1465 tagname, list ); 1466 1467} 1468 1469/*================================================================ 1470* ixmlNode_getElementsByTagNameNSRecursive 1471* Internal function to parser. 1472* 1473* 1474*=================================================================*/ 1475void 1476ixmlNode_getElementsByTagNameNSRecursive( IN IXML_Node * n, 1477 IN char *namespaceURI, 1478 IN char *localName, 1479 OUT IXML_NodeList ** list ) 1480{ 1481 const DOMString nsURI; 1482 const DOMString name; 1483 1484 if( n != NULL ) { 1485 if( ixmlNode_getNodeType( n ) == eELEMENT_NODE ) { 1486 name = ixmlNode_getLocalName( n ); 1487 nsURI = ixmlNode_getNamespaceURI( n ); 1488 1489 if( ( name != NULL ) && ( nsURI != NULL ) && 1490 ( strcmp( namespaceURI, nsURI ) == 0 1491 || strcmp( namespaceURI, "*" ) == 0 ) 1492 && ( strcmp( name, localName ) == 0 1493 || strcmp( localName, "*" ) == 0 ) ) { 1494 ixmlNodeList_addToNodeList( list, n ); 1495 } 1496 } 1497 1498 ixmlNode_getElementsByTagNameNSRecursive( ixmlNode_getFirstChild 1499 ( n ), namespaceURI, 1500 localName, list ); 1501 ixmlNode_getElementsByTagNameNSRecursive( ixmlNode_getNextSibling 1502 ( n ), namespaceURI, 1503 localName, list ); 1504 } 1505 1506} 1507 1508/*================================================================ 1509* ixmlNode_getElementsByTagNameNS 1510* Returns a nodeList of all the descendant Elements with a given 1511* local name and namespace URI in the order in which they are 1512* encountered in a preorder traversal of this Elememt tree. 1513* External function. 1514* 1515*=================================================================*/ 1516void 1517ixmlNode_getElementsByTagNameNS( IN IXML_Node * n, 1518 IN char *namespaceURI, 1519 IN char *localName, 1520 OUT IXML_NodeList ** list ) 1521{ 1522 const DOMString nsURI; 1523 const DOMString name; 1524 1525 assert( n != NULL && namespaceURI != NULL && localName != NULL ); 1526 1527 if( ixmlNode_getNodeType( n ) == eELEMENT_NODE ) { 1528 name = ixmlNode_getLocalName( n ); 1529 nsURI = ixmlNode_getNamespaceURI( n ); 1530 1531 if( ( name != NULL ) && ( nsURI != NULL ) && 1532 ( strcmp( namespaceURI, nsURI ) == 0 1533 || strcmp( namespaceURI, "*" ) == 0 ) 1534 && ( strcmp( name, localName ) == 0 1535 || strcmp( localName, "*" ) == 0 ) ) { 1536 ixmlNodeList_addToNodeList( list, n ); 1537 } 1538 } 1539 1540 ixmlNode_getElementsByTagNameNSRecursive( ixmlNode_getFirstChild( n ), 1541 namespaceURI, localName, 1542 list ); 1543 1544} 1545 1546/*================================================================ 1547* ixmlNode_setNodeName 1548* Internal to parser only. 1549* 1550*=================================================================*/ 1551int 1552ixmlNode_setNodeName( IN IXML_Node * node, 1553 IN DOMString qualifiedName ) 1554{ 1555 int rc = IXML_SUCCESS; 1556 1557 assert( node != NULL ); 1558 1559 if( node->nodeName != NULL ) { 1560 free( node->nodeName ); 1561 node->nodeName = NULL; 1562 } 1563 1564 if( qualifiedName != NULL ) { 1565 // set the name part 1566 node->nodeName = strdup( qualifiedName ); 1567 if( node->nodeName == NULL ) { 1568 return IXML_INSUFFICIENT_MEMORY; 1569 } 1570 1571 rc = Parser_setNodePrefixAndLocalName( node ); 1572 if( rc != IXML_SUCCESS ) { 1573 free( node->nodeName ); 1574 } 1575 } 1576 1577 return rc; 1578} 1579 1580/*================================================================ 1581* ixmlNode_setNodeProperties 1582* Internal to parser only. 1583* 1584*=================================================================*/ 1585int 1586ixmlNode_setNodeProperties( IN IXML_Node * destNode, 1587 IN IXML_Node * src ) 1588{ 1589 1590 int rc; 1591 1592 assert( destNode != NULL || src != NULL ); 1593 1594 rc = ixmlNode_setNodeValue( destNode, src->nodeValue ); 1595 if( rc != IXML_SUCCESS ) { 1596 goto ErrorHandler; 1597 } 1598 1599 rc = ixmlNode_setLocalName( destNode, src->localName ); 1600 if( rc != IXML_SUCCESS ) { 1601 goto ErrorHandler; 1602 } 1603 1604 rc = ixmlNode_setPrefix( destNode, src->prefix ); 1605 if( rc != IXML_SUCCESS ) { 1606 goto ErrorHandler; 1607 } 1608 // set nodetype 1609 destNode->nodeType = src->nodeType; 1610 1611 return IXML_SUCCESS; 1612 1613 ErrorHandler: 1614 if( destNode->nodeName != NULL ) { 1615 free( destNode->nodeName ); 1616 destNode->nodeName = NULL; 1617 } 1618 if( destNode->nodeValue != NULL ) { 1619 free( destNode->nodeValue ); 1620 destNode->nodeValue = NULL; 1621 } 1622 if( destNode->localName != NULL ) { 1623 free( destNode->localName ); 1624 destNode->localName = NULL; 1625 } 1626 1627 return IXML_INSUFFICIENT_MEMORY; 1628} 1629