Annotation of embedaddon/php/ext/dom/document.c, revision 1.1.1.2

1.1       misho       1: /*
                      2:    +----------------------------------------------------------------------+
                      3:    | PHP Version 5                                                        |
                      4:    +----------------------------------------------------------------------+
                      5:    | Copyright (c) 1997-2012 The PHP Group                                |
                      6:    +----------------------------------------------------------------------+
                      7:    | This source file is subject to version 3.01 of the PHP license,      |
                      8:    | that is bundled with this package in the file LICENSE, and is        |
                      9:    | available through the world-wide-web at the following url:           |
                     10:    | http://www.php.net/license/3_01.txt                                  |
                     11:    | If you did not receive a copy of the PHP license and are unable to   |
                     12:    | obtain it through the world-wide-web, please send a note to          |
                     13:    | license@php.net so we can mail you a copy immediately.               |
                     14:    +----------------------------------------------------------------------+
                     15:    | Authors: Christian Stocker <chregu@php.net>                          |
                     16:    |          Rob Richards <rrichards@php.net>                            |
                     17:    +----------------------------------------------------------------------+
                     18: */
                     19: 
1.1.1.2 ! misho      20: /* $Id$ */
1.1       misho      21: 
                     22: #ifdef HAVE_CONFIG_H
                     23: #include "config.h"
                     24: #endif
                     25: 
                     26: #include "php.h"
                     27: #if HAVE_LIBXML && HAVE_DOM
                     28: #include "php_dom.h"
                     29: #include <libxml/SAX.h>
                     30: #ifdef LIBXML_SCHEMAS_ENABLED
                     31: #include <libxml/relaxng.h>
                     32: #include <libxml/xmlschemas.h>
                     33: #endif
                     34: 
                     35: typedef struct _idsIterator idsIterator;
                     36: struct _idsIterator {
                     37:        xmlChar *elementId;
                     38:        xmlNode *element;
                     39: };
                     40: 
                     41: #define DOM_LOAD_STRING 0
                     42: #define DOM_LOAD_FILE 1
                     43: 
                     44: /* {{{ arginfo */
                     45: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_element, 0, 0, 1)
                     46:        ZEND_ARG_INFO(0, tagName)
                     47:        ZEND_ARG_INFO(0, value)
                     48: ZEND_END_ARG_INFO();
                     49: 
                     50: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_document_fragment, 0, 0, 0)
                     51: ZEND_END_ARG_INFO();
                     52: 
                     53: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_text_node, 0, 0, 1)
                     54:        ZEND_ARG_INFO(0, data)
                     55: ZEND_END_ARG_INFO();
                     56: 
                     57: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_comment, 0, 0, 1)
                     58:        ZEND_ARG_INFO(0, data)
                     59: ZEND_END_ARG_INFO();
                     60: 
                     61: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_cdatasection, 0, 0, 1)
                     62:        ZEND_ARG_INFO(0, data)
                     63: ZEND_END_ARG_INFO();
                     64: 
                     65: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_processing_instruction, 0, 0, 2)
                     66:        ZEND_ARG_INFO(0, target)
                     67:        ZEND_ARG_INFO(0, data)
                     68: ZEND_END_ARG_INFO();
                     69: 
                     70: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_attribute, 0, 0, 1)
                     71:        ZEND_ARG_INFO(0, name)
                     72: ZEND_END_ARG_INFO();
                     73: 
                     74: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_entity_reference, 0, 0, 1)
                     75:        ZEND_ARG_INFO(0, name)
                     76: ZEND_END_ARG_INFO();
                     77: 
                     78: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_get_elements_by_tag_name, 0, 0, 1)
                     79:        ZEND_ARG_INFO(0, tagName)
                     80: ZEND_END_ARG_INFO();
                     81: 
                     82: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_import_node, 0, 0, 2)
                     83:        ZEND_ARG_OBJ_INFO(0, importedNode, DOMNode, 0)
                     84:        ZEND_ARG_INFO(0, deep)
                     85: ZEND_END_ARG_INFO();
                     86: 
                     87: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_element_ns, 0, 0, 2)
                     88:        ZEND_ARG_INFO(0, namespaceURI)
                     89:        ZEND_ARG_INFO(0, qualifiedName)
                     90:        ZEND_ARG_INFO(0, value)
                     91: ZEND_END_ARG_INFO();
                     92: 
                     93: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_create_attribute_ns, 0, 0, 2)
                     94:        ZEND_ARG_INFO(0, namespaceURI)
                     95:        ZEND_ARG_INFO(0, qualifiedName)
                     96: ZEND_END_ARG_INFO();
                     97: 
                     98: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_get_elements_by_tag_name_ns, 0, 0, 2)
                     99:        ZEND_ARG_INFO(0, namespaceURI)
                    100:        ZEND_ARG_INFO(0, localName)
                    101: ZEND_END_ARG_INFO();
                    102: 
                    103: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_get_element_by_id, 0, 0, 1)
                    104:        ZEND_ARG_INFO(0, elementId)
                    105: ZEND_END_ARG_INFO();
                    106: 
                    107: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_adopt_node, 0, 0, 1)
                    108:        ZEND_ARG_OBJ_INFO(0, source, DOMNode, 0)
                    109: ZEND_END_ARG_INFO();
                    110: 
                    111: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_normalize_document, 0, 0, 0)
                    112: ZEND_END_ARG_INFO();
                    113: 
                    114: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_rename_node, 0, 0, 3)
                    115:        ZEND_ARG_OBJ_INFO(0, node, DOMNode, 0)
                    116:        ZEND_ARG_INFO(0, namespaceURI)
                    117:        ZEND_ARG_INFO(0, qualifiedName)
                    118: ZEND_END_ARG_INFO();
                    119: 
                    120: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_load, 0, 0, 1)
                    121:        ZEND_ARG_INFO(0, source)
                    122:        ZEND_ARG_INFO(0, options)
                    123: ZEND_END_ARG_INFO();
                    124: 
                    125: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_save, 0, 0, 1)
                    126:        ZEND_ARG_INFO(0, file)
                    127: ZEND_END_ARG_INFO();
                    128: 
                    129: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_loadxml, 0, 0, 1)
                    130:        ZEND_ARG_INFO(0, source)
                    131:        ZEND_ARG_INFO(0, options)
                    132: ZEND_END_ARG_INFO();
                    133: 
                    134: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_savexml, 0, 0, 0)
                    135:        ZEND_ARG_OBJ_INFO(0, node, DOMNode, 1)
                    136: ZEND_END_ARG_INFO();
                    137: 
                    138: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_construct, 0, 0, 0)
                    139:        ZEND_ARG_INFO(0, version)
                    140:        ZEND_ARG_INFO(0, encoding)
                    141: ZEND_END_ARG_INFO();
                    142: 
                    143: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_validate, 0, 0, 0)
                    144: ZEND_END_ARG_INFO();
                    145: 
                    146: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_xinclude, 0, 0, 0)
                    147:        ZEND_ARG_INFO(0, options)
                    148: ZEND_END_ARG_INFO();
                    149: 
                    150: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_loadhtml, 0, 0, 1)
                    151:        ZEND_ARG_INFO(0, source)
1.1.1.2 ! misho     152:        ZEND_ARG_INFO(0, options)
1.1       misho     153: ZEND_END_ARG_INFO();
                    154: 
                    155: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_loadhtmlfile, 0, 0, 1)
                    156:        ZEND_ARG_INFO(0, source)
