From 5b19e1ec92cc49031c069fcebdc570b5fa7a325b Mon Sep 17 00:00:00 2001 From: Rob Richards Date: Thu, 12 Jun 2003 20:02:05 +0000 Subject: [PATCH] add node->isSupported() add domimplementation->hasFeature() add formatOutput property (extends DOM) call xmlFreeDoc when doc is no longer referenced rather than custom code save and savexml now format based on formatOutput property --- ext/dom/document.c | 39 ++++++++++++++++++++++++++++++------- ext/dom/domimplementation.c | 13 ++++++++++++- ext/dom/node.c | 15 ++++++++++++-- ext/dom/php_dom.c | 29 ++++++++++++++++++++++++--- ext/dom/php_dom.h | 1 + 5 files changed, 84 insertions(+), 13 deletions(-) diff --git a/ext/dom/document.c b/ext/dom/document.c index afac896149..18d444cac3 100644 --- a/ext/dom/document.c +++ b/ext/dom/document.c @@ -75,6 +75,27 @@ zend_function_entry php_dom_document_class_functions[] = { }; +int dom_document_get_formatting(zval *id TSRMLS_DC) { + zval *format, *member; + zend_object_handlers *std_hnd; + int retformat = 0; + + MAKE_STD_ZVAL(member); + ZVAL_STRING(member, "formatOutput", 1); + + std_hnd = zend_get_std_object_handlers(); + format = std_hnd->read_property(id, member TSRMLS_CC); + + if (format->type == IS_BOOL) { + retformat = Z_BVAL_P(format); + } + + zval_dtor(member); + FREE_ZVAL(member); + + return retformat; +} + /* {{{ proto doctype documenttype readonly=yes URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-B63ED1A31 @@ -1070,7 +1091,7 @@ PHP_FUNCTION(dom_document_save) { zval *id; xmlDoc *docp; - int file_len, bytes; + int file_len, bytes, format; dom_object *intern; char *file; @@ -1084,7 +1105,9 @@ PHP_FUNCTION(dom_document_save) RETURN_FALSE; } - bytes = xmlSaveFile(file, docp); + /* encoding handled by property on doc */ + format = dom_document_get_formatting(id TSRMLS_CC); + bytes = xmlSaveFormatFileEnc(file, docp, NULL, format); if (bytes == -1) { RETURN_FALSE; @@ -1105,7 +1128,7 @@ PHP_FUNCTION(dom_document_savexml) xmlBufferPtr buf; xmlChar *mem; dom_object *intern, *nodeobj; - int size; + int size, format; DOM_GET_THIS_OBJ(docp, id, xmlDocPtr, intern); @@ -1113,6 +1136,8 @@ PHP_FUNCTION(dom_document_savexml) return; } + format = dom_document_get_formatting(id TSRMLS_CC); + if (nodep != NULL) { /* Dump contents of Node */ DOM_GET_OBJ(node, nodep, xmlNodePtr, nodeobj); @@ -1126,7 +1151,8 @@ PHP_FUNCTION(dom_document_savexml) php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not fetch buffer"); RETURN_FALSE; } - xmlNodeDump(buf, docp, node, 0, 0); + + xmlNodeDump(buf, docp, node, 0, format); mem = (xmlChar*) xmlBufferContent(buf); if (!mem) { xmlBufferFree(buf); @@ -1135,9 +1161,8 @@ PHP_FUNCTION(dom_document_savexml) RETVAL_STRING(mem, 1); xmlBufferFree(buf); } else { - /* Dump Document Contents - Encoding is handled from the encoding property set on the document */ - xmlDocDumpMemory(docp, &mem, &size); + /* Encoding is handled from the encoding property set on the document */ + xmlDocDumpFormatMemory(docp, &mem, &size, format); if (!size) { RETURN_FALSE; } diff --git a/ext/dom/domimplementation.c b/ext/dom/domimplementation.c index 19db5a5f0f..1a9f8a4c92 100644 --- a/ext/dom/domimplementation.c +++ b/ext/dom/domimplementation.c @@ -50,7 +50,18 @@ Since: */ PHP_FUNCTION(dom_domimplementation_has_feature) { - DOM_NOT_IMPLEMENTED(); + int feature_len, version_len; + char *feature, *version; + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &feature, &feature_len, &version, &version_len) == FAILURE) { + return; + } + + if (dom_has_feature(feature, version)) { + RETURN_TRUE; + } else { + RETURN_FALSE; + } } /* }}} end dom_domimplementation_has_feature */ diff --git a/ext/dom/node.c b/ext/dom/node.c index dc6551d96b..877b30c8e3 100644 --- a/ext/dom/node.c +++ b/ext/dom/node.c @@ -1123,12 +1123,23 @@ PHP_FUNCTION(dom_node_normalize) /* {{{ proto boolean dom_node_is_supported(string feature, string version); -URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Level-2-Core-Node-supports +URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Level-2-Core-Node-supports Since: DOM Level 2 */ PHP_FUNCTION(dom_node_is_supported) { - DOM_NOT_IMPLEMENTED(); + int feature_len, version_len; + char *feature, *version; + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &feature, &feature_len, &version, &version_len) == FAILURE) { + return; + } + + if (dom_has_feature(feature, version)) { + RETURN_TRUE; + } else { + RETURN_FALSE; + } } /* }}} end dom_node_is_supported */ diff --git a/ext/dom/php_dom.c b/ext/dom/php_dom.c index 6f3dfcb73e..633cf55de7 100644 --- a/ext/dom/php_dom.c +++ b/ext/dom/php_dom.c @@ -102,8 +102,13 @@ int decrement_document_reference(dom_object *object TSRMLS_DC) { object->document->refcount--; ret_refcount = object->document->refcount; if (ret_refcount == 0) { - dom_clean_nodes(object TSRMLS_CC); - node_free_resource(object->document->ptr TSRMLS_CC); + if (object->document->ptr != NULL) { + dom_clean_nodes(object TSRMLS_CC); + /* No references to Doc so can use xmlFreeDoc + node_free_resource(object->document->ptr TSRMLS_CC); */ + xmlFreeDoc((xmlDoc *) object->document->ptr); + object->document->ptr = NULL; + } efree(object->document); object->document = NULL; } @@ -590,7 +595,7 @@ PHP_MINFO_FUNCTION(dom) php_info_print_table_start(); php_info_print_table_row(2, "DOM/XML", "enabled"); php_info_print_table_row(2, "DOM/XML API Version", DOM_API_VERSION); - php_info_print_table_row(2, "libxml Version", xmlParserVersion); + php_info_print_table_row(2, "libxml Version", LIBXML_DOTTED_VERSION); #if defined(LIBXML_HTML_ENABLED) php_info_print_table_row(2, "HTML Support", "enabled"); #endif @@ -979,6 +984,10 @@ zval *php_dom_create_object(xmlNodePtr obj, int *found, zval *wrapper_in, zval * object_init_ex(wrapper, ce); + /* Add object properties not needing function calls */ + if (obj->type == XML_DOCUMENT_NODE || obj->type == XML_HTML_DOCUMENT_NODE) { + add_property_bool(wrapper, "formatOutput", 0); + } intern = (dom_object *)zend_objects_get_address(wrapper TSRMLS_CC); if (obj->doc != NULL) { if (domobj != NULL) { @@ -1019,6 +1028,20 @@ int dom_hierarchy(xmlNodePtr parent, xmlNodePtr child) } /* }}} end dom_hierarchy */ +/* {{{ dom_has_feature(char *feature, char *version) */ +int dom_has_feature(char *feature, char *version) +{ + int retval = 0; + + if (!(strcmp (version, "1.0") && strcmp (version,"2.0") && strcmp(version, ""))) { + if ((!strcasecmp(feature, "Core") && strcmp (version, "1.0")) || !strcasecmp(feature, "XML")) + retval = 1; + } + + return retval; +} +/* }}} end dom_has_feature */ + /* {{{ void dom_element_get_elements_by_tag_name_ns_raw(xmlNodePtr nodep, char *ns, char *local, zval **retval TSRMLS_DC) */ void dom_get_elements_by_tag_name_ns_raw(xmlNodePtr nodep, char *ns, char *local, zval **retval, dom_object *intern TSRMLS_DC) { diff --git a/ext/dom/php_dom.h b/ext/dom/php_dom.h index 8c31288714..e1e942be3a 100644 --- a/ext/dom/php_dom.h +++ b/ext/dom/php_dom.h @@ -73,6 +73,7 @@ void dom_normalize (xmlNodePtr nodep TSRMLS_DC); void dom_get_elements_by_tag_name_ns_raw(xmlNodePtr nodep, char *ns, char *local, zval **retval, dom_object *intern TSRMLS_DC); void php_dom_create_implementation(zval **retval TSRMLS_DC); int dom_hierarchy(xmlNodePtr parent, xmlNodePtr child); +int dom_has_feature(char *feature, char *version); #define DOM_NO_ARGS() \ if (ZEND_NUM_ARGS() != 0) { \ -- 2.50.1