]> granicus.if.org Git - php/commitdiff
Fix RETURN & SWITCH memory leak issue
authorZeev Suraski <zeev@php.net>
Sat, 24 Jul 1999 11:43:21 +0000 (11:43 +0000)
committerZeev Suraski <zeev@php.net>
Sat, 24 Jul 1999 11:43:21 +0000 (11:43 +0000)
Zend/zend_compile.c
Zend/zend_stack.c
Zend/zend_stack.h

index 67fed1297f17a3e7404bcced32bc1f3a9ac88b83..634ebb8c3f697583799fa3007c8f0a11b28bd4bd 100644 (file)
@@ -832,10 +832,29 @@ void do_pass_param(znode *param, int op, int offset CLS_DC)
 }
 
 
-void do_return(znode *expr CLS_DC)
+static void generate_free_switch_expr(zend_switch_entry *switch_entry CLS_DC)
 {
        zend_op *opline = get_next_op(CG(active_op_array) CLS_CC);
 
+       return;
+       opline->opcode = ZEND_SWITCH_FREE;
+       opline->op1 = switch_entry->cond;
+       SET_UNUSED(opline->op2);
+}
+
+
+void do_return(znode *expr CLS_DC)
+{
+       zend_op *opline;
+       
+#ifdef ZTS
+       zend_stack_apply_with_argument(&CG(switch_cond_stack), (void (*)(void *element, void *)) generate_free_switch_expr, ZEND_STACK_APPLY_TOPDOWN CLS_CC);
+#else
+       zend_stack_apply(&CG(switch_cond_stack), (void (*)(void *element)) generate_free_switch_expr, ZEND_STACK_APPLY_TOPDOWN);
+#endif
+
+       opline = get_next_op(CG(active_op_array) CLS_CC);
+
        opline->opcode = ZEND_RETURN;
        if (expr) {
                opline->op1 = *expr;
index 1a4b062add2ab69fc89e85e662c6b5f5b0aae133..0f3b0f6aac693738199e641d5a62eb139a0edd61 100644 (file)
@@ -116,3 +116,41 @@ ZEND_API int zend_stack_count(zend_stack *stack)
 {
        return stack->top;
 }
+
+
+ZEND_API void zend_stack_apply(zend_stack *stack, void (*apply_function)(void *element), int type)
+{
+       int i;
+
+       switch (type) {
+               case ZEND_STACK_APPLY_TOPDOWN:
+                       for (i=stack->top-1; i>=0; i--) {
+                               apply_function(stack->elements[i]);
+                       }
+                       break;
+               case ZEND_STACK_APPLY_BOTTOMUP:
+                       for (i=0; i<stack->top; i++) {
+                               apply_function(stack->elements[i]);
+                       }
+                       break;
+       }
+}
+
+
+ZEND_API void zend_stack_apply_with_argument(zend_stack *stack, void (*apply_function)(void *element, void *arg), int type, void *arg)
+{
+       int i;
+
+       switch (type) {
+               case ZEND_STACK_APPLY_TOPDOWN:
+                       for (i=stack->top-1; i>=0; i--) {
+                               apply_function(stack->elements[i], arg);
+                       }
+                       break;
+               case ZEND_STACK_APPLY_BOTTOMUP:
+                       for (i=0; i<stack->top; i++) {
+                               apply_function(stack->elements[i], arg);
+                       }
+                       break;
+       }
+}
index 520f01092493173a730d9aa0ee4bcb9a38cdd1f5..5e084fd74f3410362b09eed9dfd7b222af7a0402 100644 (file)
@@ -38,6 +38,10 @@ ZEND_API int zend_stack_is_empty(zend_stack *stack);
 ZEND_API int zend_stack_destroy(zend_stack *stack);
 ZEND_API void **zend_stack_base(zend_stack *stack);
 ZEND_API int zend_stack_count(zend_stack *stack);
+ZEND_API void zend_stack_apply(zend_stack *stack, void (*apply_function)(void *element), int type);
+ZEND_API void zend_stack_apply_with_argument(zend_stack *stack, void (*apply_function)(void *element, void *arg), int type, void *arg);
 
+#define ZEND_STACK_APPLY_TOPDOWN       1
+#define ZEND_STACK_APPLY_BOTTOMUP      2
 
 #endif /* _ZEND_STACK_H */