Skip to content
This repository was archived by the owner on Jun 1, 2023. It is now read-only.

Commit 07bfbad

Browse files
author
Reini Urban
committed
PerlIOStdio_dup: survive empty fh
Fixes [perl #63244], which is broken from 5.8.8 to blead.
1 parent 70defe2 commit 07bfbad

File tree

3 files changed

+39
-21
lines changed

3 files changed

+39
-21
lines changed

perlio.c

Lines changed: 24 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -3122,26 +3122,30 @@ PerlIOStdio_dup(pTHX_ PerlIO *f, PerlIO *o, CLONE_PARAMS *param, int flags)
31223122
*/
31233123
if ((f = PerlIOBase_dup(aTHX_ f, o, param, flags))) {
31243124
FILE *stdio = PerlIOSelf(o, PerlIOStdio)->stdio;
3125-
const int fd = fileno(stdio);
3126-
char mode[8];
3127-
if (flags & PERLIO_DUP_FD) {
3128-
const int dfd = PerlLIO_dup(fileno(stdio));
3129-
if (dfd >= 0) {
3130-
stdio = PerlSIO_fdopen(dfd, PerlIO_modestr(o,mode));
3131-
goto set_this;
3132-
}
3133-
else {
3134-
NOOP;
3135-
/* FIXME: To avoid messy error recovery if dup fails
3136-
re-use the existing stdio as though flag was not set
3137-
*/
3138-
}
3139-
}
3140-
stdio = PerlSIO_fdopen(fd, PerlIO_modestr(o,mode));
3141-
set_this:
3142-
PerlIOSelf(f, PerlIOStdio)->stdio = stdio;
3143-
if(stdio) {
3144-
PerlIOUnix_refcnt_inc(fileno(stdio));
3125+
if (!stdio) {
3126+
return f;
3127+
} else {
3128+
const int fd = fileno(stdio);
3129+
char mode[8];
3130+
if (flags & PERLIO_DUP_FD) {
3131+
const int dfd = PerlLIO_dup(fd);
3132+
if (dfd >= 0) {
3133+
stdio = PerlSIO_fdopen(dfd, PerlIO_modestr(o,mode));
3134+
goto set_this;
3135+
}
3136+
else {
3137+
NOOP;
3138+
/* FIXME: To avoid messy error recovery if dup fails
3139+
re-use the existing stdio as though flag was not set
3140+
*/
3141+
}
3142+
}
3143+
stdio = PerlSIO_fdopen(fd, PerlIO_modestr(o,mode));
3144+
set_this:
3145+
PerlIOSelf(f, PerlIOStdio)->stdio = stdio;
3146+
if (stdio) {
3147+
PerlIOUnix_refcnt_inc(fileno(stdio));
3148+
}
31453149
}
31463150
}
31473151
return f;

pod/perlcdelta.pod

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -751,6 +751,11 @@ See L<RT #128204|https://rt.perl.org/Public/Bug/Display.html?id=128204>
751751

752752
See L<RT #128313|https://rt.perl.org/Public/Bug/Display.html?id=128313>
753753

754+
=item Fix PERLIO=stdio dup on empty filehandle
755+
756+
See L<RT #63244|https://rt.perl.org/Public/Bug/Display.html?id=63244>
757+
or L<http://bugs.debian.org/164615>, crashes from 5.8.8 to blead.
758+
754759
=back
755760

756761
=head1 Acknowledgements

t/io/open.t

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ $| = 1;
1010
use warnings;
1111
use Config;
1212

13-
plan tests => 156;
13+
plan tests => 157;
1414

1515
my $Perl = which_perl();
1616

@@ -485,5 +485,14 @@ pass("no crash when open autovivifies glob in freed package");
485485
unlink "$fh";
486486
}
487487

488+
# [perl #63244] Survive dup of empty filehandle
489+
{
490+
local $ENV{PERLIO} = 'stdio';
491+
my $runperl = _create_runperl(prog => 'open(F, q{<&STDOUT});',
492+
stdin => undef);
493+
$runperl =~ s/ </ 1</;
494+
ok(system($runperl)==0, 'stdio dup on empty filehandle [perl #63244]');
495+
}
496+
488497
package OverloadTest;
489498
use overload '""' => sub { ${$_[0]} };

0 commit comments

Comments
 (0)