1.1.1.2 ! misho     157:        ZEND_ARG_INFO(0, options)
1.1       misho     158: ZEND_END_ARG_INFO();
                    159: 
                    160: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_savehtml, 0, 0, 0)
                    161: ZEND_END_ARG_INFO();
                    162: 
                    163: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_savehtmlfile, 0, 0, 1)
                    164:        ZEND_ARG_INFO(0, file)
                    165: ZEND_END_ARG_INFO();
                    166: 
                    167: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_schema_validate_file, 0, 0, 1)
                    168:        ZEND_ARG_INFO(0, filename)
                    169: ZEND_END_ARG_INFO();
                    170: 
                    171: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_schema_validate_xml, 0, 0, 1)
                    172:        ZEND_ARG_INFO(0, source)
                    173: ZEND_END_ARG_INFO();
                    174: 
                    175: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_relaxNG_validate_file, 0, 0, 1)
                    176:        ZEND_ARG_INFO(0, filename)
                    177: ZEND_END_ARG_INFO();
                    178: 
                    179: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_relaxNG_validate_xml, 0, 0, 1)
                    180:        ZEND_ARG_INFO(0, source)
                    181: ZEND_END_ARG_INFO();
                    182: 
                    183: ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_document_registernodeclass, 0, 0, 2)
                    184:        ZEND_ARG_INFO(0, baseClass)
                    185:        ZEND_ARG_INFO(0, extendedClass)
                    186: ZEND_END_ARG_INFO();
                    187: /* }}} */
                    188: 
                    189: /*
                    190: * class DOMDocument extends DOMNode 
                    191: *
                    192: * URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-i-Document
                    193: * Since: 
                    194: */
                    195: 
                    196: const zend_function_entry php_dom_document_class_functions[] = { /* {{{ */
                    197:        PHP_FALIAS(createElement, dom_document_create_element, arginfo_dom_document_create_element)
                    198:        PHP_FALIAS(createDocumentFragment, dom_document_create_document_fragment, arginfo_dom_document_create_document_fragment)
                    199:        PHP_FALIAS(createTextNode, dom_document_create_text_node, arginfo_dom_document_create_text_node)
                    200:        PHP_FALIAS(createComment, dom_document_create_comment, arginfo_dom_document_create_comment)
                    201:        PHP_FALIAS(createCDATASection, dom_document_create_cdatasection, arginfo_dom_document_create_cdatasection)
                    202:        PHP_FALIAS(createProcessingInstruction, dom_document_create_processing_instruction, arginfo_dom_document_create_processing_instruction)
                    203:        PHP_FALIAS(createAttribute, dom_document_create_attribute, arginfo_dom_document_create_attribute)
                    204:        PHP_FALIAS(createEntityReference, dom_document_create_entity_reference, arginfo_dom_document_create_entity_reference)
                    205:        PHP_FALIAS(getElementsByTagName, dom_document_get_elements_by_tag_name, arginfo_dom_document_get_elements_by_tag_name)
                    206:        PHP_FALIAS(importNode, dom_document_import_node, arginfo_dom_document_import_node)
                    207:        PHP_FALIAS(createElementNS, dom_document_create_element_ns, arginfo_dom_document_create_element_ns)
                    208:        PHP_FALIAS(createAttributeNS, dom_document_create_attribute_ns, arginfo_dom_document_create_attribute_ns)
                    209:        PHP_FALIAS(getElementsByTagNameNS, dom_document_get_elements_by_tag_name_ns, arginfo_dom_document_get_elements_by_tag_name_ns)
                    210:        PHP_FALIAS(getElementById, dom_document_get_element_by_id, arginfo_dom_document_get_element_by_id)
                    211:        PHP_FALIAS(adoptNode, dom_document_adopt_node, arginfo_dom_document_adopt_node)
                    212:        PHP_FALIAS(normalizeDocument, dom_document_normalize_document, arginfo_dom_document_normalize_document)
                    213:        PHP_FALIAS(renameNode, dom_document_rename_node, arginfo_dom_document_rename_node)
                    214:        PHP_ME(domdocument, load, arginfo_dom_document_load, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
                    215:        PHP_FALIAS(save, dom_document_save, arginfo_dom_document_save)
                    216:        PHP_ME(domdocument, loadXML, arginfo_dom_document_loadxml, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
                    217:        PHP_FALIAS(saveXML, dom_document_savexml, arginfo_dom_document_savexml)
                    218:        PHP_ME(domdocument, __construct, arginfo_dom_document_construct, ZEND_ACC_PUBLIC)
                    219:        PHP_FALIAS(validate, dom_document_validate, arginfo_dom_document_validate)
                    220:        PHP_FALIAS(xinclude, dom_document_xinclude, arginfo_dom_document_xinclude)
                    221: #if defined(LIBXML_HTML_ENABLED)
                    222:        PHP_ME(domdocument, loadHTML, arginfo_dom_document_loadhtml, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
                    223:        PHP_ME(domdocument, loadHTMLFile, arginfo_dom_document_loadhtmlfile, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
                    224:        PHP_FALIAS(saveHTML, dom_document_save_html, arginfo_dom_document_savehtml)
                    225:        PHP_FALIAS(saveHTMLFile, dom_document_save_html_file, arginfo_dom_document_savehtmlfile)
                    226: #endif  /* defined(LIBXML_HTML_ENABLED) */
                    227: #if defined(LIBXML_SCHEMAS_ENABLED)
                    228:        PHP_FALIAS(schemaValidate, dom_document_schema_validate_file, arginfo_dom_document_schema_validate_file)
                    229:        PHP_FALIAS(schemaValidateSource, dom_document_schema_validate_xml, arginfo_dom_document_schema_validate_xml)
                    230:        PHP_FALIAS(relaxNGValidate, dom_document_relaxNG_validate_file, arginfo_dom_document_relaxNG_validate_file)
                    231:        PHP_FALIAS(relaxNGValidateSource, dom_document_relaxNG_validate_xml, arginfo_dom_document_relaxNG_validate_xml)
                    232: #endif
                    233:        PHP_ME(domdocument, registerNodeClass, arginfo_dom_document_registernodeclass, ZEND_ACC_PUBLIC)
                    234:        PHP_FE_END
                    235: };
                    236: /* }}} */
                    237: 
                    238: /* {{{ docType DOMDocumentType 
                    239: readonly=yes 
                    240: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-B63ED1A31
                    241: Since: 
                    242: */
                    243: int dom_document_doctype_read(dom_object *obj, zval **retval TSRMLS_DC)
                    244: {
                    245:        xmlDoc *docp;
                    246:        xmlDtdPtr dtdptr;
                    247:        int ret;
                    248: 
                    249:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    250: 
                    251:        if (docp == NULL) {
                    252:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    253:                return FAILURE;
                    254:        }
                    255: 
                    256:        ALLOC_ZVAL(*retval);
                    257: 
                    258:        dtdptr = xmlGetIntSubset(docp);
                    259:        if (!dtdptr) {
                    260:                ZVAL_NULL(*retval);
                    261:                return SUCCESS;
                    262:        }
                    263: 
1.1.1.2 ! misho     264:        if (NULL == (*retval = php_dom_create_object((xmlNodePtr) dtdptr, &ret, *retval, obj TSRMLS_CC))) {
1.1       misho     265:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot create required DOM object");
                    266:                return FAILURE;
                    267:        }
                    268:        return SUCCESS;
                    269:        
                    270: }
                    271: 
                    272: /* }}} */
                    273: 
                    274: /* {{{ implementation  DOMImplementation       
                    275: readonly=yes 
                    276: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1B793EBA
                    277: Since: 
                    278: */
                    279: int dom_document_implementation_read(dom_object *obj, zval **retval TSRMLS_DC)
                    280: {
                    281:        ALLOC_ZVAL(*retval);
                    282:        php_dom_create_implementation(retval TSRMLS_CC);
                    283:        return SUCCESS;
                    284: }
                    285: 
                    286: /* }}} */
                    287: 
                    288: /* {{{ documentElement DOMElement      
                    289: readonly=yes 
                    290: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-87CD092
                    291: Since: 
                    292: */
                    293: int dom_document_document_element_read(dom_object *obj, zval **retval TSRMLS_DC)
                    294: {
                    295:        xmlDoc *docp;
                    296:        xmlNode *root;
                    297:        int ret;
                    298: 
                    299:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    300: 
                    301:        if (docp == NULL) {
                    302:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    303:                return FAILURE;
                    304:        }
                    305: 
                    306:        ALLOC_ZVAL(*retval);
                    307: 
                    308:        root = xmlDocGetRootElement(docp);
                    309:        if (!root) {
                    310:                ZVAL_NULL(*retval);
                    311:                return SUCCESS;
                    312:        }
                    313: 
1.1.1.2 ! misho     314:        if (NULL == (*retval = php_dom_create_object(root, &ret, *retval, obj TSRMLS_CC))) {
1.1       misho     315:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot create required DOM object");
                    316:                return FAILURE;
                    317:        }
                    318:        return SUCCESS;
                    319: }
                    320: 
                    321: /* }}} */
                    322: 
                    323: /* {{{ encoding        string
                    324: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-encoding
                    325: Since: DOM Level 3
                    326: */
                    327: int dom_document_encoding_read(dom_object *obj, zval **retval TSRMLS_DC)
                    328: {
                    329:        xmlDoc *docp;
                    330:        char *encoding;
                    331: 
                    332:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    333: 
                    334:        if (docp == NULL) {
                    335:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    336:                return FAILURE;
                    337:        }
                    338: 
                    339:        encoding = (char *) docp->encoding;
                    340:        ALLOC_ZVAL(*retval);
                    341: 
                    342:        if (encoding != NULL) {
                    343:                ZVAL_STRING(*retval, encoding, 1);
                    344:        } else {
                    345:                ZVAL_NULL(*retval);
                    346:        }
                    347: 
                    348:        return SUCCESS;
                    349: }
                    350: 
                    351: int dom_document_encoding_write(dom_object *obj, zval *newval TSRMLS_DC)
                    352: {
                    353:        zval value_copy;
                    354:        xmlDoc *docp;
                    355:        xmlCharEncodingHandlerPtr handler;
                    356: 
                    357:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    358: 
                    359:        if (docp == NULL) {
                    360:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    361:                return FAILURE;
                    362:        }
                    363: 
                    364:        if (newval->type != IS_STRING) {
                    365:                if(Z_REFCOUNT_P(newval) > 1) {
                    366:                        value_copy = *newval;
                    367:                        zval_copy_ctor(&value_copy);
                    368:                        newval = &value_copy;
                    369:                }
                    370:                convert_to_string(newval);
                    371:        }
                    372: 
                    373:        handler = xmlFindCharEncodingHandler(Z_STRVAL_P(newval));
                    374: 
                    375:     if (handler != NULL) {
                    376:                xmlCharEncCloseFunc(handler);
                    377:                if (docp->encoding != NULL) {
                    378:                        xmlFree((xmlChar *)docp->encoding);
                    379:                }
                    380:                docp->encoding = xmlStrdup((const xmlChar *) Z_STRVAL_P(newval));
                    381:     } else {
                    382:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Document Encoding");
                    383:     }
                    384: 
                    385:        if (newval == &value_copy) {
                    386:                zval_dtor(newval);
                    387:        }
                    388: 
                    389:        return SUCCESS;
                    390: }
                    391: 
                    392: /* }}} */
                    393: 
                    394: /* {{{ standalone      boolean 
                    395: readonly=no 
                    396: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-standalone
                    397: Since: DOM Level 3
                    398: */
                    399: int dom_document_standalone_read(dom_object *obj, zval **retval TSRMLS_DC)
                    400: {
                    401:        xmlDoc *docp;
                    402:        int standalone;
                    403: 
                    404:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    405: 
                    406:        if (docp == NULL) {
                    407:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    408:                return FAILURE;
                    409:        }
                    410: 
                    411:        ALLOC_ZVAL(*retval);
                    412:        standalone = docp->standalone;
                    413:        ZVAL_BOOL(*retval, standalone);
                    414: 
                    415:        return SUCCESS;
                    416: }
                    417: 
                    418: int dom_document_standalone_write(dom_object *obj, zval *newval TSRMLS_DC)
                    419: {
                    420:        zval value_copy;
                    421:        xmlDoc *docp;
                    422:        int standalone;
                    423: 
                    424:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    425: 
                    426:        if (docp == NULL) {
                    427:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    428:                return FAILURE;
                    429:        }
                    430: 
                    431:        if(Z_REFCOUNT_P(newval) > 1) {
                    432:                value_copy = *newval;
                    433:                zval_copy_ctor(&value_copy);
                    434:                newval = &value_copy;
                    435:        }
                    436:        convert_to_long(newval);
                    437: 
                    438:        standalone = Z_LVAL_P(newval);
                    439:     if (standalone > 0) {
                    440:         docp->standalone = 1;
                    441:     }
                    442:     else if (standalone < 0) {
                    443:         docp->standalone = -1;
                    444:     }
                    445:     else {
                    446:         docp->standalone = 0;
                    447:     }
                    448: 
                    449:        if (newval == &value_copy) {
                    450:                zval_dtor(newval);
                    451:        }
                    452: 
                    453:        return SUCCESS;
                    454: }
                    455: 
                    456: /* }}} */
                    457: 
                    458: /* {{{ version string  
                    459: readonly=no
                    460: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-version
                    461: Since: DOM Level 3
                    462: */
                    463: int dom_document_version_read(dom_object *obj, zval **retval TSRMLS_DC)
                    464: {
                    465:        xmlDoc *docp;
                    466:        char *version;
                    467: 
                    468:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    469: 
                    470:        if (docp == NULL) {
                    471:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    472:                return FAILURE;
                    473:        }
                    474: 
                    475:        version = (char *) docp->version;
                    476:        ALLOC_ZVAL(*retval);
                    477: 
                    478:        if (version != NULL) {
                    479:                ZVAL_STRING(*retval, version, 1);
                    480:        } else {
                    481:                ZVAL_NULL(*retval);
                    482:        }
                    483: 
                    484:        return SUCCESS;
                    485: }
                    486: 
                    487: int dom_document_version_write(dom_object *obj, zval *newval TSRMLS_DC)
                    488: {
                    489:        zval value_copy;
                    490:        xmlDoc *docp;
                    491: 
                    492:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    493: 
                    494:        if (docp == NULL) {
                    495:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    496:                return FAILURE;
                    497:        }
                    498: 
                    499:        if (docp->version != NULL) {
                    500:                xmlFree((xmlChar *) docp->version );
                    501:        }
                    502: 
                    503:        if (newval->type != IS_STRING) {
                    504:                if(Z_REFCOUNT_P(newval) > 1) {
                    505:                        value_copy = *newval;
                    506:                        zval_copy_ctor(&value_copy);
                    507:                        newval = &value_copy;
                    508:                }
                    509:                convert_to_string(newval);
                    510:        }
                    511: 
                    512:        docp->version = xmlStrdup((const xmlChar *) Z_STRVAL_P(newval));
                    513: 
                    514:        if (newval == &value_copy) {
                    515:                zval_dtor(newval);
                    516:        }
                    517: 
                    518:        return SUCCESS;
                    519: }
                    520: 
                    521: /* }}} */
                    522: 
                    523: /* {{{ strictErrorChecking     boolean 
                    524: readonly=no 
                    525: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-strictErrorChecking
                    526: Since: DOM Level 3
                    527: */
                    528: int dom_document_strict_error_checking_read(dom_object *obj, zval **retval TSRMLS_DC)
                    529: {
                    530:        dom_doc_propsptr doc_prop;
                    531: 
                    532:        ALLOC_ZVAL(*retval);
                    533:        if (obj->document) {
                    534:                doc_prop = dom_get_doc_props(obj->document);
                    535:                ZVAL_BOOL(*retval, doc_prop->stricterror);
                    536:        } else {
                    537:                ZVAL_FALSE(*retval);
                    538:        }
                    539:        return SUCCESS;
                    540: }
                    541: 
                    542: int dom_document_strict_error_checking_write(dom_object *obj, zval *newval TSRMLS_DC)
                    543: {
                    544:        zval value_copy;
                    545:        dom_doc_propsptr doc_prop;
                    546: 
                    547:        if(Z_REFCOUNT_P(newval) > 1) {
                    548:                value_copy = *newval;
                    549:                zval_copy_ctor(&value_copy);
                    550:                newval = &value_copy;
                    551:        }
                    552:        convert_to_boolean(newval);
                    553: 
                    554:        if (obj->document) {
                    555:                doc_prop = dom_get_doc_props(obj->document);
                    556:                doc_prop->stricterror = Z_LVAL_P(newval);
                    557:        }
                    558: 
                    559:        if (newval == &value_copy) {
                    560:                zval_dtor(newval);
                    561:        }
                    562: 
                    563:        return SUCCESS;
                    564: }
                    565: 
                    566: /* }}} */
                    567: 
                    568: /* {{{ formatOutput    boolean 
                    569: readonly=no
                    570: */
                    571: int dom_document_format_output_read(dom_object *obj, zval **retval TSRMLS_DC)
                    572: {
                    573:        dom_doc_propsptr doc_prop;
                    574: 
                    575:        ALLOC_ZVAL(*retval);
                    576:        if (obj->document) {
                    577:                doc_prop = dom_get_doc_props(obj->document);
                    578:                ZVAL_BOOL(*retval, doc_prop->formatoutput);
                    579:        } else {
                    580:                ZVAL_FALSE(*retval);
                    581:        }
                    582:        return SUCCESS;
                    583: }
                    584: 
                    585: int dom_document_format_output_write(dom_object *obj, zval *newval TSRMLS_DC)
                    586: {
                    587:        zval value_copy;
                    588:        dom_doc_propsptr doc_prop;
                    589: 
                    590:        if(Z_REFCOUNT_P(newval) > 1) {
                    591:                value_copy = *newval;
                    592:                zval_copy_ctor(&value_copy);
                    593:                newval = &value_copy;
                    594:        }
                    595:        convert_to_boolean(newval);
                    596: 
                    597:        if (obj->document) {
                    598:                doc_prop = dom_get_doc_props(obj->document);
                    599:                doc_prop->formatoutput = Z_LVAL_P(newval);
                    600:        }
                    601: 
                    602:        if (newval == &value_copy) {
                    603:                zval_dtor(newval);
                    604:        }
                    605: 
                    606:        return SUCCESS;
                    607: }
                    608: /* }}} */
                    609: 
                    610: /* {{{ validateOnParse boolean 
                    611: readonly=no
                    612: */
                    613: int    dom_document_validate_on_parse_read(dom_object *obj, zval **retval TSRMLS_DC)
                    614: {
                    615:        dom_doc_propsptr doc_prop;
                    616: 
                    617:        ALLOC_ZVAL(*retval);
                    618:        if (obj->document) {
                    619:                doc_prop = dom_get_doc_props(obj->document);
                    620:                ZVAL_BOOL(*retval, doc_prop->validateonparse);
                    621:        } else {
                    622:                ZVAL_FALSE(*retval);
                    623:        }
                    624:        return SUCCESS;
                    625: }
                    626: 
                    627: int dom_document_validate_on_parse_write(dom_object *obj, zval *newval TSRMLS_DC)
                    628: {
                    629:        zval value_copy;
                    630:        dom_doc_propsptr doc_prop;
                    631: 
                    632:        if(Z_REFCOUNT_P(newval) > 1) {
                    633:                value_copy = *newval;
                    634:                zval_copy_ctor(&value_copy);
                    635:                newval = &value_copy;
                    636:        }
                    637:        convert_to_boolean(newval);
                    638: 
                    639:        if (obj->document) {
                    640:                doc_prop = dom_get_doc_props(obj->document);
                    641:                doc_prop->validateonparse = Z_LVAL_P(newval);
                    642:        }
                    643: 
                    644:        if (newval == &value_copy) {
                    645:                zval_dtor(newval);
                    646:        }
                    647: 
                    648:        return SUCCESS;
                    649: }
                    650: /* }}} */
                    651: 
                    652: /* {{{ resolveExternals        boolean 
                    653: readonly=no
                    654: */
                    655: int dom_document_resolve_externals_read(dom_object *obj, zval **retval TSRMLS_DC)
                    656: {
                    657:        dom_doc_propsptr doc_prop;
                    658: 
                    659:        ALLOC_ZVAL(*retval);
                    660:        if (obj->document) {
                    661:                doc_prop = dom_get_doc_props(obj->document);
                    662:                ZVAL_BOOL(*retval, doc_prop->resolveexternals);
                    663:        } else {
                    664:                ZVAL_FALSE(*retval);
                    665:        }
                    666:        return SUCCESS;
                    667: }
                    668: 
                    669: int dom_document_resolve_externals_write(dom_object *obj, zval *newval TSRMLS_DC)
                    670: {
                    671:        zval value_copy;
                    672:        dom_doc_propsptr doc_prop;
                    673: 
                    674:        if(Z_REFCOUNT_P(newval) > 1) {
                    675:                value_copy = *newval;
                    676:                zval_copy_ctor(&value_copy);
                    677:                newval = &value_copy;
                    678:        }
                    679:        convert_to_boolean(newval);
                    680: 
                    681:        if (obj->document) {
                    682:                doc_prop = dom_get_doc_props(obj->document);
                    683:                doc_prop->resolveexternals = Z_LVAL_P(newval);
                    684:        }
                    685: 
                    686:        if (newval == &value_copy) {
                    687:                zval_dtor(newval);
                    688:        }
                    689: 
                    690:        return SUCCESS;
                    691: }
                    692: /* }}} */
                    693: 
                    694: /* {{{ preserveWhiteSpace      boolean 
                    695: readonly=no
                    696: */
                    697: int dom_document_preserve_whitespace_read(dom_object *obj, zval **retval TSRMLS_DC)
                    698: {
                    699:        dom_doc_propsptr doc_prop;
                    700: 
                    701:        ALLOC_ZVAL(*retval);
                    702:        if (obj->document) {
                    703:                doc_prop = dom_get_doc_props(obj->document);
                    704:                ZVAL_BOOL(*retval, doc_prop->preservewhitespace);
                    705:        } else {
                    706:                ZVAL_FALSE(*retval);
                    707:        }
                    708:        return SUCCESS;
                    709: }
                    710: 
                    711: int dom_document_preserve_whitespace_write(dom_object *obj, zval *newval TSRMLS_DC)
                    712: {
                    713:        zval value_copy;
                    714:        dom_doc_propsptr doc_prop;
                    715: 
                    716:        if(Z_REFCOUNT_P(newval) > 1) {
                    717:                value_copy = *newval;
                    718:                zval_copy_ctor(&value_copy);
                    719:                newval = &value_copy;
                    720:        }
                    721:        convert_to_boolean(newval);
                    722: 
                    723:        if (obj->document) {
                    724:                doc_prop = dom_get_doc_props(obj->document);
                    725:                doc_prop->preservewhitespace = Z_LVAL_P(newval);
                    726:        }
                    727: 
                    728:        if (newval == &value_copy) {
                    729:                zval_dtor(newval);
                    730:        }
                    731: 
                    732:        return SUCCESS;
                    733: }
                    734: /* }}} */
                    735: 
                    736: /* {{{ recover boolean 
                    737: readonly=no
                    738: */
                    739: int dom_document_recover_read(dom_object *obj, zval **retval TSRMLS_DC)
                    740: {
                    741:        dom_doc_propsptr doc_prop;
                    742: 
                    743:        ALLOC_ZVAL(*retval);
                    744:        if (obj->document) {
                    745:                doc_prop = dom_get_doc_props(obj->document);
                    746:                ZVAL_BOOL(*retval, doc_prop->recover);
                    747:        } else {
                    748:                ZVAL_FALSE(*retval);
                    749:        }
                    750:        return SUCCESS;
                    751: }
                    752: 
                    753: int dom_document_recover_write(dom_object *obj, zval *newval TSRMLS_DC)
                    754: {
                    755:        zval value_copy;
                    756:        dom_doc_propsptr doc_prop;
                    757: 
                    758:        if(Z_REFCOUNT_P(newval) > 1) {
                    759:                value_copy = *newval;
                    760:                zval_copy_ctor(&value_copy);
                    761:                newval = &value_copy;
                    762:        }
                    763:        convert_to_boolean(newval);
                    764: 
                    765:        if (obj->document) {
                    766:                doc_prop = dom_get_doc_props(obj->document);
                    767:                doc_prop->recover = Z_LVAL_P(newval);
                    768:        }
                    769: 
                    770:        if (newval == &value_copy) {
                    771:                zval_dtor(newval);
                    772:        }
                    773: 
                    774:        return SUCCESS;
                    775: }
                    776: /* }}} */
                    777: 
                    778: /* {{{ substituteEntities      boolean 
                    779: readonly=no
                    780: */
                    781: int dom_document_substitue_entities_read(dom_object *obj, zval **retval TSRMLS_DC)
                    782: {
                    783:        dom_doc_propsptr doc_prop;
                    784: 
                    785:        ALLOC_ZVAL(*retval);
                    786:        if (obj->document) {
                    787:                doc_prop = dom_get_doc_props(obj->document);
                    788:                ZVAL_BOOL(*retval, doc_prop->substituteentities);
                    789:        } else {
                    790:                ZVAL_FALSE(*retval);
                    791:        }
                    792:        return SUCCESS;
                    793: }
                    794: 
                    795: int dom_document_substitue_entities_write(dom_object *obj, zval *newval TSRMLS_DC)
                    796: {
                    797:        zval value_copy;
                    798:        dom_doc_propsptr doc_prop;
                    799: 
                    800:        if(Z_REFCOUNT_P(newval) > 1) {
                    801:                value_copy = *newval;
                    802:                zval_copy_ctor(&value_copy);
                    803:                newval = &value_copy;
                    804:        }
                    805:        convert_to_boolean(newval);
                    806: 
                    807:        if (obj->document) {
                    808:                doc_prop = dom_get_doc_props(obj->document);
                    809:                doc_prop->substituteentities = Z_LVAL_P(newval);
                    810:        }
                    811: 
                    812:        if (newval == &value_copy) {
                    813:                zval_dtor(newval);
                    814:        }
                    815: 
                    816:        return SUCCESS;
                    817: }
                    818: /* }}} */
                    819: 
                    820: /* {{{ documentURI     string  
                    821: readonly=no 
                    822: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-documentURI
                    823: Since: DOM Level 3
                    824: */
                    825: int dom_document_document_uri_read(dom_object *obj, zval **retval TSRMLS_DC)
                    826: {
                    827:        xmlDoc *docp;
                    828:        char *url;
                    829: 
                    830:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    831: 
                    832:        if (docp == NULL) {
                    833:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    834:                return FAILURE;
                    835:        }
                    836: 
                    837:        ALLOC_ZVAL(*retval);
                    838:        url = (char *) docp->URL;
                    839:        if (url != NULL) {
                    840:                ZVAL_STRING(*retval, url, 1);
                    841:        } else {
                    842:                ZVAL_NULL(*retval);
                    843:        }
                    844: 
                    845:        return SUCCESS;
                    846: }
                    847: 
                    848: int dom_document_document_uri_write(dom_object *obj, zval *newval TSRMLS_DC)
                    849: {
                    850:        zval value_copy;
                    851:        xmlDoc *docp;
                    852: 
                    853:        docp = (xmlDocPtr) dom_object_get_node(obj);
                    854: 
                    855:        if (docp == NULL) {
                    856:                php_dom_throw_error(INVALID_STATE_ERR, 0 TSRMLS_CC);
                    857:                return FAILURE;
                    858:        }
                    859: 
                    860:        if (docp->URL != NULL) {
                    861:                xmlFree((xmlChar *) docp->URL);
                    862:        }
                    863: 
                    864:        if (newval->type != IS_STRING) {
                    865:                if(Z_REFCOUNT_P(newval) > 1) {
                    866:                        value_copy = *newval;
                    867:                        zval_copy_ctor(&value_copy);
                    868:                        newval = &value_copy;
                    869:                }
                    870:                convert_to_string(newval);
                    871:        }
                    872: 
                    873:        docp->URL = xmlStrdup((const xmlChar *) Z_STRVAL_P(newval));
                    874: 
                    875:        if (newval == &value_copy) {
                    876:                zval_dtor(newval);
                    877:        }
                    878: 
                    879:        return SUCCESS;
                    880: }
                    881: 
                    882: /* }}} */
                    883: 
                    884: /* {{{ config  DOMConfiguration        
                    885: readonly=yes 
                    886: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-config
                    887: Since: DOM Level 3
                    888: */
                    889: int dom_document_config_read(dom_object *obj, zval **retval TSRMLS_DC)
                    890: {
                    891:        ALLOC_ZVAL(*retval);
                    892:        ZVAL_NULL(*retval);
                    893:        return SUCCESS;
                    894: }
                    895: 
                    896: /* }}} */
                    897: 
                    898: /* {{{ proto DOMElement dom_document_create_element(string tagName [, string value]);
                    899: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-2141741547
                    900: Since: 
                    901: */
                    902: PHP_FUNCTION(dom_document_create_element)
                    903: {
1.1.1.2 ! misho     904:        zval *id;
1.1       misho     905:        xmlNode *node;
                    906:        xmlDocPtr docp;
                    907:        dom_object *intern;
                    908:        int ret, name_len, value_len;
                    909:        char *name, *value = NULL;
                    910: 
                    911:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os|s", &id, dom_document_class_entry, &name, &name_len, &value, &value_len) == FAILURE) {
                    912:                return;
                    913:        }
                    914: 
                    915:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                    916: 
                    917:        if (xmlValidateName((xmlChar *) name, 0) != 0) {
                    918:                php_dom_throw_error(INVALID_CHARACTER_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                    919:                RETURN_FALSE;
                    920:        }
                    921: 
                    922:        node = xmlNewDocNode(docp, NULL, name, value);
                    923:        if (!node) {
                    924:                RETURN_FALSE;
                    925:        }
                    926: 
1.1.1.2 ! misho     927:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho     928: }
                    929: /* }}} end dom_document_create_element */
                    930: 
                    931: /* {{{ proto DOMDocumentFragment dom_document_create_document_fragment();
                    932: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-35CB04B5
                    933: Since: 
                    934: */
                    935: PHP_FUNCTION(dom_document_create_document_fragment)
                    936: {
1.1.1.2 ! misho     937:        zval *id;
1.1       misho     938:        xmlNode *node;
                    939:        xmlDocPtr docp;
                    940:        dom_object *intern;
                    941:        int ret;
                    942: 
                    943:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &id, dom_document_class_entry) == FAILURE) {
                    944:                return;
                    945:        }
                    946: 
                    947:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                    948: 
                    949:        node =  xmlNewDocFragment(docp);
                    950:        if (!node) {
                    951:                RETURN_FALSE;
                    952:        }
                    953: 
1.1.1.2 ! misho     954:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho     955: }
                    956: /* }}} end dom_document_create_document_fragment */
                    957: 
                    958: /* {{{ proto DOMText dom_document_create_text_node(string data);
                    959: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1975348127
                    960: Since: 
                    961: */
                    962: PHP_FUNCTION(dom_document_create_text_node)
                    963: {
1.1.1.2 ! misho     964:        zval *id;
1.1       misho     965:        xmlNode *node;
                    966:        xmlDocPtr docp;
                    967:        int ret, value_len;
                    968:        dom_object *intern;
                    969:        char *value;
                    970: 
                    971:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &value, &value_len) == FAILURE) {
                    972:                return;
                    973:        }
                    974: 
                    975:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                    976: 
                    977:        node = xmlNewDocText(docp, (xmlChar *) value);
                    978:        if (!node) {
                    979:                RETURN_FALSE;
                    980:        }
                    981: 
1.1.1.2 ! misho     982:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho     983: }
                    984: /* }}} end dom_document_create_text_node */
                    985: 
                    986: /* {{{ proto DOMComment dom_document_create_comment(string data);
                    987: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1334481328
                    988: Since: 
                    989: */
                    990: PHP_FUNCTION(dom_document_create_comment)
                    991: {
1.1.1.2 ! misho     992:        zval *id;
1.1       misho     993:        xmlNode *node;
                    994:        xmlDocPtr docp;
                    995:        int ret, value_len;
                    996:        dom_object *intern;
                    997:        char *value;
                    998: 
                    999:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &value, &value_len) == FAILURE) {
                   1000:                return;
                   1001:        }
                   1002: 
                   1003:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1004: 
                   1005:        node = xmlNewDocComment(docp, (xmlChar *) value);
                   1006:        if (!node) {
                   1007:                RETURN_FALSE;
                   1008:        }
                   1009: 
