Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

%SIG not properly local-ized #8049

Closed
p5pRT opened this issue Aug 1, 2005 · 7 comments
Closed

%SIG not properly local-ized #8049

p5pRT opened this issue Aug 1, 2005 · 7 comments

Comments

@p5pRT
Copy link

p5pRT commented Aug 1, 2005

Migrated from rt.perl.org#36733 (status was 'resolved')

Searchable as RT36733$

@p5pRT
Copy link
Author

p5pRT commented Aug 1, 2005

From mb29450@suttles.sca.sfbay.sun.com

This is a bug report for perl from mb29450@​suttles.sca.sfbay.sun.com,
generated with the help of perlbug 1.35 running under perl v5.8.6.


The construct
local %SIG = %SIG;
does *not* make an exact local copy of %SIG, as it should.

The program

perl -e 'print scalar keys %SIG,"\n"; local %SIG = %SIG; print scalar keys %SIG, "\n"'
prints

49
0

instead of (something like)

49
49

as it should.

For comparison, another "magic" hash, %ENV, does not have the same problem.

perl -e 'print scalar keys %ENV,"\n"; local %ENV = %ENV; print scalar keys %ENV, "\n"'
61
61



Flags​:
  category=core
  severity=medium


Site configuration information for perl v5.8.6​:

Configured by mb29450 at Wed Dec 8 21​:44​:47 PST 2004.

Summary of my perl5 (revision 5 version 8 subversion 6) configuration​:
  Platform​:
  osname=solaris, osvers=2.9, archname=sun4-solaris
  uname='sunos suttles 5.9 generic_112233-05 sun4u sparc sunw,sun-blade-1000 '
  config_args='-ds -e -Dprefix=/usr/local'
  hint=recommended, useposix=true, d_sigaction=define
  usethreads=undef use5005threads=undef useithreads=undef usemultiplicity=undef
  useperlio=define d_sfio=undef uselargefiles=define usesocks=undef
  use64bitint=undef use64bitall=undef uselongdouble=undef
  usemymalloc=n, bincompat5005=undef
  Compiler​:
  cc='cc', ccflags ='-I/usr/local/include -D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64',
  optimize='-O',
  cppflags='-I/usr/local/include'
  ccversion='Sun C 5.5 Patch 112760-04 2003/10/03', gccversion='', gccosandvers=''
  intsize=4, longsize=4, ptrsize=4, doublesize=8, byteorder=4321
  d_longlong=define, longlongsize=8, d_longdbl=define, longdblsize=16
  ivtype='long', ivsize=4, nvtype='double', nvsize=8, Off_t='off_t', lseeksize=8
  alignbytes=8, prototype=define
  Linker and Libraries​:
  ld='cc', ldflags =' -L/usr/lib -L/usr/ccs/lib -L/u/SUNWspro/prod/lib -L/usr/local/lib '
  libpth=/usr/lib /usr/ccs/lib /u/SUNWspro/prod/lib /usr/local/lib
  libs=-lsocket -lnsl -ldl -lm -lc
  perllibs=-lsocket -lnsl -ldl -lm -lc
  libc=/lib/libc.so, so=so, useshrplib=false, libperl=libperl.a
  gnulibc_version=''
  Dynamic Linking​:
  dlsrc=dl_dlopen.xs, dlext=so, d_dlsymun=undef, ccdlflags=' '
  cccdlflags='-KPIC', lddlflags='-G -L/usr/lib -L/usr/ccs/lib -L/u/SUNWspro/prod/lib -L/usr/local/lib'

Locally applied patches​:
 


@​INC for perl v5.8.6​:
  /usr/local/lib/perl5/5.8.6/sun4-solaris
  /usr/local/lib/perl5/5.8.6
  /usr/local/lib/perl5/site_perl/5.8.6/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.6
  /usr/local/lib/perl5/site_perl/5.8.5/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.5
  /usr/local/lib/perl5/site_perl/5.8.4/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.4
  /usr/local/lib/perl5/site_perl/5.8.3/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.3
  /usr/local/lib/perl5/site_perl/5.8.1/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.1
  /usr/local/lib/perl5/site_perl/5.8.0/sun4-solaris
  /usr/local/lib/perl5/site_perl/5.8.0
  /usr/local/lib/perl5/site_perl
  .


