summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--NEWS2
-rwxr-xr-xZend/tests/bug26697.phpt24
-rw-r--r--Zend/zend.c1
-rw-r--r--Zend/zend_execute_API.c9
-rw-r--r--Zend/zend_globals.h1
5 files changed, 37 insertions, 0 deletions
diff --git a/NEWS b/NEWS
index 2d195be42a..44fab3455b 100644
--- a/NEWS
+++ b/NEWS
@@ -2,6 +2,8 @@ PHP NEWS
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
?? ??? 2004, PHP 5 RC 1
- Preserve class name casing for userspace classes. (Marcus)
+- Fixed bug #26697 (calling class_exists on a nonexistent class in __autoload
+ results in segfault). (Marcus)
- Fixed bug #26695 (Reflection API does not recognize mixed-case class hints).
(Marcus)
- Fixed bug #26690 (make xsltProcessor->transformToUri use streams wrappers).
diff --git a/Zend/tests/bug26697.phpt b/Zend/tests/bug26697.phpt
new file mode 100755
index 0000000000..8266a23e34
--- /dev/null
+++ b/Zend/tests/bug26697.phpt
@@ -0,0 +1,24 @@
+--TEST--
+Bug #26697 (calling class_exists on a nonexistent class in __autoload results in segfault)
+--SKIPIF--
+<?php if (function_exists('__autoload')) die('skip __autoload() declared in auto_prepend_file');?>
+--FILE--
+<?php
+
+function __autoload($name)
+{
+ echo __METHOD__ . "($name)\n";
+ var_dump(class_exists('NotExistingClass'));
+ echo __METHOD__ . "($name), done\n";
+}
+
+var_dump(class_exists('NotExistingClass'));
+
+?>
+===DONE===
+--EXPECTF--
+__autoload(NotExistingClass)
+bool(false)
+__autoload(NotExistingClass), done
+bool(false)
+===DONE===
diff --git a/Zend/zend.c b/Zend/zend.c
index cfaa465590..a4fabb393b 100644
--- a/Zend/zend.c
+++ b/Zend/zend.c
@@ -472,6 +472,7 @@ static void executor_globals_ctor(zend_executor_globals *executor_globals TSRMLS
EG(user_error_handler) = NULL;
EG(user_exception_handler) = NULL;
EG(in_execution) = 0;
+ EG(in_autoload) = 0;
EG(current_execute_data) = NULL;
}
diff --git a/Zend/zend_execute_API.c b/Zend/zend_execute_API.c
index 0b8f8d3f05..058e713ff8 100644
--- a/Zend/zend_execute_API.c
+++ b/Zend/zend_execute_API.c
@@ -138,6 +138,7 @@ void init_executor(TSRMLS_D)
EG(class_table) = CG(class_table);
EG(in_execution) = 0;
+ EG(in_autoload) = 0;
zend_ptr_stack_init(&EG(argument_stack));
@@ -791,6 +792,12 @@ ZEND_API int zend_lookup_class(char *name, int name_length, zend_class_entry ***
return SUCCESS;
}
+ if (EG(in_autoload)) {
+ free_alloca(lc_name);
+ return FAILURE;
+ }
+ EG(in_autoload) = 1;
+
ZVAL_STRINGL(&autoload_function, "__autoload", sizeof("__autoload")-1, 0);
INIT_PZVAL(class_name_ptr);
@@ -802,6 +809,8 @@ ZEND_API int zend_lookup_class(char *name, int name_length, zend_class_entry ***
EG(exception) = NULL;
retval = call_user_function_ex(EG(function_table), NULL, &autoload_function, &retval_ptr, 1, args, 0, NULL TSRMLS_CC);
+ EG(in_autoload) = 0;
+
if (retval == FAILURE) {
EG(exception) = exception;
free_alloca(lc_name);
diff --git a/Zend/zend_globals.h b/Zend/zend_globals.h
index 95f3c8933d..16c5e7848c 100644
--- a/Zend/zend_globals.h
+++ b/Zend/zend_globals.h
@@ -191,6 +191,7 @@ struct _zend_executor_globals {
int ticks_count;
zend_bool in_execution;
+ zend_bool in_autoload;
zend_bool bailout_set;
zend_bool full_tables_cleanup;
zend_bool implicit_clone;