1.1.1.2 ! misho    1010:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho    1011: }
                   1012: /* }}} end dom_document_create_comment */
                   1013: 
                   1014: /* {{{ proto DOMCdataSection dom_document_create_cdatasection(string data);
                   1015: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-D26C0AF8
                   1016: Since: 
                   1017: */
                   1018: PHP_FUNCTION(dom_document_create_cdatasection)
                   1019: {
1.1.1.2 ! misho    1020:        zval *id;
1.1       misho    1021:        xmlNode *node;
                   1022:        xmlDocPtr docp;
                   1023:        int ret, value_len;
                   1024:        dom_object *intern;
                   1025:        char *value;
                   1026: 
                   1027:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &value, &value_len) == FAILURE) {
                   1028:                return;
                   1029:        }
                   1030: 
                   1031:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1032: 
                   1033:        node = xmlNewCDataBlock(docp, (xmlChar *) value, value_len);
                   1034:        if (!node) {
                   1035:                RETURN_FALSE;
                   1036:        }
                   1037: 
1.1.1.2 ! misho    1038:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho    1039: }
                   1040: /* }}} end dom_document_create_cdatasection */
                   1041: 
                   1042: /* {{{ proto DOMProcessingInstruction dom_document_create_processing_instruction(string target, string data);
                   1043: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-135944439
                   1044: Since: 
                   1045: */
                   1046: PHP_FUNCTION(dom_document_create_processing_instruction)
                   1047: {
1.1.1.2 ! misho    1048:        zval *id;
1.1       misho    1049:        xmlNode *node;
                   1050:        xmlDocPtr docp;
                   1051:        int ret, value_len, name_len = 0;
                   1052:        dom_object *intern;
                   1053:        char *name, *value = NULL;
                   1054: 
                   1055:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os|s", &id, dom_document_class_entry, &name, &name_len, &value, &value_len) == FAILURE) {
                   1056:                return;
                   1057:        }
                   1058: 
                   1059:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1060: 
                   1061:        if (xmlValidateName((xmlChar *) name, 0) != 0) {
                   1062:                php_dom_throw_error(INVALID_CHARACTER_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1063:                RETURN_FALSE;
                   1064:        }
                   1065: 
                   1066:        node = xmlNewPI((xmlChar *) name, (xmlChar *) value);
                   1067:        if (!node) {
                   1068:                RETURN_FALSE;
                   1069:        }
                   1070: 
                   1071:        node->doc = docp;
                   1072: 
1.1.1.2 ! misho    1073:        DOM_RET_OBJ(node, &ret, intern);
1.1       misho    1074: }
                   1075: /* }}} end dom_document_create_processing_instruction */
                   1076: 
                   1077: /* {{{ proto DOMAttr dom_document_create_attribute(string name);
                   1078: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1084891198
                   1079: Since: 
                   1080: */
                   1081: PHP_FUNCTION(dom_document_create_attribute)
                   1082: {
1.1.1.2 ! misho    1083:        zval *id;
1.1       misho    1084:        xmlAttrPtr node;
                   1085:        xmlDocPtr docp;
                   1086:        int ret, name_len;
                   1087:        dom_object *intern;
                   1088:        char *name;
                   1089: 
                   1090:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &name, &name_len) == FAILURE) {
                   1091:                return;
                   1092:        }
                   1093: 
                   1094:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1095: 
                   1096:        if (xmlValidateName((xmlChar *) name, 0) != 0) {
                   1097:                php_dom_throw_error(INVALID_CHARACTER_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1098:                RETURN_FALSE;
                   1099:        }
                   1100: 
                   1101:        node = xmlNewDocProp(docp, (xmlChar *) name, NULL);
                   1102:        if (!node) {
                   1103:                RETURN_FALSE;
                   1104:        }
                   1105: 
1.1.1.2 ! misho    1106:        DOM_RET_OBJ((xmlNodePtr) node, &ret, intern);
1.1       misho    1107: 
                   1108: }
                   1109: /* }}} end dom_document_create_attribute */
                   1110: 
                   1111: /* {{{ proto DOMEntityReference dom_document_create_entity_reference(string name);
                   1112: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-392B75AE
                   1113: Since: 
                   1114: */
                   1115: PHP_FUNCTION(dom_document_create_entity_reference)
                   1116: {
1.1.1.2 ! misho    1117:        zval *id;
1.1       misho    1118:        xmlNode *node;
                   1119:        xmlDocPtr docp = NULL;
                   1120:        dom_object *intern;
                   1121:        int ret, name_len;
                   1122:        char *name;
                   1123: 
                   1124:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &name, &name_len) == FAILURE) {
                   1125:                return;
                   1126:        }
                   1127: 
                   1128:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1129: 
                   1130:        if (xmlValidateName((xmlChar *) name, 0) != 0) {
                   1131:                php_dom_throw_error(INVALID_CHARACTER_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1132:                RETURN_FALSE;
                   1133:        }
                   1134: 
                   1135:        node = xmlNewReference(docp, name);
                   1136:        if (!node) {
                   1137:                RETURN_FALSE;
                   1138:        }
                   1139: 
1.1.1.2 ! misho    1140:        DOM_RET_OBJ((xmlNodePtr) node, &ret, intern);
1.1       misho    1141: }
                   1142: /* }}} end dom_document_create_entity_reference */
                   1143: 
                   1144: /* {{{ proto DOMNodeList dom_document_get_elements_by_tag_name(string tagname);
                   1145: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-A6C9094
                   1146: Since: 
                   1147: */
                   1148: PHP_FUNCTION(dom_document_get_elements_by_tag_name)
                   1149: {
                   1150:        zval *id;
                   1151:        xmlDocPtr docp;
                   1152:        int name_len;
                   1153:        dom_object *intern, *namednode;
                   1154:        char *name;
                   1155:        xmlChar *local;
                   1156: 
                   1157:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &name, &name_len) == FAILURE) {
                   1158:                return;
                   1159:        }
                   1160: 
                   1161:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1162: 
                   1163:        php_dom_create_interator(return_value, DOM_NODELIST TSRMLS_CC);
                   1164:        namednode = (dom_object *)zend_objects_get_address(return_value TSRMLS_CC);
                   1165:        local = xmlCharStrndup(name, name_len);
                   1166:        dom_namednode_iter(intern, 0, namednode, NULL, local, NULL TSRMLS_CC);
                   1167: }
                   1168: /* }}} end dom_document_get_elements_by_tag_name */
                   1169: 
                   1170: /* {{{ proto DOMNode dom_document_import_node(DOMNode importedNode, boolean deep);
                   1171: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Core-Document-importNode
                   1172: Since: DOM Level 2
                   1173: */
                   1174: PHP_FUNCTION(dom_document_import_node)
                   1175: {
                   1176:        zval *id, *node;
                   1177:        xmlDocPtr docp;
                   1178:        xmlNodePtr nodep, retnodep;
                   1179:        dom_object *intern, *nodeobj;
                   1180:        int ret; 
                   1181:        long recursive = 0;
                   1182: 
                   1183:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "OO|l", &id, dom_document_class_entry, &node, dom_node_class_entry, &recursive) == FAILURE) {
                   1184:                return;
                   1185:        }
                   1186: 
                   1187:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1188: 
                   1189:        DOM_GET_OBJ(nodep, node, xmlNodePtr, nodeobj);
                   1190: 
                   1191:        if (nodep->type == XML_HTML_DOCUMENT_NODE || nodep->type == XML_DOCUMENT_NODE 
                   1192:                || nodep->type == XML_DOCUMENT_TYPE_NODE) {
                   1193:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot import: Node Type Not Supported");
                   1194:                RETURN_FALSE;
                   1195:        }
                   1196: 
                   1197:        if (nodep->doc == docp) {
                   1198:                retnodep = nodep;
                   1199:        } else {
                   1200:                if ((recursive == 0) && (nodep->type == XML_ELEMENT_NODE)) {
                   1201:                        recursive = 2;
                   1202:                }
                   1203:                retnodep = xmlDocCopyNode(nodep, docp, recursive);
                   1204:                if (!retnodep) {
                   1205:                        RETURN_FALSE;
                   1206:                }
                   1207: 
                   1208:                if ((retnodep->type == XML_ATTRIBUTE_NODE) && (nodep->ns != NULL)) {
                   1209:                        xmlNsPtr nsptr = NULL;
                   1210:                        xmlNodePtr root = xmlDocGetRootElement(docp);
                   1211: 
                   1212:                        nsptr = xmlSearchNsByHref (nodep->doc, root, nodep->ns->href);
                   1213:                        if (nsptr == NULL) {
                   1214:                                int errorcode;
1.1.1.2 ! misho    1215:                                nsptr = dom_get_ns(root, (char *) nodep->ns->href, &errorcode, (char *) nodep->ns->prefix);
1.1       misho    1216:                        }
                   1217:                        xmlSetNs(retnodep, nsptr);
                   1218:                }
                   1219:        }
                   1220: 
