title: race condition in PHP using pthreads
body: <p>I have small code that demonstrate how to perform a race condition in multithreads PHP.</p>
  <p>The idea is I and my friend is sharing the pot for cooking. if the pot already have ingredient, so the pot can not cook.</p>
  <p>class Pot:</p>
  <pre class="lang-php prettyprint-override"><code>class Pot
  {
      public $id;
      function __construct()
      {
          $this-&gt;id = rand();
      }
  
      public $ingredient;
  
      public function cook($ingredient, $who, $time){
          if ($this-&gt;ingredient==null){
              $this-&gt;ingredient = $ingredient;
              print &quot;pot&quot;.$this-&gt;id.'/'.$who.&quot; cooking &quot;.$this-&gt;ingredient. &quot; time spent: &quot;.$time.&quot; \n&quot;;
              sleep($time);
              print &quot;pot&quot;.$this-&gt;id.'/'.$who.&quot; had flush ingredient \n&quot;;
              $this-&gt;ingredient = null;
              
          }else{
              throw new Exception(&quot;Pot still cook &quot;.$this-&gt;ingredient);
          }
      }
  }
  </code></pre>
  <p>class Friend:</p>
  <pre><code>class Friend extends Thread
  {
      /**
       * @var Pot
       */
      protected $pot;
  
      function run() {
          Cocking::cleanVegetable(&quot;Friend&quot;);
          print &quot;Friend will cook: \n&quot;;
          $this-&gt;pot-&gt;cook(&quot;vegetable&quot;, 'Friend',4);
          Cocking::digVegetable(&quot;Friend&quot;);
      }
  
      public function __construct($pot)
      {
          $this-&gt;pot = $pot;
      }
  }
  </code></pre>
  <p>class My:</p>
  <pre class="lang-php prettyprint-override"><code>class My
  {
      /**
       * @var Pot
       */
      private $pot;
      public function doMyJob(){
          Cocking::cleanRice(&quot;I&quot;);
          print &quot;I will cook: \n&quot;;
          $this-&gt;pot-&gt;cook(&quot;rice&quot;, &quot;I&quot;,10);
  
  
          Cocking::digRice(&quot;I&quot;);
      }
  
      public function playGame(Friend $friend){
          print &quot;play with friend \n&quot;;
      }
  
      public function __construct($pot)
      {
          $this-&gt;pot = $pot;
      }
  }
  </code></pre>
  <p>class Coocking:</p>
  <pre class="lang-php prettyprint-override"><code>&lt;?php
  
  
  class Cocking
  {
      static function cleanRice($who){
          print $who.&quot; is cleaning rice \n&quot;;
      }
      static function cleanVegetable($who){
          print $who.&quot;is cleaning vegetable \n&quot;;
      }
  
  
      static function digRice($who){
          print $who.&quot; is digging rice \n&quot;;
      }
  
      static function digVegetable($who){
          print $who.&quot; is digging vegetable \n&quot;;
      }
  }
  </code></pre>
  <p>running script:</p>
  <pre class="lang-php prettyprint-override"><code>require_once &quot;Friend.php&quot;;
  require_once &quot;My.php&quot;;
  require_once &quot;Cocking.php&quot;;
  require_once &quot;Pot.php&quot;;
  
  $pot = new Pot();
  $friend = new Friend($pot);
  $my = new My($pot);
  
  $friend-&gt;start();
  $my-&gt;doMyJob();
  $friend-&gt;join();
  $my-&gt;playGame($friend);
  </code></pre>
  <p>that is so wreid that the output never throw exception? that i assume always happen.</p>
  <pre><code>root@e03ed8b56f21:/app/RealLive# php index.php
  Friendis cleaning vegetable
  I is cleaning rice
  Friend will cook:
  I will cook:
  pot926057642/I cooking rice time spent: 10
  pot926057642/Friend cooking vegetable time spent: 4
  pot926057642/Friend had flush ingredient
  Friend is digging vegetable
  pot926057642/I had flush ingredient
  I is digging rice
  play with friend
  </code></pre>
  <p>the <code>Pot</code> had used by me, but my friend still can use it to cook vegetable. that so freak?
  i expect the result would be:</p>
  <pre class="lang-php prettyprint-override"><code>Friend will cook:
  I will cook:
  pot926057642/I cooking rice time spent: 10
  PHP Fatal error:  Uncaught Exception: Pot still cook rice in /app/RealLive/Pot.php:23
  Stack trace:
  #0 /app/RealLive/My.php(14): Pot-&gt;cook('rice', 'I', 10)
  #1 /app/RealLive/index.php(12): My-&gt;doMyJob()
  #2 {main}
    thrown in /app/RealLive/Pot.php on line 23
  </code></pre>
  <p>ps: my env is</p>
  <pre class="lang-php prettyprint-override"><code>PHP 7.0.10 (cli) (built: Apr 30 2019 21:14:24) ( ZTS )
  Copyright (c) 1997-2016 The PHP Group
  Zend Engine v3.0.0, Copyright (c) 1998-2016 Zend Technologies
  </code></pre>
  <p>Many thanks from your comment.</p>