Environment for perl v5.8.6​:
  HOME=/u/martin
  LANG (unset)
  LANGUAGE (unset)
  LD_LIBRARY_PATH (unset)
  LOGDIR (unset)
  PATH=/u/martin/bin​:/u/martin/bin/sun​:/usr/java1.5.0/bin​:/opt/Acrobat5/bin​:/usr/local/bin​:/usr/local/samba/bin​:/usr/local/apache2/bin​:/usr/sfw/bin​:/opt/sfw/bin​:/usr/dt/bin​:/usr/openwin/bin​:/usr/xpg4/bin​:/usr/proc/bin​:/usr/ccs/bin​:/usr/bin​:/sbin​:/usr/sbin​:/devtools/sparc/SUNWspro/SS10/bin
  PERL_BADLANG (unset)
  SHELL=/usr/bin/zsh

@p5pRT
Copy link
Author

p5pRT commented Sep 4, 2005

From @smpeters

[mb29450@​suttles.sca.sfbay.sun.com - Sun Jul 31 23​:23​:50 2005]​:

This is a bug report for perl from mb29450@​suttles.sca.sfbay.sun.com,
generated with the help of perlbug 1.35 running under perl v5.8.6.

-----------------------------------------------------------------
The construct
local %SIG = %SIG;
does *not* make an exact local copy of %SIG, as it should.

The program

perl -e 'print scalar keys %SIG,"\n"; local %SIG = %SIG; print scalar
keys %SIG, "\n"'
prints

49
0

instead of (something like)

49
49

as it should.

For comparison, another "magic" hash, %ENV, does not have the same
problem.

perl -e 'print scalar keys %ENV,"\n"; local %ENV = %ENV; print scalar
keys %ENV, "\n"'
61
61

I added Devel​::Peek to see more of what's going on. I'm guessing the
copy during localization is not working correctly in this case. The
following chunk of code from mg.c may hold the key to the problem.

  if ((mg->mg_flags & MGf_COPY) && vtbl->svt_copy) {
  /* XXX calling the copy method is probably not correct. DAPM */
  (void)CALL_FPTR(vtbl->svt_copy)(aTHX_ sv, mg, nsv,
  mg->mg_ptr, mg->mg_len);
  }

steve@​kirk​:~/perl-current$ perl -MDevel​::Peek -le'print scalar keys
%SIG; print Dump \%SIG; local %SIG = %SIG; print scalar keys %SIG; print
Dump \%SIG'
69
SV = RV(0x81751a8) at 0x814dc28
  REFCNT = 1
  FLAGS = (TEMP,ROK)
  RV = 0x817ea98
  SV = PVHV(0x8152130) at 0x817ea98
  REFCNT = 2
  FLAGS = (RMG,SHAREKEYS)
  IV = 69
  NV = 0
  MAGIC = 0x8185820
  MG_VIRTUAL = &PL_vtbl_sig
  MG_TYPE = PERL_MAGIC_sig(S)
  ARRAY = 0x8187a50 (0​:75, 1​:42, 2​:7, 3​:3, 4​:1)
  hash quality = 93.5%
  KEYS = 69
  FILL = 53
  MAX = 127
  RITER = -1
  EITER = 0x0
  Elt "NUM63" HASH = 0xcfaba382
  SV = PVMG(0x81635f0) at 0x817ed8c
  REFCNT = 1
  FLAGS = (GMG,SMG,RMG)
  IV = 0
  NV = 0
  PV = 0
  MAGIC = 0x81879c0
  MG_VIRTUAL = &PL_vtbl_sigelem
  MG_TYPE = PERL_MAGIC_sigelem(s)
  MG_LEN = 5
  MG_PTR = 0x81879e0 "NUM63"
  Elt "TRAP" HASH = 0xdc841002
  SV = PVMG(0x8162eb0) at 0x817ead4
  REFCNT = 1
  FLAGS = (GMG,SMG,RMG)
  IV = 0
  NV = 0
  PV = 0
  MAGIC = 0x8185930
  MG_VIRTUAL = &PL_vtbl_sigelem
  MG_TYPE = PERL_MAGIC_sigelem(s)
  MG_LEN = 4
  MG_PTR = 0x8185950 "TRAP"
  Elt "NUM42" HASH = 0x2ea7df85
  SV = PVMG(0x8163350) at 0x817ec90
  REFCNT = 1
  FLAGS = (GMG,SMG,RMG)
  IV = 0
  NV = 0
  PV = 0
  MAGIC = 0x81821b8
  MG_VIRTUAL = &PL_vtbl_sigelem
  MG_TYPE = PERL_MAGIC_sigelem(s)
  MG_LEN = 5
  MG_PTR = 0x81838f0 "NUM42"

