diff --git a/examples/debug_trace.php b/examples/debug_trace.php new file mode 100644 index 00000000..b21ecce0 --- /dev/null +++ b/examples/debug_trace.php @@ -0,0 +1,25 @@ +run(); +} \ No newline at end of file diff --git a/src/Php/CompilerBase.php b/src/Php/CompilerBase.php index e07e9d53..fad1a54b 100644 --- a/src/Php/CompilerBase.php +++ b/src/Php/CompilerBase.php @@ -1095,7 +1095,16 @@ class CompilerBase extends \PhpAot\Core\Translator $code .= $this->genPropertyPromotion($argInfo); } $this->indentLevel--; - $code .= $this->genDebugInfo(); + // 构建 PHP 级别的函数名用于 debug backtrace + if ($this->class) { + $debugName = $this->class . '::' . $this->function; + } else { + $debugName = $this->function; + if ($this->namespace) { + $debugName = $this->namespace . '\\' . $debugName; + } + } + $code .= $this->genDebugInfo(null, $debugName, $v->getStartLine()); // 函数中存在动态调用的函数,需要在运行时动态切换作用域 if ($this->methodDef and $this->methodDef->hasDynamicCall) { @@ -5541,12 +5550,16 @@ class CompilerBase extends \PhpAot\Core\Translator return 'this_.call(' . $this->getMethodPtr($parentClass, $method) . ', ' . $this->parseCallArgs($expr->args) . ')'; } - protected function genDebugInfo(?NodeAbstract $stmt = null): string + protected function genDebugInfo(?NodeAbstract $stmt = null, string $functionName = '', int $startLine = 0): string { $code = ''; if ($this->debug) { if ($stmt) { $code .= 'php::traceDebugInfo("' . $this->escapeString($this->file) . '", ' . $stmt->getLine() . ');' . PHP_EOL; + } elseif ($functionName) { + $code .= 'php::enableDebugInfo();' . PHP_EOL; + $code .= 'php::pushDebugFrame("' . $this->escapeString($this->file) . '", ' . $startLine . ', "' . $this->escapeString($functionName) . '");' . PHP_EOL; + $code .= 'ON_SCOPE_EXIT(php::popDebugFrame());' . PHP_EOL; } else { $code .= 'php::enableDebugInfo();' . PHP_EOL; } diff --git a/tests/aot/debug_exception.phpt b/tests/aot/debug_exception.phpt new file mode 100644 index 00000000..b9f20fb6 --- /dev/null +++ b/tests/aot/debug_exception.phpt @@ -0,0 +1,22 @@ +--TEST-- +debug exception propagation through nested function calls +--FILE-- +getMessage() . "\n"; + echo "Exception class: " . get_class($e) . "\n"; + } +} +?> +--EXPECT-- +Caught: error at inner level +Exception class: Exception