PluginProbe ʕ •ᴥ•ʔ
Matomo Analytics – Powerful, Privacy-First Insights for WordPress / trunk
Matomo Analytics – Powerful, Privacy-First Insights for WordPress vtrunk
5.11.1 5.11.0 5.10.2 5.10.1 trunk 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.1.0 1.1.1 1.1.2 1.1.3 1.2.0 1.3.0 1.3.1 1.3.2 4.0.0 4.0.1 4.0.2 4.0.3 4.0.4 4.1.0 4.1.1 4.1.2 4.1.3 4.10.0 4.11.0 4.12.0 4.13.0 4.13.2 4.13.3 4.13.4 4.13.5 4.14.0 4.14.1 4.14.2 4.15.0 4.15.1 4.15.2 4.15.3 4.2.0 4.3.0 4.3.1 4.4.1 4.4.2 4.5.0 4.6.0 5.0.1 5.0.2 5.0.3 5.0.4 5.0.5 5.0.6 5.0.7 5.0.8 5.1.0 5.1.1 5.1.2 5.1.3 5.1.4 5.1.5 5.1.6 5.1.7 5.10.0 5.2.0 5.2.1 5.2.2 5.3.0 5.3.1 5.3.2 5.3.3 5.6.0 5.6.1 5.7.0 5.7.1 5.8.0 5.8.1 5.8.2
matomo / app / vendor / symfony / process / Pipes / WindowsPipes.php
matomo / app / vendor / symfony / process / Pipes Last commit date
AbstractPipes.php 1 year ago PipesInterface.php 1 year ago UnixPipes.php 1 year ago WindowsPipes.php 1 year ago
WindowsPipes.php
172 lines
1 <?php
2
3 /*
4 * This file is part of the Symfony package.
5 *
6 * (c) Fabien Potencier <fabien@symfony.com>
7 *
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
10 */
11 namespace Symfony\Component\Process\Pipes;
12
13 use Symfony\Component\Process\Exception\RuntimeException;
14 use Symfony\Component\Process\Process;
15 /**
16 * WindowsPipes implementation uses temporary files as handles.
17 *
18 * @see https://bugs.php.net/51800
19 * @see https://bugs.php.net/65650
20 *
21 * @author Romain Neutron <imprec@gmail.com>
22 *
23 * @internal
24 */
25 class WindowsPipes extends \Symfony\Component\Process\Pipes\AbstractPipes
26 {
27 private $files = [];
28 private $fileHandles = [];
29 private $lockHandles = [];
30 private $readBytes = [Process::STDOUT => 0, Process::STDERR => 0];
31 private $haveReadSupport;
32 public function __construct($input, bool $haveReadSupport)
33 {
34 $this->haveReadSupport = $haveReadSupport;
35 if ($this->haveReadSupport) {
36 // Fix for PHP bug #51800: reading from STDOUT pipe hangs forever on Windows if the output is too big.
37 // Workaround for this problem is to use temporary files instead of pipes on Windows platform.
38 //
39 // @see https://bugs.php.net/51800
40 $pipes = [Process::STDOUT => Process::OUT, Process::STDERR => Process::ERR];
41 $tmpDir = sys_get_temp_dir();
42 $lastError = 'unknown reason';
43 set_error_handler(function ($type, $msg) use(&$lastError) {
44 $lastError = $msg;
45 });
46 for ($i = 0;; ++$i) {
47 foreach ($pipes as $pipe => $name) {
48 $file = sprintf('%s\\sf_proc_%02X.%s', $tmpDir, $i, $name);
49 if (!($h = fopen($file . '.lock', 'w'))) {
50 if (file_exists($file . '.lock')) {
51 continue 2;
52 }
53 restore_error_handler();
54 throw new RuntimeException('A temporary file could not be opened to write the process output: ' . $lastError);
55 }
56 if (!flock($h, \LOCK_EX | \LOCK_NB)) {
57 continue 2;
58 }
59 if (isset($this->lockHandles[$pipe])) {
60 flock($this->lockHandles[$pipe], \LOCK_UN);
61 fclose($this->lockHandles[$pipe]);
62 }
63 $this->lockHandles[$pipe] = $h;
64 if (!($h = fopen($file, 'w')) || !fclose($h) || !($h = fopen($file, 'r'))) {
65 flock($this->lockHandles[$pipe], \LOCK_UN);
66 fclose($this->lockHandles[$pipe]);
67 unset($this->lockHandles[$pipe]);
68 continue 2;
69 }
70 $this->fileHandles[$pipe] = $h;
71 $this->files[$pipe] = $file;
72 }
73 break;
74 }
75 restore_error_handler();
76 }
77 parent::__construct($input);
78 }
79 public function __sleep() : array
80 {
81 throw new \BadMethodCallException('Cannot serialize ' . __CLASS__);
82 }
83 public function __wakeup()
84 {
85 throw new \BadMethodCallException('Cannot unserialize ' . __CLASS__);
86 }
87 public function __destruct()
88 {
89 $this->close();
90 }
91 /**
92 * {@inheritdoc}
93 */
94 public function getDescriptors() : array
95 {
96 if (!$this->haveReadSupport) {
97 $nullstream = fopen('NUL', 'c');
98 return [['pipe', 'r'], $nullstream, $nullstream];
99 }
100 // We're not using pipe on Windows platform as it hangs (https://bugs.php.net/51800)
101 // We're not using file handles as it can produce corrupted output https://bugs.php.net/65650
102 // So we redirect output within the commandline and pass the nul device to the process
103 return [['pipe', 'r'], ['file', 'NUL', 'w'], ['file', 'NUL', 'w']];
104 }
105 /**
106 * {@inheritdoc}
107 */
108 public function getFiles() : array
109 {
110 return $this->files;
111 }
112 /**
113 * {@inheritdoc}
114 */
115 public function readAndWrite(bool $blocking, bool $close = \false) : array
116 {
117 $this->unblock();
118 $w = $this->write();
119 $read = $r = $e = [];
120 if ($blocking) {
121 if ($w) {
122 @stream_select($r, $w, $e, 0, Process::TIMEOUT_PRECISION * 1000000.0);
123 } elseif ($this->fileHandles) {
124 usleep((int) (Process::TIMEOUT_PRECISION * 1000000.0));
125 }
126 }
127 foreach ($this->fileHandles as $type => $fileHandle) {
128 $data = stream_get_contents($fileHandle, -1, $this->readBytes[$type]);
129 if (isset($data[0])) {
130 $this->readBytes[$type] += \strlen($data);
131 $read[$type] = $data;
132 }
133 if ($close) {
134 ftruncate($fileHandle, 0);
135 fclose($fileHandle);
136 flock($this->lockHandles[$type], \LOCK_UN);
137 fclose($this->lockHandles[$type]);
138 unset($this->fileHandles[$type], $this->lockHandles[$type]);
139 }
140 }
141 return $read;
142 }
143 /**
144 * {@inheritdoc}
145 */
146 public function haveReadSupport() : bool
147 {
148 return $this->haveReadSupport;
149 }
150 /**
151 * {@inheritdoc}
152 */
153 public function areOpen() : bool
154 {
155 return $this->pipes && $this->fileHandles;
156 }
157 /**
158 * {@inheritdoc}
159 */
160 public function close()
161 {
162 parent::close();
163 foreach ($this->fileHandles as $type => $handle) {
164 ftruncate($handle, 0);
165 fclose($handle);
166 flock($this->lockHandles[$type], \LOCK_UN);
167 fclose($this->lockHandles[$type]);
168 }
169 $this->fileHandles = $this->lockHandles = [];
170 }
171 }
172