function RunStep($runner) { BenchmarkSuite::ResetRNG(); $this->results = array(); $this->runner = $runner; $length = count($this->benchmarks); $index = 0; $suite = $this; $data = null; $RunNextSetup = null; $RunNextBenchmark = null; $RunNextTearDown = null; // Run the setup, the actual benchmark, and the tear down in three // separate steps to allow the framework to yield between any of the // steps. $RunNextSetup = function () use($suite, &$index, $length, &$RunNextBenchmark) { if ($index < $length) { try { $setup = $suite->benchmarks[$index]->Setup; $setup(); } catch (Exception $e) { $suite->NotifyError($e); return null; } return $RunNextBenchmark; } $suite->NotifyResult(); return null; }; $RunNextBenchmark = function () use($suite, &$index, &$data, &$RunNextTearDown, &$RunNextBenchmark) { try { $data = $suite->RunSingleBenchmark($suite->benchmarks[$index], $data); } catch (Exception $e) { $suite->NotifyError($e); return null; } // If data is null, we're done with this benchmark. return is_null($data) ? $RunNextTearDown : $RunNextBenchmark(); }; $RunNextTearDown = function () use($suite, &$index, &$RunNextSetup) { try { $tearDown = $suite->benchmarks[$index++]->TearDown; $tearDown(); } catch (Exception $e) { $suite->NotifyError($e); return null; } return $RunNextSetup; }; // Start out running the setup. return $RunNextSetup(); }