0
SV = RV(0x81751a8) at 0x814dc28
  REFCNT = 1
  FLAGS = (TEMP,ROK)
  RV = 0x818be1c
  SV = PVHV(0x8152190) at 0x818be1c
  REFCNT = 2
  FLAGS = (RMG,SHAREKEYS)
  IV = 0
  NV = 0
  MAGIC = 0x8185820
  MG_VIRTUAL = &PL_vtbl_sig
  MG_TYPE = PERL_MAGIC_sig(S)
  ARRAY = 0x0
  KEYS = 0
  FILL = 0
  MAX = 7
  RITER = -1
  EITER = 0x0

@p5pRT
Copy link
Author

p5pRT commented Sep 4, 2005

The RT System itself - Status changed from 'new' to 'open'

@p5pRT
Copy link
Author

p5pRT commented Sep 4, 2005

From @iabyn

On Sat, Sep 03, 2005 at 09​:44​:44PM -0700, Steve Peters via RT wrote​:

I added Devel​::Peek to see more of what's going on. I'm guessing the
copy during localization is not working correctly in this case. The
following chunk of code from mg.c may hold the key to the problem.

    if \(\(mg\->mg\_flags & MGf\_COPY\) && vtbl\->svt\_copy\) \{
        /\* XXX calling the copy method is probably not correct\. DAPM \*/
        \(void\)CALL\_FPTR\(vtbl\->svt\_copy\)\(aTHX\_ sv\, mg\, nsv\,
                                mg\->mg\_ptr\, mg\->mg\_len\);
    \}

No, that's only where the magic type adds its own magic copy functions,
which %SIG doesn't. That only affects shared thread magic AFAIK, and I
plan to revisit it at some point.

--
The perl5 internals are a complete mess. It's like Jenga - to get the
perl5 tower taller and do something new you select a block somewhere in
the middle, with trepidation pull it out slowly, and then carefully
balance it somewhere new, hoping the whole edifice won't collapse as a
result.
  - Nicholas Clark, based on an original by Simon Cozens.

@p5pRT
Copy link
Author

p5pRT commented Sep 8, 2005

From rick@bort.ca

This is a bug report for perl from mb29450@​suttles.sca.sfbay.sun.com,
generated with the help of perlbug 1.35 running under perl v5.8.6.

-----------------------------------------------------------------
The construct
local %SIG = %SIG;
does *not* make an exact local copy of %SIG, as it should.

Please look at the following patch. I really don't understand what
needs_store is for but keeping it TRUE for %SIG seems to fix this.
Anyway, the tests should be good.

--
Rick Delaney
rick@​bort.ca