1.1.1.2 ! misho    1221:        DOM_RET_OBJ((xmlNodePtr) retnodep, &ret, intern);
1.1       misho    1222: }
                   1223: /* }}} end dom_document_import_node */
                   1224: 
                   1225: /* {{{ proto DOMElement dom_document_create_element_ns(string namespaceURI, string qualifiedName [,string value]);
                   1226: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-DocCrElNS
                   1227: Since: DOM Level 2
                   1228: */
                   1229: PHP_FUNCTION(dom_document_create_element_ns)
                   1230: {
1.1.1.2 ! misho    1231:        zval *id;
1.1       misho    1232:        xmlDocPtr docp;
                   1233:        xmlNodePtr nodep = NULL;
                   1234:        xmlNsPtr nsptr = NULL;
                   1235:        int ret, uri_len = 0, name_len = 0, value_len = 0;
                   1236:        char *uri, *name, *value = NULL;
                   1237:        char *localname = NULL, *prefix = NULL;
                   1238:        int errorcode;
                   1239:        dom_object *intern;
                   1240: 
                   1241:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os!s|s", &id, dom_document_class_entry, &uri, &uri_len, &name, &name_len, &value, &value_len) == FAILURE) {
                   1242:                return;
                   1243:        }
                   1244: 
                   1245:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1246: 
                   1247:        errorcode = dom_check_qname(name, &localname, &prefix, uri_len, name_len);
                   1248: 
                   1249:        if (errorcode == 0) {
                   1250:                if (xmlValidateName((xmlChar *) localname, 0) == 0) {
                   1251:                        nodep = xmlNewDocNode (docp, NULL, localname, value);
                   1252:                        if (nodep != NULL && uri != NULL) {
                   1253:                                nsptr = xmlSearchNsByHref (nodep->doc, nodep, uri);
                   1254:                                if (nsptr == NULL) {
                   1255:                                        nsptr = dom_get_ns(nodep, uri, &errorcode, prefix);
                   1256:                                }
                   1257:                                xmlSetNs(nodep, nsptr);
                   1258:                        }
                   1259:                } else {
                   1260:                        errorcode = INVALID_CHARACTER_ERR;
                   1261:                }
                   1262:        }
                   1263: 
                   1264:        xmlFree(localname);
                   1265:        if (prefix != NULL) {
                   1266:                xmlFree(prefix);
                   1267:        }
                   1268: 
                   1269:        if (errorcode != 0) {
                   1270:                if (nodep != NULL) {
                   1271:                        xmlFreeNode(nodep);
                   1272:                }
                   1273:                php_dom_throw_error(errorcode, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1274:                RETURN_FALSE;
                   1275:        }
                   1276: 
                   1277:        if (nodep == NULL) {
                   1278:                RETURN_FALSE;
                   1279:        }
                   1280: 
                   1281:        
                   1282:        nodep->ns = nsptr;
                   1283: 
1.1.1.2 ! misho    1284:        DOM_RET_OBJ(nodep, &ret, intern);
1.1       misho    1285: }
                   1286: /* }}} end dom_document_create_element_ns */
                   1287: 
                   1288: /* {{{ proto DOMAttr dom_document_create_attribute_ns(string namespaceURI, string qualifiedName);
                   1289: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-DocCrAttrNS
                   1290: Since: DOM Level 2
                   1291: */
                   1292: PHP_FUNCTION(dom_document_create_attribute_ns)
                   1293: {
1.1.1.2 ! misho    1294:        zval *id;
1.1       misho    1295:        xmlDocPtr docp;
                   1296:        xmlNodePtr nodep = NULL, root;
                   1297:        xmlNsPtr nsptr;
                   1298:        int ret, uri_len = 0, name_len = 0;
                   1299:        char *uri, *name;
                   1300:        char *localname = NULL, *prefix = NULL;
                   1301:        dom_object *intern;
                   1302:        int errorcode;
                   1303: 
                   1304:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os!s", &id, dom_document_class_entry, &uri, &uri_len, &name, &name_len) == FAILURE) {
                   1305:                return;
                   1306:        }
                   1307: 
                   1308:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1309: 
                   1310:        root = xmlDocGetRootElement(docp);
                   1311:        if (root != NULL) {
                   1312:                errorcode = dom_check_qname(name, &localname, &prefix, uri_len, name_len);
                   1313:                if (errorcode == 0) {
                   1314:                        if (xmlValidateName((xmlChar *) localname, 0) == 0) {
                   1315:                                nodep = (xmlNodePtr) xmlNewDocProp(docp, localname, NULL);
                   1316:                                if (nodep != NULL && uri_len > 0) {
                   1317:                                        nsptr = xmlSearchNsByHref (nodep->doc, root, uri);
                   1318:                                        if (nsptr == NULL) {
                   1319:                                                nsptr = dom_get_ns(root, uri, &errorcode, prefix);
                   1320:                                        }
                   1321:                                        xmlSetNs(nodep, nsptr);
                   1322:                                }
                   1323:                        } else {
                   1324:                                errorcode = INVALID_CHARACTER_ERR;
                   1325:                        }
                   1326:                }
                   1327:        } else {
                   1328:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Document Missing Root Element");
                   1329:                RETURN_FALSE;
                   1330:        }
                   1331: 
                   1332:        xmlFree(localname);
                   1333:        if (prefix != NULL) {
                   1334:                xmlFree(prefix);
                   1335:        }
                   1336: 
                   1337:        if (errorcode != 0) {
                   1338:                if (nodep != NULL) {
                   1339:                        xmlFreeProp((xmlAttrPtr) nodep);
                   1340:                }
                   1341:                php_dom_throw_error(errorcode, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1342:                RETURN_FALSE;
                   1343:        }
                   1344: 
                   1345:        if (nodep == NULL) {
                   1346:                RETURN_FALSE;
                   1347:        }
                   1348: 
1.1.1.2 ! misho    1349:        DOM_RET_OBJ(nodep, &ret, intern);
1.1       misho    1350: }
                   1351: /* }}} end dom_document_create_attribute_ns */
                   1352: 
                   1353: /* {{{ proto DOMNodeList dom_document_get_elements_by_tag_name_ns(string namespaceURI, string localName);
                   1354: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-getElBTNNS
                   1355: Since: DOM Level 2
                   1356: */
                   1357: PHP_FUNCTION(dom_document_get_elements_by_tag_name_ns)
                   1358: {
                   1359:        zval *id;
                   1360:        xmlDocPtr docp;
                   1361:        int uri_len, name_len;
                   1362:        dom_object *intern, *namednode;
                   1363:        char *uri, *name;
                   1364:        xmlChar *local, *nsuri;
                   1365: 
                   1366:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Oss", &id, dom_document_class_entry, &uri, &uri_len, &name, &name_len) == FAILURE) {
                   1367:                return;
                   1368:        }
                   1369: 
                   1370:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1371: 
                   1372:        php_dom_create_interator(return_value, DOM_NODELIST TSRMLS_CC);
                   1373:        namednode = (dom_object *)zend_objects_get_address(return_value TSRMLS_CC);
                   1374:        local = xmlCharStrndup(name, name_len);
                   1375:        nsuri = xmlCharStrndup(uri, uri_len);
                   1376:        dom_namednode_iter(intern, 0, namednode, NULL, local, nsuri TSRMLS_CC);
                   1377: }
                   1378: /* }}} end dom_document_get_elements_by_tag_name_ns */
                   1379: 
                   1380: /* {{{ proto DOMElement dom_document_get_element_by_id(string elementId);
                   1381: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-getElBId
                   1382: Since: DOM Level 2
                   1383: */
                   1384: PHP_FUNCTION(dom_document_get_element_by_id)
                   1385: {
1.1.1.2 ! misho    1386:        zval *id;
1.1       misho    1387:        xmlDocPtr docp;
                   1388:        xmlAttrPtr  attrp;
                   1389:        int ret, idname_len;
                   1390:        dom_object *intern;
                   1391:        char *idname;
                   1392: 
                   1393:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &idname, &idname_len) == FAILURE) {
                   1394:                return;
                   1395:        }
                   1396: 
                   1397:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1398: 
                   1399:        attrp = xmlGetID(docp, (xmlChar *) idname);
                   1400: 
                   1401:        if (attrp && attrp->parent) {
1.1.1.2 ! misho    1402:                DOM_RET_OBJ((xmlNodePtr) attrp->parent, &ret, intern);
1.1       misho    1403:        } else {
                   1404:                RETVAL_NULL();
                   1405:        }
                   1406: 
                   1407: }
                   1408: /* }}} end dom_document_get_element_by_id */
                   1409: 
                   1410: /* {{{ proto DOMNode dom_document_adopt_node(DOMNode source);
                   1411: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-adoptNode
                   1412: Since: DOM Level 3
                   1413: */
                   1414: PHP_FUNCTION(dom_document_adopt_node)
                   1415: {
                   1416:  DOM_NOT_IMPLEMENTED();
                   1417: }
                   1418: /* }}} end dom_document_adopt_node */
                   1419: 
                   1420: /* {{{ proto void dom_document_normalize_document();
                   1421: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-normalizeDocument
                   1422: Since: DOM Level 3
                   1423: */
                   1424: PHP_FUNCTION(dom_document_normalize_document)
                   1425: {
                   1426:        zval *id;
                   1427:        xmlDocPtr docp;
                   1428:        dom_object *intern;
                   1429: 
                   1430:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &id, dom_document_class_entry) == FAILURE) {
                   1431:                return;
                   1432:        }
                   1433: 
                   1434:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1435: 
                   1436:        dom_normalize((xmlNodePtr) docp TSRMLS_CC);
                   1437: }
                   1438: /* }}} end dom_document_normalize_document */
                   1439: 
                   1440: /* {{{ proto DOMNode dom_document_rename_node(node n, string namespaceURI, string qualifiedName);
                   1441: URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-renameNode
                   1442: Since: DOM Level 3
                   1443: */
                   1444: PHP_FUNCTION(dom_document_rename_node)
                   1445: {
                   1446:  DOM_NOT_IMPLEMENTED();
                   1447: }
                   1448: /* }}} end dom_document_rename_node */
                   1449: 
                   1450: /* {{{ proto void DOMDocument::__construct([string version], [string encoding]); */
                   1451: PHP_METHOD(domdocument, __construct)
                   1452: {
                   1453: 
                   1454:        zval *id;
                   1455:        xmlDoc *docp = NULL, *olddoc;
                   1456:        dom_object *intern;
                   1457:        char *encoding, *version = NULL;
                   1458:        int encoding_len = 0, version_len = 0, refcount;
                   1459:        zend_error_handling error_handling;
                   1460: 
                   1461:        zend_replace_error_handling(EH_THROW, dom_domexception_class_entry, &error_handling TSRMLS_CC);
                   1462:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O|ss", &id, dom_document_class_entry, &version, &version_len, &encoding, &encoding_len) == FAILURE) {
                   1463:                zend_restore_error_handling(&error_handling TSRMLS_CC);
                   1464:                return;
                   1465:        }
                   1466: 
                   1467:        zend_restore_error_handling(&error_handling TSRMLS_CC);
                   1468:        docp = xmlNewDoc(version);
                   1469: 
                   1470:        if (!docp) {
                   1471:                php_dom_throw_error(INVALID_STATE_ERR, 1 TSRMLS_CC);
                   1472:                RETURN_FALSE;
                   1473:        }
                   1474: 
                   1475:        if (encoding_len > 0) {
                   1476:                docp->encoding = (const xmlChar*)xmlStrdup(encoding);
                   1477:        }
                   1478: 
                   1479:        intern = (dom_object *)zend_object_store_get_object(id TSRMLS_CC);
                   1480:        if (intern != NULL) {
                   1481:                olddoc = (xmlDocPtr) dom_object_get_node(intern);
                   1482:                if (olddoc != NULL) {
                   1483:                        php_libxml_decrement_node_ptr((php_libxml_node_object *) intern TSRMLS_CC);
                   1484:                        refcount = php_libxml_decrement_doc_ref((php_libxml_node_object *)intern TSRMLS_CC);
                   1485:                        if (refcount != 0) {
                   1486:                                olddoc->_private = NULL;
                   1487:                        }
                   1488:                }
                   1489:                intern->document = NULL;
                   1490:                if (php_libxml_increment_doc_ref((php_libxml_node_object *)intern, docp TSRMLS_CC) == -1) {
                   1491:                        RETURN_FALSE;
                   1492:                }
                   1493:                php_libxml_increment_node_ptr((php_libxml_node_object *)intern, (xmlNodePtr)docp, (void *)intern TSRMLS_CC);
                   1494:        }
                   1495: }
                   1496: /* }}} end DOMDocument::__construct */
                   1497: 
                   1498: char *_dom_get_valid_file_path(char *source, char *resolved_path, int resolved_path_len  TSRMLS_DC) /* {{{ */
                   1499: {
                   1500:        xmlURI *uri;
                   1501:        xmlChar *escsource;
                   1502:        char *file_dest;
                   1503:        int isFileUri = 0;
                   1504: 
                   1505:        uri = xmlCreateURI();
                   1506:        escsource = xmlURIEscapeStr(source, ":");
                   1507:        xmlParseURIReference(uri, escsource);
                   1508:        xmlFree(escsource);
                   1509: 
                   1510:        if (uri->scheme != NULL) {
                   1511:                /* absolute file uris - libxml only supports localhost or empty host */
                   1512:                if (strncasecmp(source, "file:///",8) == 0) {
                   1513:                        isFileUri = 1;
                   1514: #ifdef PHP_WIN32
                   1515:                        source += 8;
                   1516: #else
                   1517:                        source += 7;
                   1518: #endif
                   1519:                } else if (strncasecmp(source, "file://localhost/",17) == 0) {
                   1520:                        isFileUri = 1;
                   1521: #ifdef PHP_WIN32
                   1522:                        source += 17;
                   1523: #else
                   1524:                        source += 16;
                   1525: #endif
                   1526:                }
                   1527:        }
                   1528: 
                   1529:        file_dest = source;
                   1530: 
                   1531:        if ((uri->scheme == NULL || isFileUri)) {
                   1532:                /* XXX possible buffer overflow if VCWD_REALPATH does not know size of resolved_path */
                   1533:                if (!VCWD_REALPATH(source, resolved_path) && !expand_filepath(source, resolved_path TSRMLS_CC)) {
                   1534:                        xmlFreeURI(uri);
                   1535:                        return NULL;
                   1536:                }
                   1537:                file_dest = resolved_path;
                   1538:        }
                   1539: 
                   1540:        xmlFreeURI(uri);
                   1541: 
                   1542:        return file_dest;
                   1543: }
                   1544: /* }}} */
                   1545: 
                   1546: static xmlDocPtr dom_document_parser(zval *id, int mode, char *source, int source_len, int options TSRMLS_DC) /* {{{ */
                   1547: {
                   1548:     xmlDocPtr ret;
                   1549:     xmlParserCtxtPtr ctxt = NULL;
                   1550:        dom_doc_propsptr doc_props;
                   1551:        dom_object *intern;
                   1552:        php_libxml_ref_obj *document = NULL;
                   1553:        int validate, recover, resolve_externals, keep_blanks, substitute_ent;
                   1554:        int resolved_path_len;
                   1555:        int old_error_reporting = 0;
                   1556:        char *directory=NULL, resolved_path[MAXPATHLEN];
                   1557: 
                   1558:        if (id != NULL) {
                   1559:                intern = (dom_object *)zend_object_store_get_object(id TSRMLS_CC);
                   1560:                document = intern->document;
                   1561:        }
                   1562: 
                   1563:        doc_props = dom_get_doc_props(document);
                   1564:        validate = doc_props->validateonparse;
                   1565:        resolve_externals = doc_props->resolveexternals;
                   1566:        keep_blanks = doc_props->preservewhitespace;
                   1567:        substitute_ent = doc_props->substituteentities;
                   1568:        recover = doc_props->recover;
                   1569: 
                   1570:        if (document == NULL) {
                   1571:                efree(doc_props);
                   1572:        }
                   1573: 
                   1574:        xmlInitParser();
                   1575: 
                   1576:        if (mode == DOM_LOAD_FILE) {
                   1577:                char *file_dest = _dom_get_valid_file_path(source, resolved_path, MAXPATHLEN  TSRMLS_CC);
                   1578:                if (file_dest) {
                   1579:                        ctxt = xmlCreateFileParserCtxt(file_dest);
                   1580:                }
                   1581:                
                   1582:        } else {
                   1583:                ctxt = xmlCreateMemoryParserCtxt(source, source_len);
                   1584:        }
                   1585: 
                   1586:        if (ctxt == NULL) {
                   1587:                return(NULL);
                   1588:        }
                   1589: 
                   1590:        /* If loading from memory, we need to set the base directory for the document */
                   1591:        if (mode != DOM_LOAD_FILE) {
                   1592: #if HAVE_GETCWD
                   1593:                directory = VCWD_GETCWD(resolved_path, MAXPATHLEN);
                   1594: #elif HAVE_GETWD
                   1595:                directory = VCWD_GETWD(resolved_path);
                   1596: #endif
                   1597:                if (directory) {
                   1598:                        if(ctxt->directory != NULL) {
                   1599:                                xmlFree((char *) ctxt->directory);
                   1600:                        }
                   1601:                        resolved_path_len = strlen(resolved_path);
                   1602:                        if (resolved_path[resolved_path_len - 1] != DEFAULT_SLASH) {
                   1603:                                resolved_path[resolved_path_len] = DEFAULT_SLASH;
                   1604:                                resolved_path[++resolved_path_len] = '\0';
                   1605:                        }
                   1606:                        ctxt->directory = (char *) xmlCanonicPath((const xmlChar *) resolved_path);
                   1607:                }
                   1608:        }
                   1609: 
                   1610:        ctxt->vctxt.error = php_libxml_ctx_error;
                   1611:        ctxt->vctxt.warning = php_libxml_ctx_warning;
                   1612: 
                   1613:        if (ctxt->sax != NULL) {
                   1614:                ctxt->sax->error = php_libxml_ctx_error;
                   1615:                ctxt->sax->warning = php_libxml_ctx_warning;
                   1616:        }
                   1617: 
                   1618:        if (validate && ! (options & XML_PARSE_DTDVALID)) {
                   1619:                options |= XML_PARSE_DTDVALID;
                   1620:        }
                   1621:        if (resolve_externals && ! (options & XML_PARSE_DTDATTR)) {
                   1622:                options |= XML_PARSE_DTDATTR;
                   1623:        }
                   1624:        if (substitute_ent && ! (options & XML_PARSE_NOENT)) {
                   1625:                options |= XML_PARSE_NOENT;
                   1626:        }
                   1627:        if (keep_blanks == 0 && ! (options & XML_PARSE_NOBLANKS)) {
                   1628:                options |= XML_PARSE_NOBLANKS;
                   1629:        }
                   1630: 
                   1631:        xmlCtxtUseOptions(ctxt, options);
                   1632: 
                   1633:        ctxt->recovery = recover;
                   1634:        if (recover) {
                   1635:                old_error_reporting = EG(error_reporting);
                   1636:                EG(error_reporting) = old_error_reporting | E_WARNING;
                   1637:        }
                   1638: 
                   1639:        xmlParseDocument(ctxt);
                   1640: 
                   1641:        if (ctxt->wellFormed || recover) {
                   1642:                ret = ctxt->myDoc;
                   1643:                if (ctxt->recovery) {
                   1644:                        EG(error_reporting) = old_error_reporting;
                   1645:                }
                   1646:                /* If loading from memory, set the base reference uri for the document */
                   1647:                if (ret && ret->URL == NULL && ctxt->directory != NULL) {
                   1648:                        ret->URL = xmlStrdup(ctxt->directory);
                   1649:                }
                   1650:        } else {
                   1651:                ret = NULL;
                   1652:                xmlFreeDoc(ctxt->myDoc);
                   1653:                ctxt->myDoc = NULL;
                   1654:        }
                   1655: 
                   1656:        xmlFreeParserCtxt(ctxt);
                   1657: 
                   1658:        return(ret);
                   1659: }
                   1660: /* }}} */
                   1661: 
                   1662: /* {{{ static void dom_parse_document(INTERNAL_FUNCTION_PARAMETERS, int mode) */
                   1663: static void dom_parse_document(INTERNAL_FUNCTION_PARAMETERS, int mode) {
1.1.1.2 ! misho    1664:        zval *id;
1.1       misho    1665:        xmlDoc *docp = NULL, *newdoc;
                   1666:        dom_doc_propsptr doc_prop;
                   1667:        dom_object *intern;
                   1668:        char *source;
                   1669:        int source_len, refcount, ret;
                   1670:        long options = 0;
                   1671: 
                   1672:        id = getThis();
                   1673:        if (id != NULL && ! instanceof_function(Z_OBJCE_P(id), dom_document_class_entry TSRMLS_CC)) {
                   1674:                id = NULL;
                   1675:        }
                   1676: 
                   1677:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &source, &source_len, &options) == FAILURE) {
                   1678:                return;
                   1679:        }
                   1680: 
                   1681:        if (!source_len) {
                   1682:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty string supplied as input");
                   1683:                RETURN_FALSE;
                   1684:        }
                   1685: 
                   1686:        newdoc = dom_document_parser(id, mode, source, source_len, options TSRMLS_CC);
                   1687: 
                   1688:        if (!newdoc)
                   1689:                RETURN_FALSE;
                   1690: 
                   1691:        if (id != NULL) {
                   1692:                intern = (dom_object *)zend_object_store_get_object(id TSRMLS_CC);
                   1693:                if (intern != NULL) {
                   1694:                        docp = (xmlDocPtr) dom_object_get_node(intern);
                   1695:                        doc_prop = NULL;
                   1696:                        if (docp != NULL) {
                   1697:                                php_libxml_decrement_node_ptr((php_libxml_node_object *) intern TSRMLS_CC);
                   1698:                                doc_prop = intern->document->doc_props;
                   1699:                                intern->document->doc_props = NULL;
                   1700:                                refcount = php_libxml_decrement_doc_ref((php_libxml_node_object *)intern TSRMLS_CC);
                   1701:                                if (refcount != 0) {
                   1702:                                        docp->_private = NULL;
                   1703:                                }
                   1704:                        }
                   1705:                        intern->document = NULL;
                   1706:                        if (php_libxml_increment_doc_ref((php_libxml_node_object *)intern, newdoc TSRMLS_CC) == -1) {
                   1707:                                RETURN_FALSE;
                   1708:                        }
                   1709:                        intern->document->doc_props = doc_prop;
                   1710:                }
                   1711: 
                   1712:                php_libxml_increment_node_ptr((php_libxml_node_object *)intern, (xmlNodePtr)newdoc, (void *)intern TSRMLS_CC);
                   1713: 
                   1714:                RETURN_TRUE;
                   1715:        } else {
1.1.1.2 ! misho    1716:                DOM_RET_OBJ((xmlNodePtr) newdoc, &ret, NULL);
1.1       misho    1717:        }
                   1718: }
                   1719: /* }}} end dom_parser_document */
                   1720: 
                   1721: /* {{{ proto DOMNode dom_document_load(string source [, int options]);
                   1722: URL: http://www.w3.org/TR/DOM-Level-3-LS/load-save.html#LS-DocumentLS-load
                   1723: Since: DOM Level 3
                   1724: */
                   1725: PHP_METHOD(domdocument, load)
                   1726: {
                   1727:        dom_parse_document(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE);
                   1728: }
                   1729: /* }}} end dom_document_load */
                   1730: 
                   1731: /* {{{ proto DOMNode dom_document_loadxml(string source [, int options]);
                   1732: URL: http://www.w3.org/TR/DOM-Level-3-LS/load-save.html#LS-DocumentLS-loadXML
                   1733: Since: DOM Level 3
                   1734: */
                   1735: PHP_METHOD(domdocument, loadXML)
                   1736: {
                   1737:        dom_parse_document(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING);
                   1738: }
                   1739: /* }}} end dom_document_loadxml */
                   1740: 
                   1741: /* {{{ proto int dom_document_save(string file);
                   1742: Convenience method to save to file
                   1743: */
                   1744: PHP_FUNCTION(dom_document_save)
                   1745: {
                   1746:        zval *id;
                   1747:        xmlDoc *docp;
                   1748:        int file_len = 0, bytes, format, saveempty = 0;
                   1749:        dom_object *intern;
                   1750:        dom_doc_propsptr doc_props;
                   1751:        char *file;
                   1752:        long options = 0;
                   1753: 
                   1754:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os|l", &id, dom_document_class_entry, &file, &file_len, &options) == FAILURE) {
                   1755:                return;
                   1756:        }
                   1757: 
                   1758:        if (file_len == 0) {
                   1759:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Filename");
                   1760:                RETURN_FALSE;
                   1761:        }
                   1762: 
                   1763:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1764: 
                   1765:        /* encoding handled by property on doc */
                   1766: 
                   1767:        doc_props = dom_get_doc_props(intern->document);
                   1768:        format = doc_props->formatoutput;
                   1769:        if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1770:                saveempty = xmlSaveNoEmptyTags;
                   1771:                xmlSaveNoEmptyTags = 1;
                   1772:        }
                   1773:        bytes = xmlSaveFormatFileEnc(file, docp, NULL, format);
                   1774:        if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1775:                xmlSaveNoEmptyTags = saveempty;
                   1776:        }
                   1777:        if (bytes == -1) {
                   1778:                RETURN_FALSE;
                   1779:        }
                   1780:        RETURN_LONG(bytes);
                   1781: }
                   1782: /* }}} end dom_document_save */
                   1783: 
                   1784: /* {{{ proto string dom_document_savexml([node n]);
                   1785: URL: http://www.w3.org/TR/DOM-Level-3-LS/load-save.html#LS-DocumentLS-saveXML
                   1786: Since: DOM Level 3
                   1787: */
                   1788: PHP_FUNCTION(dom_document_savexml)
                   1789: {
                   1790:        zval *id, *nodep = NULL;
                   1791:        xmlDoc *docp;
                   1792:        xmlNode *node;
                   1793:        xmlBufferPtr buf;
                   1794:        xmlChar *mem;
                   1795:        dom_object *intern, *nodeobj;
                   1796:        dom_doc_propsptr doc_props;
                   1797:        int size, format, saveempty = 0;
                   1798:        long options = 0;
                   1799: 
                   1800:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O|O!l", &id, dom_document_class_entry, &nodep, dom_node_class_entry, &options) == FAILURE) {
                   1801:                return;
                   1802:        }
                   1803: 
                   1804:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1805: 
                   1806:        doc_props = dom_get_doc_props(intern->document);
                   1807:        format = doc_props->formatoutput;
                   1808: 
                   1809:        if (nodep != NULL) {
                   1810:                /* Dump contents of Node */
                   1811:                DOM_GET_OBJ(node, nodep, xmlNodePtr, nodeobj);
                   1812:                if (node->doc != docp) {
                   1813:                        php_dom_throw_error(WRONG_DOCUMENT_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                   1814:                        RETURN_FALSE;
                   1815:                }
                   1816:                buf = xmlBufferCreate();
                   1817:                if (!buf) {
                   1818:                        php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not fetch buffer");
                   1819:                        RETURN_FALSE;
                   1820:                }
                   1821:                if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1822:                        saveempty = xmlSaveNoEmptyTags;
                   1823:                        xmlSaveNoEmptyTags = 1;
                   1824:                }
                   1825:                xmlNodeDump(buf, docp, node, 0, format);
                   1826:                if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1827:                        xmlSaveNoEmptyTags = saveempty;
                   1828:                }
                   1829:                mem = (xmlChar*) xmlBufferContent(buf);
                   1830:                if (!mem) {
                   1831:                        xmlBufferFree(buf);
                   1832:                        RETURN_FALSE;
                   1833:                }
                   1834:                RETVAL_STRING(mem, 1);
                   1835:                xmlBufferFree(buf);
                   1836:        } else {
                   1837:                if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1838:                        saveempty = xmlSaveNoEmptyTags;
                   1839:                        xmlSaveNoEmptyTags = 1;
                   1840:                }
                   1841:                /* Encoding is handled from the encoding property set on the document */
                   1842:                xmlDocDumpFormatMemory(docp, &mem, &size, format);
                   1843:                if (options & LIBXML_SAVE_NOEMPTYTAG) {
                   1844:                        xmlSaveNoEmptyTags = saveempty;
                   1845:                }
                   1846:                if (!size) {
                   1847:                        RETURN_FALSE;
                   1848:                }
                   1849:                RETVAL_STRINGL(mem, size, 1);
                   1850:                xmlFree(mem);
                   1851:        }
                   1852: }
                   1853: /* }}} end dom_document_savexml */
                   1854: 
                   1855: static xmlNodePtr php_dom_free_xinclude_node(xmlNodePtr cur TSRMLS_DC) /* {{{ */
                   1856: {
                   1857:        xmlNodePtr xincnode;
                   1858: 
                   1859:        xincnode = cur;
                   1860:        cur = cur->next;
                   1861:        xmlUnlinkNode(xincnode);
                   1862:        php_libxml_node_free_resource(xincnode TSRMLS_CC);
                   1863: 
                   1864:        return cur;
                   1865: }
                   1866: /* }}} */
                   1867: 
                   1868: static void php_dom_remove_xinclude_nodes(xmlNodePtr cur TSRMLS_DC) /* {{{ */
                   1869: {
                   1870:        while(cur) {
                   1871:                if (cur->type == XML_XINCLUDE_START) {
                   1872:                        cur = php_dom_free_xinclude_node(cur TSRMLS_CC);
                   1873: 
                   1874:                        /* XML_XINCLUDE_END node will be a sibling of XML_XINCLUDE_START */
                   1875:                        while(cur && cur->type != XML_XINCLUDE_END) {
                   1876:                                /* remove xinclude processing nodes from recursive xincludes */
                   1877:                                if (cur->type == XML_ELEMENT_NODE) {
                   1878:                                           php_dom_remove_xinclude_nodes(cur->children TSRMLS_CC);
                   1879:                                }
                   1880:                                cur = cur->next;
                   1881:                        }
                   1882: 
                   1883:                        if (cur && cur->type == XML_XINCLUDE_END) {
                   1884:                                cur = php_dom_free_xinclude_node(cur TSRMLS_CC);
                   1885:                        }
                   1886:                } else {
                   1887:                        if (cur->type == XML_ELEMENT_NODE) {
                   1888:                                php_dom_remove_xinclude_nodes(cur->children TSRMLS_CC);
                   1889:                        }
                   1890:                        cur = cur->next;
                   1891:                }
                   1892:        }
                   1893: }
                   1894: /* }}} */
                   1895: 
                   1896: /* {{{ proto int dom_document_xinclude([int options])
                   1897:    Substitutues xincludes in a DomDocument */
                   1898: PHP_FUNCTION(dom_document_xinclude)
                   1899: {
                   1900:        zval *id;
                   1901:        xmlDoc *docp;
                   1902:        xmlNodePtr root;
                   1903:        long flags = 0; 
                   1904:        int err;
                   1905:        dom_object *intern;
                   1906: 
                   1907:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O|l", &id, dom_document_class_entry, &flags) == FAILURE) {
                   1908:                return;
                   1909:        }
                   1910: 
                   1911:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1912: 
                   1913:        err = xmlXIncludeProcessFlags(docp, flags);
                   1914: 
                   1915:        /* XML_XINCLUDE_START and XML_XINCLUDE_END nodes need to be removed as these
                   1916:        are added via xmlXIncludeProcess to mark beginning and ending of xincluded document 
                   1917:        but are not wanted in resulting document - must be done even if err as it could fail after
                   1918:        having processed some xincludes */
                   1919:        root = (xmlNodePtr) docp->children;
                   1920:        while(root && root->type != XML_ELEMENT_NODE && root->type != XML_XINCLUDE_START) {
                   1921:                root = root->next;
                   1922:        }
                   1923:        if (root) {
                   1924:                php_dom_remove_xinclude_nodes(root TSRMLS_CC);
                   1925:        }
                   1926: 
                   1927:        if (err) {
                   1928:                RETVAL_LONG(err);
                   1929:        } else {
                   1930:                RETVAL_FALSE;
                   1931:        }
                   1932:     
                   1933: }
                   1934: /* }}} */
                   1935: 
                   1936: /* {{{ proto boolean dom_document_validate();
                   1937: Since: DOM extended
                   1938: */
                   1939: PHP_FUNCTION(dom_document_validate)
                   1940: {
                   1941:        zval *id;
                   1942:        xmlDoc *docp;
                   1943:        dom_object *intern;
                   1944:        xmlValidCtxt *cvp;
                   1945: 
                   1946:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &id, dom_document_class_entry) == FAILURE) {
                   1947:                return;
                   1948:        }
                   1949: 
                   1950:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1951: 
                   1952:        cvp = xmlNewValidCtxt();
                   1953:        
                   1954:        cvp->userData = NULL;
                   1955:        cvp->error    = (xmlValidityErrorFunc) php_libxml_error_handler;
                   1956:        cvp->warning  = (xmlValidityErrorFunc) php_libxml_error_handler;
                   1957:        
                   1958:        if (xmlValidateDocument(cvp, docp)) {
                   1959:                RETVAL_TRUE;
                   1960:        } else {
                   1961:                RETVAL_FALSE;
                   1962:        }
                   1963:        
                   1964:        xmlFreeValidCtxt(cvp);
                   1965:        
                   1966: }
                   1967: /* }}} */
                   1968: 
                   1969: #if defined(LIBXML_SCHEMAS_ENABLED)
                   1970: static void _dom_document_schema_validate(INTERNAL_FUNCTION_PARAMETERS, int type) /* {{{ */
                   1971: {
                   1972:        zval *id;
                   1973:        xmlDoc *docp;
                   1974:        dom_object *intern;
                   1975:        char *source = NULL, *valid_file = NULL;
                   1976:        int source_len = 0;
                   1977:        xmlSchemaParserCtxtPtr  parser;
                   1978:        xmlSchemaPtr            sptr;
                   1979:        xmlSchemaValidCtxtPtr   vptr;
                   1980:        int                     is_valid;
                   1981:        char resolved_path[MAXPATHLEN + 1];
                   1982: 
1.1.1.2 ! misho    1983:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Op", &id, dom_document_class_entry, &source, &source_len) == FAILURE) {
1.1       misho    1984:                return;
                   1985:        }
                   1986: 
                   1987:        if (source_len == 0) {
                   1988:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Schema source");
                   1989:                RETURN_FALSE;
                   1990:        }
                   1991: 
                   1992:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   1993: 
                   1994:        switch (type) {
                   1995:        case DOM_LOAD_FILE:
                   1996:                valid_file = _dom_get_valid_file_path(source, resolved_path, MAXPATHLEN  TSRMLS_CC);
                   1997:                if (!valid_file) {
                   1998:                        php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Schema file source");
                   1999:                        RETURN_FALSE;
                   2000:                }
                   2001:                parser = xmlSchemaNewParserCtxt(valid_file);
                   2002:                break;
                   2003:        case DOM_LOAD_STRING:
                   2004:                parser = xmlSchemaNewMemParserCtxt(source, source_len);
                   2005:                /* If loading from memory, we need to set the base directory for the document 
                   2006:                   but it is not apparent how to do that for schema's */
                   2007:                break;
                   2008:        default:
                   2009:                return;
                   2010:        }
                   2011: 
                   2012:        xmlSchemaSetParserErrors(parser,
                   2013:                (xmlSchemaValidityErrorFunc) php_libxml_error_handler,
                   2014:                (xmlSchemaValidityWarningFunc) php_libxml_error_handler,
                   2015:                parser);
                   2016:        sptr = xmlSchemaParse(parser);
                   2017:        xmlSchemaFreeParserCtxt(parser);
                   2018:        if (!sptr) {
                   2019:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Schema");
                   2020:                RETURN_FALSE;
                   2021:        }
                   2022: 
                   2023:        docp = (xmlDocPtr) dom_object_get_node(intern);
                   2024: 
                   2025:        vptr = xmlSchemaNewValidCtxt(sptr);
                   2026:        if (!vptr) {
                   2027:                xmlSchemaFree(sptr);
                   2028:                php_error(E_ERROR, "Invalid Schema Validation Context");
                   2029:                RETURN_FALSE;
                   2030:        }
                   2031: 
                   2032:        xmlSchemaSetValidErrors(vptr, php_libxml_error_handler, php_libxml_error_handler, vptr);
                   2033:        is_valid = xmlSchemaValidateDoc(vptr, docp);
                   2034:        xmlSchemaFree(sptr);
                   2035:        xmlSchemaFreeValidCtxt(vptr);
                   2036: 
                   2037:        if (is_valid == 0) {
                   2038:                RETURN_TRUE;
                   2039:        } else {
                   2040:                RETURN_FALSE;
                   2041:        }
                   2042: }
                   2043: /* }}} */
                   2044: 
                   2045: /* {{{ proto boolean dom_document_schema_validate_file(string filename); */
                   2046: PHP_FUNCTION(dom_document_schema_validate_file)
                   2047: {
                   2048:        _dom_document_schema_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE);
                   2049: }
                   2050: /* }}} end dom_document_schema_validate_file */
                   2051: 
                   2052: /* {{{ proto boolean dom_document_schema_validate(string source); */
                   2053: PHP_FUNCTION(dom_document_schema_validate_xml)
                   2054: {
                   2055:        _dom_document_schema_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING);
                   2056: }
                   2057: /* }}} end dom_document_schema_validate */
                   2058: 
                   2059: static void _dom_document_relaxNG_validate(INTERNAL_FUNCTION_PARAMETERS, int type) /* {{{ */
                   2060: {
                   2061:        zval *id;
                   2062:        xmlDoc *docp;
                   2063:        dom_object *intern;
                   2064:        char *source = NULL, *valid_file = NULL;
                   2065:        int source_len = 0;
                   2066:        xmlRelaxNGParserCtxtPtr parser;
                   2067:        xmlRelaxNGPtr           sptr;
                   2068:        xmlRelaxNGValidCtxtPtr  vptr;
                   2069:        int                     is_valid;
                   2070:        char resolved_path[MAXPATHLEN + 1];
                   2071: 
1.1.1.2 ! misho    2072:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Op", &id, dom_document_class_entry, &source, &source_len) == FAILURE) {
1.1       misho    2073:                return;
                   2074:        }
                   2075: 
                   2076:        if (source_len == 0) {
                   2077:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Schema source");
                   2078:                RETURN_FALSE;
                   2079:        }
                   2080: 
                   2081:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   2082: 
                   2083:        switch (type) {
                   2084:        case DOM_LOAD_FILE:
                   2085:                valid_file = _dom_get_valid_file_path(source, resolved_path, MAXPATHLEN  TSRMLS_CC);
                   2086:                if (!valid_file) {
                   2087:                        php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid RelaxNG file source");
                   2088:                        RETURN_FALSE;
                   2089:                }
                   2090:                parser = xmlRelaxNGNewParserCtxt(valid_file);
                   2091:                break;
                   2092:        case DOM_LOAD_STRING:
                   2093:                parser = xmlRelaxNGNewMemParserCtxt(source, source_len);
                   2094:                /* If loading from memory, we need to set the base directory for the document 
                   2095:                   but it is not apparent how to do that for schema's */
                   2096:                break;
                   2097:        default:
                   2098:                return;
                   2099:        }
                   2100: 
                   2101:        xmlRelaxNGSetParserErrors(parser,
                   2102:                (xmlRelaxNGValidityErrorFunc) php_libxml_error_handler,
                   2103:                (xmlRelaxNGValidityWarningFunc) php_libxml_error_handler,
                   2104:                parser);
                   2105:        sptr = xmlRelaxNGParse(parser);
                   2106:        xmlRelaxNGFreeParserCtxt(parser);
                   2107:        if (!sptr) {
                   2108:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid RelaxNG");
                   2109:                RETURN_FALSE;
                   2110:        }
                   2111: 
                   2112:        docp = (xmlDocPtr) dom_object_get_node(intern);
                   2113: 
                   2114:        vptr = xmlRelaxNGNewValidCtxt(sptr);
                   2115:        if (!vptr) {
                   2116:                xmlRelaxNGFree(sptr);
                   2117:                php_error(E_ERROR, "Invalid RelaxNG Validation Context");
                   2118:                RETURN_FALSE;
                   2119:        }
                   2120: 
                   2121:        xmlRelaxNGSetValidErrors(vptr, php_libxml_error_handler, php_libxml_error_handler, vptr);
                   2122:        is_valid = xmlRelaxNGValidateDoc(vptr, docp);
                   2123:        xmlRelaxNGFree(sptr);
                   2124:        xmlRelaxNGFreeValidCtxt(vptr);
                   2125: 
                   2126:        if (is_valid == 0) {
                   2127:                RETURN_TRUE;
                   2128:        } else {
                   2129:                RETURN_FALSE;
                   2130:        }
                   2131: }
                   2132: /* }}} */
                   2133: 
                   2134: /* {{{ proto boolean dom_document_relaxNG_validate_file(string filename); */
                   2135: PHP_FUNCTION(dom_document_relaxNG_validate_file)
                   2136: {
                   2137:        _dom_document_relaxNG_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE);
                   2138: }
                   2139: /* }}} end dom_document_relaxNG_validate_file */
                   2140: 
                   2141: /* {{{ proto boolean dom_document_relaxNG_validate_xml(string source); */
                   2142: PHP_FUNCTION(dom_document_relaxNG_validate_xml)
                   2143: {
                   2144:        _dom_document_relaxNG_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING);
                   2145: }
                   2146: /* }}} end dom_document_relaxNG_validate_xml */
                   2147: 
                   2148: #endif
                   2149: 
                   2150: #if defined(LIBXML_HTML_ENABLED)
                   2151: 
                   2152: static void dom_load_html(INTERNAL_FUNCTION_PARAMETERS, int mode) /* {{{ */
                   2153: {
1.1.1.2 ! misho    2154:        zval *id;
1.1       misho    2155:        xmlDoc *docp = NULL, *newdoc;
                   2156:        dom_object *intern;
                   2157:        dom_doc_propsptr doc_prop;
                   2158:        char *source;
                   2159:        int source_len, refcount, ret;
1.1.1.2 ! misho    2160:        long options = 0;
1.1       misho    2161:        htmlParserCtxtPtr ctxt;
                   2162:        
                   2163:        id = getThis();
                   2164: 
1.1.1.2 ! misho    2165:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &source, &source_len, &options) == FAILURE) {
1.1       misho    2166:                return;
                   2167:        }
                   2168: 
                   2169:        if (!source_len) {
                   2170:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty string supplied as input");
                   2171:                RETURN_FALSE;
                   2172:        }
                   2173: 
                   2174:        if (mode == DOM_LOAD_FILE) {
                   2175:                ctxt = htmlCreateFileParserCtxt(source, NULL);
                   2176:        } else {
                   2177:                source_len = xmlStrlen(source);
                   2178:                ctxt = htmlCreateMemoryParserCtxt(source, source_len);
                   2179:        }
                   2180: 
                   2181:        if (!ctxt) {
                   2182:                RETURN_FALSE;
                   2183:        }
                   2184: 
