Hacktoberfest 2026:メンテナが10月に向けて印を付けた、オープンで初心者向けの issue。 Hacktoberfest の issue を見る

Magic property access skips __get() when another Fiber is suspended in __get() on the same object

オープン
#23,075 コメント 0 件 リアクション 0 件 担当者 0 名 GitHub で見る

メンテナーはふだん 1 日以内に返信

まだ誰も着手していません。

評価

難易度
4/5
見積もり時間
3〜5日
初心者へのやさしさ
48/100
issue の種類
バグ
明瞭さ
おおむね明確
活発さ
静か
技術スタック
php
領域
compilers

調査の方向性

提供された fiber-magic-get.php の再現コードから始め、php -n で実行してから、実際の出力と期待される出力を比較します。共有オブジェクトを使用する 2 つの Fibers にまたがるオーバーロードされたプロパティの再帰ガードを、関連する __isset() と null 合体のケースも含めて調査します。両方の独立したアクセスがそれぞれのハンドラーを呼び出し、期待される値を返せば完了です。

索引モデルが issue の本文から書いたものです。

説明

Bug Category: Fibers Status: Verified
Description
Description

When two Fibers access the same undefined property on the same object, and the
first Fiber suspends inside __get(), the second Fiber does not invoke
__get().

Instead, PHP emits an "Undefined property" warning and returns null.
After the first Fiber is resumed, its property access returns the correct value.

The access from the second Fiber is not a recursive property access. It is an
independent access with its own Fiber execution stack.

The issue reproduces with php -n, without loading a php.ini or third-party
extensions.

Steps to reproduce

Save the following script as fiber-magic-get.php:

<?php

declare(strict_types=1);

final class YieldingProperty
{
    public function __get(string $name): int
    {
        Fiber::suspend();
        return 8;
    }
}

$value = new YieldingProperty();

$first = new Fiber(static function () use ($value): void {
    var_dump($value->property);
});

$second = new Fiber(static function () use ($value): void {
    var_dump($value->property);
});

$first->start();
$second->start();
$first->resume();

Run it without loading configuration or extensions:

php -n fiber-magic-get.php
Actual result
Warning: Undefined property: YieldingProperty::$property ...
NULL
int(8)

__get() is skipped for the second Fiber and the property access returns
null.

Expected result
int(8)
int(8)

Both property accesses should invoke __get() independently and return 8.

Suspending one Fiber inside __get() should not make an access from another
Fiber appear recursive.

Reproducibility

Always reproducible.

Tested with:

  • PHP 8.3.33 CLI on Linux, using php -n
  • PHP 8.4.7 CLI on Windows, using php -n
Additional information

The issue only occurs when the Fibers share the same object.

The following controls do not fail:

  • Giving each Fiber its own object
  • Replacing the magic property access with a normal method call on the shared
    object

The same problem also affects __isset() and null-coalescing property
expressions such as:

$value = $object->property ?? 0;

Under contention, these expressions can silently return the fallback value
even though __isset() returns true and __get() returns the expected value.

This behavior suggests that the recursion guard for overloaded properties is
associated with the shared object and remains visible to other Fibers while a
magic property handler is suspended.

PHP Version
PHP 8.3.33 (cli) (built: Jul 31 2026 12:56:07) (NTS)
Copyright (c) The PHP Group
Zend Engine v4.3.33, Copyright (c) Zend Technologies
    with Zend OPcache v8.3.33, Copyright (c), by Zend Technologies

PHP 8.4.7 (cli) (built: May  6 2025 14:12:45) (ZTS Visual C++ 2022 x64)
Copyright (c) The PHP Group
Zend Engine v4.4.7, Copyright (c) Zend Technologies
Operating System

Windows 11, Plesk Linux ... 6.8.0-111-generic #111-Ubuntu SMP PREEMPT_DYNAMIC Sat Apr 11 23:16:02 UTC 2026 x86_64 x86_64 x86_64 GNU/Linux

主要言語
C
スター
40.4k
フォーク
8.2k
平均マージ
2日 9時間
マージ済み PR(30日)
122

環境構築

はじめの一歩

  1. issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
  2. 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
  3. リポジトリをフォークし、ブランチを切って変更します。
  4. issue 番号を参照したプルリクエストを送ります。

php/php-src のほかの issue

php/php-src の issue をすべて見る

似ている issue

C の issue をもっと見る

新しい issue をメールで受け取る

初心者向けの GitHub issue を短くまとめたダイジェスト。