Inline Patch
diff -pruN perl-current/hv.c perl-current-dev/hv.c
--- perl-current/hv.c	2005-08-30 05:37:41.000000000 -0400
+++ perl-current-dev/hv.c	2005-09-08 08:31:28.458708179 -0400
@@ -861,7 +861,6 @@ S_hv_magic_check(pTHX_ HV *hv, bool *nee
 	    *needs_copy = TRUE;
 	    switch (mg->mg_type) {
 	    case PERL_MAGIC_tied:
-	    case PERL_MAGIC_sig:
 		*needs_store = FALSE;
 		return; /* We've set all there is to set. */
 	    }
diff -pruN perl-current/t/op/local.t perl-current-dev/t/op/local.t
--- perl-current/t/op/local.t	2005-09-08 03:50:38.000000000 -0400
+++ perl-current-dev/t/op/local.t	2005-09-08 08:30:03.296126706 -0400
@@ -4,7 +4,7 @@ BEGIN {
     chdir 't' if -d 't';
     require './test.pl';
 }
-plan tests => 79;
+plan tests => 85;
 
 sub foo {
     local($a, $b) = @_;
@@ -93,6 +93,11 @@ ok(!defined $a[0]);
     shift @a;
 }
 is($a[0].$a[1], "Xb");
+{
+    my $d = "@a";
+    local @a = @a;
+    is("@a", $d);
+}
 
 %h = ('a' => 1, 'b' => 2, 'c' => 3);
 {
@@ -105,6 +110,11 @@ is($a[0].$a[1], "Xb");
 }
 is($h{'a'}, 1);
 is($h{'b'}, 2);
+{
+    my $d = join("\n", map { "$_=>$h{$_}" } sort keys %h);
+    local %h = %h;
+    is(join("\n", map { "$_=>$h{$_}" } sort keys %h), $d);
+}
 is($h{'c'}, 3);
 
 # check for scope leakage
@@ -146,6 +156,11 @@ tie @a, 'TA';
 is($a[1], 'b');
 is($a[2], 'c');
 ok(!defined $a[0]);
+{
+    my $d = "@a";
+    local @a = @a;
+    is("@a", $d);
+}
 
 {
     package TH;
@@ -155,6 +170,8 @@ ok(!defined $a[0]);
     sub EXISTS { print "# EXISTS [@_]\n"; exists $_[0]->{$_[1]}; }
     sub DELETE { print "# DELETE [@_]\n"; delete $_[0]->{$_[1]}; }
     sub CLEAR { print "# CLEAR [@_]\n"; %{$_[0]} = (); }
+    sub FIRSTKEY { print "# FIRSTKEY [@_]\n"; keys %{$_[0]}; each %{$_[0]} }
+    sub NEXTKEY { print "# NEXTKEY [@_]\n"; each %{$_[0]} }
 }
 
 # see if localization works on tied hashes
@@ -177,6 +194,12 @@ is($h{'c'}, 3);
 # local() should preserve the existenceness of tied hash elements
 ok(! exists $h{'y'});
 ok(! exists $h{'z'});
+TODO: {
+    todo_skip("Localize entire tied hash");
+    my $d = join("\n", map { "$_=>$h{$_}" } sort keys %h);
+    local %h = %h;
+    is(join("\n", map { "$_=>$h{$_}" } sort keys %h), $d);
+}
 
 @a = ('a', 'b', 'c');
 {
@@ -203,6 +226,11 @@ $SIG{__WARN__} = $SIG{INT};
 is($SIG{TERM}, 'main::foo');
 is($SIG{INT}, \&foo);
 is($SIG{__WARN__}, \&foo);
+{
+    my $d = join("\n", map { "$_=>$SIG{$_}" } sort keys %SIG);
+    local %SIG = %SIG;
+    is(join("\n", map { "$_=>$SIG{$_}" } sort keys %SIG), $d);
+}
 
 # and for %ENV
 
@@ -225,6 +253,11 @@ is($ENV{_Z_}, 'c');
 # local() should preserve the existenceness of %ENV elements
 ok(! exists $ENV{_A_});
 ok(! exists $ENV{_B_});
+{
+    my $d = join("\n", map { "$_=>$ENV{$_}" } sort keys %ENV);
+    local %ENV = %ENV;
+    is(join("\n", map { "$_=>$ENV{$_}" } sort keys %ENV), $d);
+}
 
 # does implicit localization in foreach skip magic?
 

@p5pRT p5pRT closed this as completed Sep 20, 2005
@p5pRT
Copy link
Author

p5pRT commented Sep 20, 2005

@rgs - Status changed from 'open' to 'resolved'

@p5pRT
Copy link
Author

p5pRT commented Sep 20, 2005

From @rgs

Rick Delaney wrote​:

This is a bug report for perl from mb29450@​suttles.sca.sfbay.sun.com,
generated with the help of perlbug 1.35 running under perl v5.8.6.

-----------------------------------------------------------------
The construct
local %SIG = %SIG;
does *not* make an exact local copy of %SIG, as it should.

Please look at the following patch. I really don't understand what
needs_store is for but keeping it TRUE for %SIG seems to fix this.
Anyway, the tests should be good.

Thanks, applied as #25515 (although I made the hv.c chunk a bit nicer.)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant