This source file includes following definitions.
- _zval_dtor_func
- _zval_dtor_func_for_ptr
- _zval_internal_dtor
- _zval_internal_dtor_for_ptr
- zval_add_ref
- zval_add_ref_unref
- _zval_copy_ctor_func
- zend_print_variable
- _zval_dtor_wrapper
- _zval_internal_dtor_wrapper
- _zval_ptr_dtor_wrapper
- _zval_internal_ptr_dtor_wrapper
- zval_copy_static_var
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23 #include <stdio.h>
24 #include "zend.h"
25 #include "zend_API.h"
26 #include "zend_ast.h"
27 #include "zend_globals.h"
28 #include "zend_constants.h"
29 #include "zend_list.h"
30
31 ZEND_API void ZEND_FASTCALL _zval_dtor_func(zend_refcounted *p ZEND_FILE_LINE_DC)
32 {
33 switch (GC_TYPE(p)) {
34 case IS_STRING:
35 case IS_CONSTANT: {
36 zend_string *str = (zend_string*)p;
37 CHECK_ZVAL_STRING_REL(str);
38 zend_string_release(str);
39 break;
40 }
41 case IS_ARRAY: {
42 zend_array *arr = (zend_array*)p;
43 ZEND_ASSERT(GC_REFCOUNT(arr) <= 1);
44 zend_array_destroy(arr);
45 break;
46 }
47 case IS_CONSTANT_AST: {
48 zend_ast_ref *ast = (zend_ast_ref*)p;
49
50 zend_ast_destroy_and_free(ast->ast);
51 efree_size(ast, sizeof(zend_ast_ref));
52 break;
53 }
54 case IS_OBJECT: {
55 zend_object *obj = (zend_object*)p;
56
57 OBJ_RELEASE(obj);
58 break;
59 }
60 case IS_RESOURCE: {
61 zend_resource *res = (zend_resource*)p;
62
63 if (--GC_REFCOUNT(res) == 0) {
64
65 zend_list_free(res);
66 }
67 break;
68 }
69 case IS_REFERENCE: {
70 zend_reference *ref = (zend_reference*)p;
71 if (--GC_REFCOUNT(ref) == 0) {
72
73 i_zval_ptr_dtor(&ref->val ZEND_FILE_LINE_RELAY_CC);
74 efree_size(ref, sizeof(zend_reference));
75 }
76 break;
77 }
78 default:
79 break;
80 }
81 }
82
83 ZEND_API void ZEND_FASTCALL _zval_dtor_func_for_ptr(zend_refcounted *p ZEND_FILE_LINE_DC)
84 {
85 switch (GC_TYPE(p)) {
86 case IS_STRING:
87 case IS_CONSTANT: {
88 zend_string *str = (zend_string*)p;
89 CHECK_ZVAL_STRING_REL(str);
90 zend_string_free(str);
91 break;
92 }
93 case IS_ARRAY: {
94 zend_array *arr = (zend_array*)p;
95
96 zend_array_destroy(arr);
97 break;
98 }
99 case IS_CONSTANT_AST: {
100 zend_ast_ref *ast = (zend_ast_ref*)p;
101
102 zend_ast_destroy_and_free(ast->ast);
103 efree_size(ast, sizeof(zend_ast_ref));
104 break;
105 }
106 case IS_OBJECT: {
107 zend_object *obj = (zend_object*)p;
108
109 zend_objects_store_del(obj);
110 break;
111 }
112 case IS_RESOURCE: {
113 zend_resource *res = (zend_resource*)p;
114
115
116 zend_list_free(res);
117 break;
118 }
119 case IS_REFERENCE: {
120 zend_reference *ref = (zend_reference*)p;
121
122 i_zval_ptr_dtor(&ref->val ZEND_FILE_LINE_RELAY_CC);
123 efree_size(ref, sizeof(zend_reference));
124 break;
125 }
126 default:
127 break;
128 }
129 }
130
131 ZEND_API void _zval_internal_dtor(zval *zvalue ZEND_FILE_LINE_DC)
132 {
133 switch (Z_TYPE_P(zvalue)) {
134 case IS_STRING:
135 case IS_CONSTANT:
136 CHECK_ZVAL_STRING_REL(Z_STR_P(zvalue));
137 zend_string_release(Z_STR_P(zvalue));
138 break;
139 case IS_ARRAY:
140 case IS_CONSTANT_AST:
141 case IS_OBJECT:
142 case IS_RESOURCE:
143 zend_error_noreturn(E_CORE_ERROR, "Internal zval's can't be arrays, objects or resources");
144 break;
145 case IS_REFERENCE: {
146 zend_reference *ref = (zend_reference*)Z_REF_P(zvalue);
147
148 zval_internal_ptr_dtor(&ref->val);
149 free(ref);
150 break;
151 }
152 case IS_LONG:
153 case IS_DOUBLE:
154 case IS_FALSE:
155 case IS_TRUE:
156 case IS_NULL:
157 default:
158 break;
159 }
160 }
161
162 ZEND_API void _zval_internal_dtor_for_ptr(zval *zvalue ZEND_FILE_LINE_DC)
163 {
164 switch (Z_TYPE_P(zvalue)) {
165 case IS_STRING:
166 case IS_CONSTANT:
167 CHECK_ZVAL_STRING_REL(Z_STR_P(zvalue));
168 zend_string_free(Z_STR_P(zvalue));
169 break;
170 case IS_ARRAY:
171 case IS_CONSTANT_AST:
172 case IS_OBJECT:
173 case IS_RESOURCE:
174 zend_error_noreturn(E_CORE_ERROR, "Internal zval's can't be arrays, objects or resources");
175 break;
176 case IS_REFERENCE: {
177 zend_reference *ref = (zend_reference*)Z_REF_P(zvalue);
178
179 zval_internal_ptr_dtor(&ref->val);
180 free(ref);
181 break;
182 }
183 case IS_LONG:
184 case IS_DOUBLE:
185 case IS_FALSE:
186 case IS_TRUE:
187 case IS_NULL:
188 default:
189 break;
190 }
191 }
192
193
194
195
196
197 ZEND_API void zval_add_ref(zval *p)
198 {
199 if (Z_REFCOUNTED_P(p)) {
200 if (Z_ISREF_P(p) && Z_REFCOUNT_P(p) == 1) {
201 ZVAL_COPY(p, Z_REFVAL_P(p));
202 } else {
203 Z_ADDREF_P(p);
204 }
205 }
206 }
207
208 ZEND_API void zval_add_ref_unref(zval *p)
209 {
210 if (Z_REFCOUNTED_P(p)) {
211 if (Z_ISREF_P(p)) {
212 ZVAL_COPY(p, Z_REFVAL_P(p));
213 } else {
214 Z_ADDREF_P(p);
215 }
216 }
217 }
218
219 ZEND_API void ZEND_FASTCALL _zval_copy_ctor_func(zval *zvalue ZEND_FILE_LINE_DC)
220 {
221 if (EXPECTED(Z_TYPE_P(zvalue) == IS_ARRAY)) {
222 ZVAL_ARR(zvalue, zend_array_dup(Z_ARRVAL_P(zvalue)));
223 } else if (EXPECTED(Z_TYPE_P(zvalue) == IS_STRING) ||
224 EXPECTED(Z_TYPE_P(zvalue) == IS_CONSTANT)) {
225 CHECK_ZVAL_STRING_REL(Z_STR_P(zvalue));
226 Z_STR_P(zvalue) = zend_string_dup(Z_STR_P(zvalue), 0);
227 } else if (EXPECTED(Z_TYPE_P(zvalue) == IS_CONSTANT_AST)) {
228 zend_ast_ref *ast = emalloc(sizeof(zend_ast_ref));
229
230 GC_REFCOUNT(ast) = 1;
231 GC_TYPE_INFO(ast) = IS_CONSTANT_AST;
232 ast->ast = zend_ast_copy(Z_ASTVAL_P(zvalue));
233 Z_AST_P(zvalue) = ast;
234 }
235 }
236
237
238 ZEND_API size_t zend_print_variable(zval *var)
239 {
240 return zend_print_zval(var, 0);
241 }
242
243
244 ZEND_API void _zval_dtor_wrapper(zval *zvalue)
245 {
246 zval_dtor(zvalue);
247 }
248
249
250 #if ZEND_DEBUG
251 ZEND_API void _zval_internal_dtor_wrapper(zval *zvalue)
252 {
253 zval_internal_dtor(zvalue);
254 }
255
256
257 ZEND_API void _zval_ptr_dtor_wrapper(zval *zval_ptr)
258 {
259
260 i_zval_ptr_dtor(zval_ptr ZEND_FILE_LINE_CC);
261 }
262
263
264 ZEND_API void _zval_internal_ptr_dtor_wrapper(zval *zval_ptr)
265 {
266 zval_internal_ptr_dtor(zval_ptr);
267 }
268 #endif
269
270 ZEND_API int zval_copy_static_var(zval *p, int num_args, va_list args, zend_hash_key *key)
271 {
272 zend_array *symbol_table;
273 HashTable *target = va_arg(args, HashTable*);
274 zend_bool is_ref;
275 zval tmp;
276
277 if (Z_CONST_FLAGS_P(p) & (IS_LEXICAL_VAR|IS_LEXICAL_REF)) {
278 is_ref = Z_CONST_FLAGS_P(p) & IS_LEXICAL_REF;
279
280 symbol_table = zend_rebuild_symbol_table();
281 p = zend_hash_find(symbol_table, key->key);
282 if (!p) {
283 p = &tmp;
284 ZVAL_NULL(&tmp);
285 if (is_ref) {
286 ZVAL_NEW_REF(&tmp, &tmp);
287 zend_hash_add_new(symbol_table, key->key, &tmp);
288 Z_ADDREF_P(p);
289 } else {
290 zend_error(E_NOTICE,"Undefined variable: %s", ZSTR_VAL(key->key));
291 }
292 } else {
293 if (Z_TYPE_P(p) == IS_INDIRECT) {
294 p = Z_INDIRECT_P(p);
295 if (Z_TYPE_P(p) == IS_UNDEF) {
296 if (!is_ref) {
297 zend_error(E_NOTICE,"Undefined variable: %s", ZSTR_VAL(key->key));
298 p = &tmp;
299 ZVAL_NULL(&tmp);
300 } else {
301 ZVAL_NULL(p);
302 }
303 }
304 }
305 if (is_ref) {
306 ZVAL_MAKE_REF(p);
307 Z_ADDREF_P(p);
308 } else if (Z_ISREF_P(p)) {
309 ZVAL_DUP(&tmp, Z_REFVAL_P(p));
310 p = &tmp;
311 } else if (Z_REFCOUNTED_P(p)) {
312 Z_ADDREF_P(p);
313 }
314 }
315 } else if (Z_REFCOUNTED_P(p)) {
316 Z_ADDREF_P(p);
317 }
318 zend_hash_add(target, key->key, p);
319 return ZEND_HASH_APPLY_KEEP;
320 }
321
322
323
324
325
326
327
328
329