View Issue Details

IDProjectCategoryView StatusLast Update
0001881XdebugInstallationpublic2020-11-05 16:25
Reporterrjung Assigned Toderick  
PrioritynormalSeverityminorReproducibilityalways
Status feedbackResolutionopen 
Product Version3.0.0beta1 
Summary0001881: Unterminated loop during unit test
DescriptionThe DebugClient class tests/debugger/dbgp/dbgpclient.php contains a do-while read loop in function doRead().

When the script debugged in the PHP child process terminates due to an error, this is not detected and the following call to doRead() will loop unterminated.

Observed on Solaris. The first attempt to read() from the socket after the child script error results on a ECONNRESET and all following ones simply will read zero bytes.

I scripted a workaround but it is not particularly elegent:

--- tests/debugger/dbgp/dbgpclient.php 2020-09-28 12:24:43.000000000 +0000
+++ tests/debugger/dbgp/dbgpclient.php 2020-11-05 17:11:34.378662701 +0000
@@ -8,6 +8,7 @@
        protected $port = 0;

        private $tmpDir;
+ private $closed = false;

        public function getPort()
        {
@@ -123,9 +124,31 @@
                        {
                                $end = false;
                        }
+ if ( preg_match( '@<error code=@', $read ) )
+ {
+ $end = true;
+ fclose( $conn );
+ $this->closed = true;
+ }
                } while( !$end );
        }

+ function close( $echo, $conn, $socket, $ppipes, $php )
+ {
+ if ( $echo )
+ {
+ echo "Connection unexpectedly closed\n";
+ echo @file_get_contents( $this->tmpDir . '/php-stdout.txt' ), "\n";
+ echo @file_get_contents( $this->tmpDir . '/php-stderr.txt' ), "\n";
+ echo @file_get_contents( $this->tmpDir . '/error-output.txt' ), "\n";
+ echo @file_get_contents( $this->tmpDir . '/remote_log.txt' ), "\n";
+ }
+ fclose( $socket );
+ fclose( $ppipes[0] );
+ fclose( $ppipes[1] );
+ proc_close( $php );
+ }
+
        function runTest( $filename, array $commands, array $ini_options = null )
        {
                $filename = realpath( $filename );
@@ -144,16 +167,17 @@

                if ( $conn === false )
                {
- echo @file_get_contents( $this->tmpDir . '/php-stdout.txt' ), "\n";
- echo @file_get_contents( $this->tmpDir . '/php-stderr.txt' ), "\n";
- echo @file_get_contents( $this->tmpDir . '/error-output.txt' ), "\n";
- echo @file_get_contents( $this->tmpDir . '/remote_log.txt' ), "\n";
- proc_close( $php );
+ $this->close(true, $conn, $socket, $ppipes, $php );
                        return;
                }

                // read header
                $this->doRead( $conn );
+ if ( $this->closed )
+ {
+ $this->close(true, $conn, $socket, $ppipes, $php );
+ return;
+ }
                foreach ( $commands as $command )
                {
                        // inject identifier
@@ -174,14 +198,15 @@
                        fwrite( $conn, $command . "\0" );

                        $this->doRead( $conn );
+ if ( $this->closed )
+ {
+ $this->close(true, $conn, $socket, $ppipes, $php );
+ return;
+ }

                        $i++;
                }
- fclose( $conn );
- fclose( $ppipes[0] );
- fclose( $ppipes[1] );
- fclose( $socket );
- proc_close( $php );
+ $this->close(false, $conn, $socket, $ppipes, $php);

                // echo @file_get_contents( $this->tmpDir . '/php-stderr.txt' ), "\n";
                // echo @file_get_contents( $this->tmpDir . '/error-output.txt' ), "\n";
Tagstest
Operating System
PHP Version8.0-dev

Activities

derick

2020-11-05 16:25

administrator   ~0005501

Do you have a reproducible case here?

Issue History

Date Modified Username Field Change
2020-11-05 16:13 rjung New Issue
2020-11-05 16:13 rjung Tag Attached: test
2020-11-05 16:25 derick Assigned To => derick
2020-11-05 16:25 derick Status new => feedback
2020-11-05 16:25 derick Note Added: 0005501