ead74ac57a8043e90e3e73a581a42b06a0941c8c
[m6w6/ext-http] / http_request_method_api.c
1 /*
2 +--------------------------------------------------------------------+
3 | PECL :: http |
4 +--------------------------------------------------------------------+
5 | Redistribution and use in source and binary forms, with or without |
6 | modification, are permitted provided that the conditions mentioned |
7 | in the accompanying LICENSE file are met. |
8 +--------------------------------------------------------------------+
9 | Copyright (c) 2004-2005, Michael Wallner <mike@php.net> |
10 +--------------------------------------------------------------------+
11 */
12
13 /* $Id$ */
14
15 #ifdef HAVE_CONFIG_H
16 # include "config.h"
17 #endif
18
19 #define HTTP_WANT_CURL
20 #include "php_http.h"
21
22 #include "php_http_api.h"
23 #include "php_http_request_api.h"
24 #include "php_http_request_method_api.h"
25
26 #if defined(ZEND_ENGINE_2) && defined(HTTP_HAVE_CURL) && !defined(WONKY)
27 # include "php_http_request_object.h"
28 #endif
29
30 /* {{{ char *http_request_methods[] */
31 static const char *const http_request_methods[] = {
32 "UNKNOWN",
33 /* HTTP/1.1 */
34 "GET",
35 "HEAD",
36 "POST",
37 "PUT",
38 "DELETE",
39 "OPTIONS",
40 "TRACE",
41 "CONNECT",
42 /* WebDAV - RFC 2518 */
43 "PROPFIND",
44 "PROPPATCH",
45 "MKCOL",
46 "COPY",
47 "MOVE",
48 "LOCK",
49 "UNLOCK",
50 /* WebDAV Versioning - RFC 3253 */
51 "VERSION-CONTROL",
52 "REPORT",
53 "CHECKOUT",
54 "CHECKIN",
55 "UNCHECKOUT",
56 "MKWORKSPACE",
57 "UPDATE",
58 "LABEL",
59 "MERGE",
60 "BASELINE-CONTROL",
61 "MKACTIVITY",
62 /* WebDAV Access Control - RFC 3744 */
63 "ACL",
64 NULL
65 };
66 /* }}} */
67
68 PHP_MINIT_FUNCTION(http_request_method)
69 {
70 /* HTTP/1.1 */
71 HTTP_LONG_CONSTANT("HTTP_METH_GET", HTTP_GET);
72 HTTP_LONG_CONSTANT("HTTP_METH_HEAD", HTTP_HEAD);
73 HTTP_LONG_CONSTANT("HTTP_METH_POST", HTTP_POST);
74 HTTP_LONG_CONSTANT("HTTP_METH_PUT", HTTP_PUT);
75 HTTP_LONG_CONSTANT("HTTP_METH_DELETE", HTTP_DELETE);
76 HTTP_LONG_CONSTANT("HTTP_METH_OPTIONS", HTTP_OPTIONS);
77 HTTP_LONG_CONSTANT("HTTP_METH_TRACE", HTTP_TRACE);
78 HTTP_LONG_CONSTANT("HTTP_METH_CONNECT", HTTP_CONNECT);
79 /* WebDAV - RFC 2518 */
80 HTTP_LONG_CONSTANT("HTTP_METH_PROPFIND", HTTP_PROPFIND);
81 HTTP_LONG_CONSTANT("HTTP_METH_PROPPATCH", HTTP_PROPPATCH);
82 HTTP_LONG_CONSTANT("HTTP_METH_MKCOL", HTTP_MKCOL);
83 HTTP_LONG_CONSTANT("HTTP_METH_COPY", HTTP_COPY);
84 HTTP_LONG_CONSTANT("HTTP_METH_MOVE", HTTP_MOVE);
85 HTTP_LONG_CONSTANT("HTTP_METH_LOCK", HTTP_LOCK);
86 HTTP_LONG_CONSTANT("HTTP_METH_UNLOCK", HTTP_UNLOCK);
87 /* WebDAV Versioning - RFC 3253 */
88 HTTP_LONG_CONSTANT("HTTP_METH_VERSION_CONTROL", HTTP_VERSION_CONTROL);
89 HTTP_LONG_CONSTANT("HTTP_METH_REPORT", HTTP_REPORT);
90 HTTP_LONG_CONSTANT("HTTP_METH_CHECKOUT", HTTP_CHECKOUT);
91 HTTP_LONG_CONSTANT("HTTP_METH_CHECKIN", HTTP_CHECKIN);
92 HTTP_LONG_CONSTANT("HTTP_METH_UNCHECKOUT", HTTP_UNCHECKOUT);
93 HTTP_LONG_CONSTANT("HTTP_METH_MKWORKSPACE", HTTP_MKWORKSPACE);
94 HTTP_LONG_CONSTANT("HTTP_METH_UPDATE", HTTP_UPDATE);
95 HTTP_LONG_CONSTANT("HTTP_METH_LABEL", HTTP_LABEL);
96 HTTP_LONG_CONSTANT("HTTP_METH_MERGE", HTTP_MERGE);
97 HTTP_LONG_CONSTANT("HTTP_METH_BASELINE_CONTROL", HTTP_BASELINE_CONTROL);
98 HTTP_LONG_CONSTANT("HTTP_METH_MKACTIVITY", HTTP_MKACTIVITY);
99 /* WebDAV Access Control - RFC 3744 */
100 HTTP_LONG_CONSTANT("HTTP_METH_ACL", HTTP_ACL);
101
102 return SUCCESS;
103 }
104
105 PHP_RSHUTDOWN_FUNCTION(http_request_method)
106 {
107 int i, c = zend_hash_num_elements(&HTTP_G(request).methods.custom);
108
109 for (i = 0; i < c; ++i) {
110 http_request_method_unregister(HTTP_MAX_REQUEST_METHOD + i);
111 }
112
113 return SUCCESS;
114 }
115
116 /* {{{ char *http_request_method_name(http_request_method) */
117 PHP_HTTP_API const char *_http_request_method_name(http_request_method m TSRMLS_DC)
118 {
119 zval **meth;
120
121 if (HTTP_STD_REQUEST_METHOD(m)) {
122 return http_request_methods[m];
123 }
124
125 if (SUCCESS == zend_hash_index_find(&HTTP_G(request).methods.custom, HTTP_CUSTOM_REQUEST_METHOD(m), (void **) &meth)) {
126 return Z_STRVAL_PP(meth);
127 }
128
129 return http_request_methods[0];
130 }
131 /* }}} */
132
133 /* {{{ ulong http_request_method_exists(zend_bool, ulong, char *) */
134 PHP_HTTP_API ulong _http_request_method_exists(zend_bool by_name, ulong id, const char *name TSRMLS_DC)
135 {
136 if (by_name) {
137 unsigned i;
138
139 for (i = HTTP_NO_REQUEST_METHOD + 1; i < HTTP_MAX_REQUEST_METHOD; ++i) {
140 if (!strcmp(name, http_request_methods[i])) {
141 return i;
142 }
143 }
144 {
145 zval **data;
146 char *key;
147 ulong idx;
148 HashPosition pos;
149
150 FOREACH_HASH_KEYVAL(pos, &HTTP_G(request).methods.custom, key, idx, data) {
151 if (!strcmp(name, Z_STRVAL_PP(data))) {
152 return idx + HTTP_MAX_REQUEST_METHOD;
153 }
154 }
155 }
156 return 0;
157 } else {
158 return HTTP_STD_REQUEST_METHOD(id) || zend_hash_index_exists(&HTTP_G(request).methods.custom, HTTP_CUSTOM_REQUEST_METHOD(id)) ? id : 0;
159 }
160 }
161 /* }}} */
162
163 /* {{{ ulong http_request_method_register(char *) */
164 PHP_HTTP_API ulong _http_request_method_register(const char *method_name, size_t method_name_len TSRMLS_DC)
165 {
166 zval array;
167 char *http_method, *method;
168 ulong i, meth_num = HTTP_G(request).methods.custom.nNextFreeElement + HTTP_MAX_REQUEST_METHOD;
169
170 method = emalloc(method_name_len + 1);
171 for (i = 0; i < method_name_len; ++i) {
172 method[i] = toupper(method_name[i]);
173 }
174 method[method_name_len] = '\0';
175
176 INIT_ZARR(array, &HTTP_G(request).methods.custom);
177 add_next_index_stringl(&array, method, method_name_len, 0);
178
179 method_name_len = spprintf(&http_method, 0, "HTTP_METH_%s", method);
180 zend_register_long_constant(http_method, method_name_len + 1, meth_num, CONST_CS, http_module_number TSRMLS_CC);
181 efree(http_method);
182
183 #if defined(ZEND_ENGINE_2) && defined(HTTP_HAVE_CURL) && !defined(WONKY)
184 method_name_len = spprintf(&http_method, 0, "METH_%s", method);
185 zend_declare_class_constant_long(http_request_object_ce, http_method, method_name_len, meth_num TSRMLS_CC);
186 efree(http_method);
187 #endif
188
189 return meth_num;
190 }
191 /* }}} */
192
193 /* {{{ STATUS http_request_method_unregister(usngigned long) */
194 PHP_HTTP_API STATUS _http_request_method_unregister(ulong method TSRMLS_DC)
195 {
196 zval **zmethod;
197 char *http_method;
198 int method_len;
199
200 if (SUCCESS != zend_hash_index_find(&HTTP_G(request).methods.custom, HTTP_CUSTOM_REQUEST_METHOD(method), (void **) &zmethod)) {
201 http_error_ex(HE_NOTICE, HTTP_E_REQUEST_METHOD, "Request method with id %lu does not exist", method);
202 return FAILURE;
203 }
204
205 #if defined(ZEND_ENGINE_2) && defined(HTTP_HAVE_CURL) && !defined(WONKY)
206 method_len = spprintf(&http_method, 0, "METH_%s", Z_STRVAL_PP(zmethod));
207 if ((SUCCESS != zend_hash_del(&http_request_object_ce->constants_table, http_method, method_len + 1))) {
208 http_error_ex(HE_NOTICE, HTTP_E_REQUEST_METHOD, "Could not unregister request method: HttpRequest::%s", http_method);
209 efree(http_method);
210 return FAILURE;
211 }
212 efree(http_method);
213 #endif
214
215 method_len = spprintf(&http_method, 0, "HTTP_METH_%s", Z_STRVAL_PP(zmethod));
216 if ( (SUCCESS != zend_hash_index_del(&HTTP_G(request).methods.custom, HTTP_CUSTOM_REQUEST_METHOD(method)))
217 || (SUCCESS != zend_hash_del(EG(zend_constants), http_method, method_len + 1))) {
218 http_error_ex(HE_NOTICE, HTTP_E_REQUEST_METHOD, "Could not unregister request method: %s", http_method);
219 efree(http_method);
220 return FAILURE;
221 }
222 efree(http_method);
223
224 return SUCCESS;
225 }
226 /* }}} */
227
228 /*
229 * Local variables:
230 * tab-width: 4
231 * c-basic-offset: 4
232 * End:
233 * vim600: noet sw=4 ts=4 fdm=marker
234 * vim<600: noet sw=4 ts=4
235 */
236