Skip to content

Commit 6ce4d38

Browse files
bug #40065 [ErrorHandler] fix handling messages with null bytes from anonymous classes (nicolas-grekas)
This PR was merged into the 4.4 branch. Discussion ---------- [ErrorHandler] fix handling messages with null bytes from anonymous classes | Q | A | ------------- | --- | Branch? | 4.4 | Bug fix? | yes | New feature? | no | Deprecations? | no | Tickets | - | License | MIT | Doc PR | - PHP truncates error messages at null bytes before calling userland error handlers (known behavior in PHP, marked as "won't fix".) This doesn't play well with anonymous classes. This PR works around the issue by getting the message from the stack trace. Commits ------- ac94746 [ErrorHandler] fix handling messages with null bytes from anonymous classes
2 parents 75e7fb6 + ac94746 commit 6ce4d38

File tree

2 files changed

+23
-12
lines changed

2 files changed

+23
-12
lines changed

src/Symfony/Component/ErrorHandler/ErrorHandler.php

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -422,11 +422,7 @@ public function handleError(int $type, string $message, string $file, int $line)
422422
return false;
423423
}
424424

425-
if (false !== strpos($message, "@anonymous\0")) {
426-
$logMessage = $this->parseAnonymousClass($message);
427-
} else {
428-
$logMessage = $this->levels[$type].': '.$message;
429-
}
425+
$logMessage = $this->levels[$type].': '.$message;
430426

431427
if (null !== self::$toStringException) {
432428
$errorAsException = self::$toStringException;
@@ -455,6 +451,23 @@ public function handleError(int $type, string $message, string $file, int $line)
455451
return true;
456452
}
457453
} else {
454+
if (false !== strpos($message, '@anonymous')) {
455+
$backtrace = debug_backtrace(false, 5);
456+
457+
for ($i = 1; isset($backtrace[$i]); ++$i) {
458+
if (isset($backtrace[$i]['function'], $backtrace[$i]['args'][0])
459+
&& ('trigger_error' === $backtrace[$i]['function'] || 'user_error' === $backtrace[$i]['function'])
460+
) {
461+
if ($backtrace[$i]['args'][0] !== $message) {
462+
$message = $this->parseAnonymousClass($backtrace[$i]['args'][0]);
463+
$logMessage = $this->levels[$type].': '.$message;
464+
}
465+
466+
break;
467+
}
468+
}
469+
}
470+
458471
$errorAsException = new \ErrorException($logMessage, 0, $type, $file, $line);
459472

460473
if ($throw || $this->tracedErrors & $type) {

src/Symfony/Component/ErrorHandler/Tests/ErrorHandlerTest.php

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -368,22 +368,20 @@ public function testHandleUserError()
368368

369369
public function testHandleErrorWithAnonymousClass()
370370
{
371+
$anonymousObject = new class() extends \stdClass {
372+
};
373+
371374
$handler = ErrorHandler::register();
372-
$handler->throwAt(3, true);
373375
try {
374-
$handler->handleError(3, 'foo '.\get_class(new class() extends \stdClass {
375-
}).' bar', 'foo.php', 12);
376+
trigger_error('foo '.\get_class($anonymousObject).' bar', \E_USER_WARNING);
376377
$this->fail('Exception expected.');
377378
} catch (\ErrorException $e) {
378379
} finally {
379380
restore_error_handler();
380381
restore_exception_handler();
381382
}
382383

383-
$this->assertSame('foo stdClass@anonymous bar', $e->getMessage());
384-
$this->assertSame(3, $e->getSeverity());
385-
$this->assertSame('foo.php', $e->getFile());
386-
$this->assertSame(12, $e->getLine());
384+
$this->assertSame('User Warning: foo stdClass@anonymous bar', $e->getMessage());
387385
}
388386

389387
public function testHandleDeprecation()

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy