1 : /*
2 : +----------------------------------------------------------------------+
3 : | PHP Version 6 |
4 : +----------------------------------------------------------------------+
5 : | Copyright (c) 1997-2009 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 :
20 : /* $Id: domimplementation.c 276986 2009-03-10 23:40:06Z helly $ */
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 :
30 : /* {{{ arginfo */
31 : ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_implementation_get_feature, 0, 0, 2)
32 : ZEND_ARG_INFO(0, feature)
33 : ZEND_ARG_INFO(0, version)
34 : ZEND_END_ARG_INFO();
35 :
36 : ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_implementation_has_feature, 0, 0, 0)
37 : ZEND_END_ARG_INFO();
38 :
39 : ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_implementation_create_documenttype, 0, 0, 3)
40 : ZEND_ARG_INFO(0, qualifiedName)
41 : ZEND_ARG_INFO(0, publicId)
42 : ZEND_ARG_INFO(0, systemId)
43 : ZEND_END_ARG_INFO();
44 :
45 : ZEND_BEGIN_ARG_INFO_EX(arginfo_dom_implementation_create_document, 0, 0, 3)
46 : ZEND_ARG_INFO(0, namespaceURI)
47 : ZEND_ARG_INFO(0, qualifiedName)
48 : ZEND_ARG_OBJ_INFO(0, docType, DOMDocumentType, 0)
49 : ZEND_END_ARG_INFO();
50 : /* }}} */
51 :
52 : /*
53 : * class DOMImplementation
54 : *
55 : * URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-102161490
56 : * Since:
57 : */
58 :
59 : const zend_function_entry php_dom_domimplementation_class_functions[] = {
60 : PHP_ME(domimplementation, getFeature, arginfo_dom_implementation_get_feature, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
61 : PHP_ME(domimplementation, hasFeature, arginfo_dom_implementation_has_feature, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
62 : PHP_ME(domimplementation, createDocumentType, arginfo_dom_implementation_create_documenttype, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
63 : PHP_ME(domimplementation, createDocument, arginfo_dom_implementation_create_document, ZEND_ACC_PUBLIC|ZEND_ACC_ALLOW_STATIC)
64 : {NULL, NULL, NULL}
65 : };
66 :
67 : /* {{{ proto boolean dom_domimplementation_has_feature(string feature, string version)
68 : URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-5CED94D7
69 : Since:
70 : */
71 : PHP_METHOD(domimplementation, hasFeature)
72 1 : {
73 : int feature_len, version_len;
74 : char *feature, *version;
75 :
76 1 : if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &feature, &feature_len, &version, &version_len) == FAILURE) {
77 0 : return;
78 : }
79 :
80 1 : if (dom_has_feature(feature, version)) {
81 0 : RETURN_TRUE;
82 : } else {
83 1 : RETURN_FALSE;
84 : }
85 : }
86 : /* }}} end dom_domimplementation_has_feature */
87 :
88 : /* {{{ proto DOMDocumentType dom_domimplementation_create_document_type(string qualifiedName, string publicId, string systemId) U
89 : URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Level-2-Core-DOM-createDocType
90 : Since: DOM Level 2
91 : */
92 : PHP_METHOD(domimplementation, createDocumentType)
93 1 : {
94 1 : zval *rv = NULL;
95 : xmlDtd *doctype;
96 1 : int ret, name_len = 0, publicid_len = 0, systemid_len = 0;
97 1 : char *name = NULL, *publicid = NULL, *systemid = NULL;
98 1 : xmlChar *pch1 = NULL, *pch2 = NULL, *localname = NULL;
99 : xmlURIPtr uri;
100 :
101 1 : if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|s&s&s&", &name, &name_len, UG(utf8_conv), &publicid, &publicid_len, UG(utf8_conv), &systemid, &systemid_len, UG(utf8_conv)) == FAILURE) {
102 0 : return;
103 : }
104 :
105 1 : if (name_len == 0) {
106 0 : php_error_docref(NULL TSRMLS_CC, E_WARNING, "qualifiedName is required");
107 0 : RETURN_FALSE;
108 : }
109 :
110 1 : if (publicid_len > 0)
111 1 : pch1 = publicid;
112 1 : if (systemid_len > 0)
113 1 : pch2 = systemid;
114 :
115 1 : uri = xmlParseURI(name);
116 1 : if (uri != NULL && uri->opaque != NULL) {
117 0 : localname = xmlStrdup(uri->opaque);
118 0 : if (xmlStrchr(localname, (xmlChar) ':') != NULL) {
119 0 : php_dom_throw_error(NAMESPACE_ERR, 1 TSRMLS_CC);
120 0 : xmlFreeURI(uri);
121 0 : xmlFree(localname);
122 0 : RETURN_FALSE;
123 : }
124 : } else {
125 1 : localname = xmlStrdup(name);
126 : }
127 :
128 : /* TODO: Test that localname has no invalid chars
129 : php_dom_throw_error(INVALID_CHARACTER_ERR, TSRMLS_CC);
130 : */
131 :
132 1 : if (uri) {
133 1 : xmlFreeURI(uri);
134 : }
135 :
136 1 : doctype = xmlCreateIntSubset(NULL, localname, pch1, pch2);
137 1 : xmlFree(localname);
138 :
139 1 : if (doctype == NULL) {
140 0 : php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unable to create DocumentType");
141 0 : RETURN_FALSE;
142 : }
143 :
144 1 : DOM_RET_OBJ(rv, (xmlNodePtr) doctype, &ret, NULL);
145 : }
146 : /* }}} end dom_domimplementation_create_document_type */
147 :
148 : /* {{{ proto DOMDocument dom_domimplementation_create_document(string namespaceURI, string qualifiedName, DOMDocumentType doctype) U
149 : URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Level-2-Core-DOM-createDocument
150 : Since: DOM Level 2
151 : */
152 : PHP_METHOD(domimplementation, createDocument)
153 1 : {
154 1 : zval *node = NULL, *rv = NULL;
155 : xmlDoc *docp;
156 : xmlNode *nodep;
157 1 : xmlDtdPtr doctype = NULL;
158 1 : xmlNsPtr nsptr = NULL;
159 1 : int ret, uri_len = 0, name_len = 0, errorcode = 0;
160 1 : char *uri = NULL, *name = NULL;
161 1 : char *prefix = NULL, *localname = NULL;
162 : dom_object *doctobj;
163 :
164 1 : if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|s&s&O", &uri, &uri_len, UG(utf8_conv), &name, &name_len, UG(utf8_conv), &node, dom_documenttype_class_entry) == FAILURE) {
165 0 : return;
166 : }
167 :
168 1 : if (node != NULL) {
169 1 : DOM_GET_OBJ(doctype, node, xmlDtdPtr, doctobj);
170 1 : if (doctype->type == XML_DOCUMENT_TYPE_NODE) {
171 0 : php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid DocumentType object");
172 0 : RETURN_FALSE;
173 : }
174 1 : if (doctype->doc != NULL) {
175 0 : php_dom_throw_error(WRONG_DOCUMENT_ERR, 1 TSRMLS_CC);
176 0 : RETURN_FALSE;
177 : }
178 : } else {
179 0 : doctobj = NULL;
180 : }
181 :
182 1 : if (name_len > 0) {
183 1 : errorcode = dom_check_qname(name, &localname, &prefix, 1, name_len);
184 1 : if (errorcode == 0 && uri_len > 0 && ((nsptr = xmlNewNs(NULL, uri, prefix)) == NULL)) {
185 0 : errorcode = NAMESPACE_ERR;
186 : }
187 : }
188 :
189 1 : if (prefix != NULL) {
190 0 : xmlFree(prefix);
191 : }
192 :
193 1 : if (errorcode != 0) {
194 0 : if (localname != NULL) {
195 0 : xmlFree(localname);
196 : }
197 0 : php_dom_throw_error(errorcode, 1 TSRMLS_CC);
198 0 : RETURN_FALSE;
199 : }
200 :
201 : /* currently letting libxml2 set the version string */
202 1 : docp = xmlNewDoc(NULL);
203 1 : if (!docp) {
204 0 : if (localname != NULL) {
205 0 : xmlFree(localname);
206 : }
207 0 : RETURN_FALSE;
208 : }
209 :
210 1 : if (doctype != NULL) {
211 1 : docp->intSubset = doctype;
212 1 : doctype->parent = docp;
213 1 : doctype->doc = docp;
214 1 : docp->children = (xmlNodePtr) doctype;
215 1 : docp->last = (xmlNodePtr) doctype;
216 : }
217 :
218 1 : if (localname != NULL) {
219 1 : nodep = xmlNewDocNode (docp, nsptr, localname, NULL);
220 1 : if (!nodep) {
221 0 : if (doctype != NULL) {
222 0 : docp->intSubset = NULL;
223 0 : doctype->parent = NULL;
224 0 : doctype->doc = NULL;
225 0 : docp->children = NULL;
226 0 : docp->last = NULL;
227 : }
228 0 : xmlFreeDoc(docp);
229 0 : xmlFree(localname);
230 : /* Need some type of error here */
231 0 : php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unexpected Error");
232 0 : RETURN_FALSE;
233 : }
234 :
235 1 : nodep->nsDef = nsptr;
236 :
237 1 : xmlDocSetRootElement(docp, nodep);
238 1 : xmlFree(localname);
239 : }
240 :
241 1 : DOM_RET_OBJ(rv, (xmlNodePtr) docp, &ret, NULL);
242 :
243 1 : if (doctobj != NULL) {
244 1 : doctobj->document = ((dom_object *)((php_libxml_node_ptr *)docp->_private)->_private)->document;
245 1 : php_libxml_increment_doc_ref((php_libxml_node_object *)doctobj, docp TSRMLS_CC);
246 : }
247 : }
248 : /* }}} end dom_domimplementation_create_document */
249 :
250 : /* {{{ proto DOMNode dom_domimplementation_get_feature(string feature, string version) U
251 : URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMImplementation3-getFeature
252 : Since: DOM Level 3
253 : */
254 : PHP_METHOD(domimplementation, getFeature)
255 0 : {
256 0 : DOM_NOT_IMPLEMENTED();
257 : }
258 : /* }}} end dom_domimplementation_get_feature */
259 :
260 : #endif
261 :
262 : /*
263 : * Local variables:
264 : * tab-width: 4
265 : * c-basic-offset: 4
266 : * End:
267 : * vim600: noet sw=4 ts=4 fdm=marker
268 : * vim<600: noet sw=4 ts=4
269 : */
|