Control: tag -1 patch

On Sat, Nov 12, 2016 at 06:33:16PM +0100, gregor herrmann wrote:
> On Sat, 20 Aug 2016 20:25:24 +0300, Niko Tyni wrote:

> > Looks like https://rt.cpan.org/Public/Bug/Display.html?id=101278 ;
> > quoting Slaven:
> > 
> >   So it seems that the completion of the fork() call is quite slow in
> >   this case. Setting $SIG{INT} to IGNORE did not happen yet in the child,
> >   so it was unexpectedly killed, and the next write() call caused a
> >   SIGPIPE in the parent
> 
> Sounds good :)
> I'm still not sure where to try and start looking for a fix ...

Here's a patch. Due to the accidental testing remigration, it looks
like there's still some time to salvage this package for stretch.
-- 
Niko
>From 8e896957bc0580b53f74152647265a5ea2cdbdf6 Mon Sep 17 00:00:00 2001
From: Niko Tyni <nt...@debian.org>
Date: Tue, 3 Jan 2017 13:54:52 +0000
Subject: [PATCH] Fix a race condition with the SIGINT handler

The parent now waits until the child is ready before proceeding.

This fixes sporadic test failures in t/File-Tee.t.

Bug-Debian: https://bugs.debian.org/834912
Bug: https://rt.cpan.org/Public/Bug/Display.html?id=101278
---
 lib/File/Tee.pm | 13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/lib/File/Tee.pm b/lib/File/Tee.pm
index caa4ae2..075a9f7 100644
--- a/lib/File/Tee.pm
+++ b/lib/File/Tee.pm
@@ -149,15 +149,23 @@ sub tee (*;@) {
     $| = $oldstate[0];
     select $oldsel;
 
+    my ($readp, $writep);
+    pipe ($readp, $writep)
+        or croak "Failed to make a pipe for synchronizing";
+
     my $pid = open $fh, '|-';
     unless ($pid) {
         defined $pid
             or return undef;
 
+        close $readp; # this end is not for us
+
 	$SIG{INT} = 'IGNORE';
         undef @ARGV;
         eval { $0 = "perl [File::Tee]" };
 
+        close $writep; # signal the parent we're ready
+
         my $error = 0;
 
         my $oldsel = select STDERR;
@@ -252,6 +260,11 @@ sub tee (*;@) {
 
         _exit($error);
     }
+    close $writep; # this end is not for us
+
+    sysread($readp, my $buf, 256); # should block until the kid is ready
+    close $readp;
+
     # close $teefh;
 
     $oldsel = select($fh);
-- 
2.11.0

Reply via email to