1.1.1.2 ! misho    2185:        if (options) {
        !          2186:                htmlCtxtUseOptions(ctxt, options);
        !          2187:        }
        !          2188: 
1.1       misho    2189:        ctxt->vctxt.error = php_libxml_ctx_error;
                   2190:        ctxt->vctxt.warning = php_libxml_ctx_warning;
                   2191:        if (ctxt->sax != NULL) {
                   2192:                ctxt->sax->error = php_libxml_ctx_error;
                   2193:                ctxt->sax->warning = php_libxml_ctx_warning;
                   2194:        }
                   2195:        htmlParseDocument(ctxt);
                   2196:        newdoc = ctxt->myDoc;
                   2197:        htmlFreeParserCtxt(ctxt);
                   2198:        
                   2199:        if (!newdoc)
                   2200:                RETURN_FALSE;
                   2201: 
                   2202:        if (id != NULL && instanceof_function(Z_OBJCE_P(id), dom_document_class_entry TSRMLS_CC)) {
                   2203:                intern = (dom_object *)zend_object_store_get_object(id TSRMLS_CC);
                   2204:                if (intern != NULL) {
                   2205:                        docp = (xmlDocPtr) dom_object_get_node(intern);
                   2206:                        doc_prop = NULL;
                   2207:                        if (docp != NULL) {
                   2208:                                php_libxml_decrement_node_ptr((php_libxml_node_object *) intern TSRMLS_CC);
                   2209:                                doc_prop = intern->document->doc_props;
                   2210:                                intern->document->doc_props = NULL;
                   2211:                                refcount = php_libxml_decrement_doc_ref((php_libxml_node_object *)intern TSRMLS_CC);
                   2212:                                if (refcount != 0) {
                   2213:                                        docp->_private = NULL;
                   2214:                                }
                   2215:                        }
                   2216:                        intern->document = NULL;
                   2217:                        if (php_libxml_increment_doc_ref((php_libxml_node_object *)intern, newdoc TSRMLS_CC) == -1) {
                   2218:                                RETURN_FALSE;
                   2219:                        }
                   2220:                        intern->document->doc_props = doc_prop;
                   2221:                }
                   2222: 
                   2223:                php_libxml_increment_node_ptr((php_libxml_node_object *)intern, (xmlNodePtr)newdoc, (void *)intern TSRMLS_CC);
                   2224: 
                   2225:                RETURN_TRUE;
                   2226:        } else {
1.1.1.2 ! misho    2227:                DOM_RET_OBJ((xmlNodePtr) newdoc, &ret, NULL);
1.1       misho    2228:        }
                   2229: }
                   2230: /* }}} */
                   2231: 
                   2232: /* {{{ proto DOMNode dom_document_load_html_file(string source);
                   2233: Since: DOM extended
                   2234: */
                   2235: PHP_METHOD(domdocument, loadHTMLFile)
                   2236: {
                   2237:        dom_load_html(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE);
                   2238: }
                   2239: /* }}} end dom_document_load_html_file */
                   2240: 
                   2241: /* {{{ proto DOMNode dom_document_load_html(string source);
                   2242: Since: DOM extended
                   2243: */
                   2244: PHP_METHOD(domdocument, loadHTML)
                   2245: {
                   2246:        dom_load_html(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING);
                   2247: }
                   2248: /* }}} end dom_document_load_html */
                   2249: 
                   2250: /* {{{ proto int dom_document_save_html_file(string file);
                   2251: Convenience method to save to file as html
                   2252: */
                   2253: PHP_FUNCTION(dom_document_save_html_file)
                   2254: {
                   2255:        zval *id;
                   2256:        xmlDoc *docp;
                   2257:        int file_len, bytes, format;
                   2258:        dom_object *intern;
                   2259:        dom_doc_propsptr doc_props;
                   2260:        char *file;
                   2261:        const char *encoding;
                   2262: 
                   2263:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Os", &id, dom_document_class_entry, &file, &file_len) == FAILURE) {
                   2264:                return;
                   2265:        }
                   2266: 
                   2267:        if (file_len == 0) {
                   2268:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid Filename");
                   2269:                RETURN_FALSE;
                   2270:        }
                   2271: 
                   2272:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   2273: 
                   2274: 
                   2275:        encoding = (const char *) htmlGetMetaEncoding(docp);
                   2276: 
                   2277:        doc_props = dom_get_doc_props(intern->document);
                   2278:        format = doc_props->formatoutput;
                   2279:        bytes = htmlSaveFileFormat(file, docp, encoding, format);
                   2280: 
                   2281:        if (bytes == -1) {
                   2282:                RETURN_FALSE;
                   2283:        }
                   2284:        RETURN_LONG(bytes);
                   2285: }
                   2286: /* }}} end dom_document_save_html_file */
                   2287: 
                   2288: /* {{{ proto string dom_document_save_html();
                   2289: Convenience method to output as html
                   2290: */
                   2291: PHP_FUNCTION(dom_document_save_html)
                   2292: {
                   2293:        zval *id, *nodep = NULL;
                   2294:        xmlDoc *docp;
                   2295:        xmlNode *node;
                   2296:        xmlBufferPtr buf;
                   2297:        dom_object *intern, *nodeobj;
                   2298:        xmlChar *mem = NULL;
                   2299:        int size, format;
                   2300:        dom_doc_propsptr doc_props;
                   2301: 
                   2302:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(),
                   2303:                "O|O!", &id, dom_document_class_entry, &nodep, dom_node_class_entry)
                   2304:                == FAILURE) {
                   2305:                return;
                   2306:        }
                   2307: 
                   2308:        DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   2309: 
                   2310:        doc_props = dom_get_doc_props(intern->document);
                   2311:        format = doc_props->formatoutput;
                   2312: 
                   2313:        if (nodep != NULL) {
                   2314:                /* Dump contents of Node */
                   2315:                DOM_GET_OBJ(node, nodep, xmlNodePtr, nodeobj);
                   2316:                if (node->doc != docp) {
                   2317:                        php_dom_throw_error(WRONG_DOCUMENT_ERR, dom_get_strict_error(intern->document) TSRMLS_CC);
                   2318:                        RETURN_FALSE;
                   2319:                }
                   2320:                
                   2321:                buf = xmlBufferCreate();
                   2322:                if (!buf) {
                   2323:                        php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not fetch buffer");
                   2324:                        RETURN_FALSE;
                   2325:                }
                   2326:                
                   2327:                size = htmlNodeDump(buf, docp, node);
                   2328:                if (size >= 0) {
                   2329:                        mem = (xmlChar*) xmlBufferContent(buf);
                   2330:                        if (!mem) {
                   2331:                                RETVAL_FALSE;
                   2332:                        } else {
                   2333:                                RETVAL_STRINGL((const char*) mem, size, 1);
                   2334:                        }
                   2335:                } else {
                   2336:                        php_error_docref(NULL TSRMLS_CC, E_WARNING, "Error dumping HTML node");
                   2337:                        RETVAL_FALSE;
                   2338:                }
                   2339:                xmlBufferFree(buf);
                   2340:        } else {
                   2341: #if LIBXML_VERSION >= 20623
                   2342:                htmlDocDumpMemoryFormat(docp, &mem, &size, format);
                   2343: #else
                   2344:                htmlDocDumpMemory(docp, &mem, &size);
                   2345: #endif
                   2346:                if (!size) {
                   2347:                        RETVAL_FALSE;
                   2348:                } else {
                   2349:                        RETVAL_STRINGL((const char*) mem, size, 1);
                   2350:                }
                   2351:                if (mem)
                   2352:                        xmlFree(mem);
                   2353:        }
                   2354: 
                   2355: }
                   2356: /* }}} end dom_document_save_html */
                   2357: 
                   2358: #endif  /* defined(LIBXML_HTML_ENABLED) */
                   2359: 
                   2360: /* {{{ proto boolean DOMDocument::registerNodeClass(string baseclass, string extendedclass);
                   2361:    Register extended class used to create base node type */
                   2362: PHP_METHOD(domdocument, registerNodeClass)
                   2363: {
                   2364:        zval *id;
                   2365:        xmlDoc *docp;
                   2366:        char *baseclass = NULL, *extendedclass = NULL;
                   2367:        int baseclass_len = 0, extendedclass_len = 0;
                   2368:        zend_class_entry *basece = NULL, *ce = NULL;
                   2369:        dom_object *intern;
                   2370: 
                   2371:        if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Oss!", &id, dom_document_class_entry, &baseclass, &baseclass_len, &extendedclass, &extendedclass_len) == FAILURE) {
                   2372:                return;
                   2373:        }
                   2374: 
                   2375:        if (baseclass_len) {
                   2376:                zend_class_entry **pce;
                   2377:                if (zend_lookup_class(baseclass, baseclass_len, &pce TSRMLS_CC) == FAILURE) {
                   2378:                        php_error_docref(NULL TSRMLS_CC, E_ERROR, "Class %s does not exist", baseclass);
                   2379:                        return;
                   2380:                }
                   2381:                basece = *pce;
                   2382:        }
                   2383: 
                   2384:        if (basece == NULL || ! instanceof_function(basece, dom_node_class_entry TSRMLS_CC)) {
                   2385:                php_error_docref(NULL TSRMLS_CC, E_ERROR, "Class %s is not derived from DOMNode.", baseclass);
                   2386:                return;
                   2387:        }
                   2388: 
                   2389:        if (extendedclass_len) {
                   2390:                zend_class_entry **pce;
                   2391:                if (zend_lookup_class(extendedclass, extendedclass_len, &pce TSRMLS_CC) == FAILURE) {
                   2392:                        php_error_docref(NULL TSRMLS_CC, E_ERROR, "Class %s does not exist", extendedclass);
                   2393:                }
                   2394:                ce = *pce;
                   2395:        }
                   2396: 
                   2397:        if (ce == NULL || instanceof_function(ce, basece TSRMLS_CC)) {
                   2398: 
                   2399:                DOM_GET_OBJ(docp, id, xmlDocPtr, intern);
                   2400: 
                   2401:                if (dom_set_doc_classmap(intern->document, basece, ce TSRMLS_CC) == FAILURE) {
                   2402:                        php_error_docref(NULL TSRMLS_CC, E_ERROR, "Class %s could not be registered.", extendedclass);
                   2403:                }
                   2404:                RETURN_TRUE;
                   2405:        } else {
                   2406:                php_error_docref(NULL TSRMLS_CC, E_ERROR, "Class %s is not derived from %s.", extendedclass, baseclass);
                   2407:        }
                   2408: 
                   2409:        RETURN_FALSE;
                   2410: }
                   2411: /* }}} */
                   2412: 
                   2413: #endif  /* HAVE_LIBXML && HAVE_DOM */
                   2414: 
                   2415: /*
                   2416:  * Local variables:
                   2417:  * tab-width: 4
                   2418:  * c-basic-offset: 4
                   2419:  * End:
                   2420:  * vim600: noet sw=4 ts=4 fdm=marker
                   2421:  * vim<600: noet sw=4 ts=4
                   2422:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>