import Devel-Size 0.68 from CPAN
Tels [Tue, 12 Jun 2007 20:22:30 +0000 (12:22 -0800)]
git-cpan-module:   Devel-Size
git-cpan-version:  0.68
git-cpan-authorid: TELS
git-cpan-file:     authors/id/T/TE/TELS/devel/Devel-Size-0.68.tar.gz

CHANGES
META.yml
SIGNATURE
Size.xs
lib/Devel/Size.pm
t/basic.t
t/pod_cov.t
t/recurse.t

diff --git a/CHANGES b/CHANGES
index fd6eb47..df20f1c 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,5 +1,11 @@
 Revision history for Perl extension Devel::Size.
 
+0.68 2007-06-12 Tels 69 tests
+  * remove a bit of duplicate code in op_size, the second instance
+    was a no-op anyway
+  * fix the failing tests by rewriting the test logic to be sane
+  * the count of array slots was off by one
+
 0.67 2007-03-15 Tels 20 tests
   * rip out Build.PL since it doesn't actually work
   * fix bug #1653: All SVPV subtype may contain an RV instead of a PV
index bd3f555..8affd5f 100644 (file)
--- a/META.yml
+++ b/META.yml
@@ -19,4 +19,4 @@ recommends:
   Devel::Size::Report: 0.11
 requires: 
   DynaLoader: 0
-version: 0.67
+version: 0.68
index f414cf1..b8ddb62 100644 (file)
--- a/SIGNATURE
+++ b/SIGNATURE
@@ -14,12 +14,12 @@ not run its Makefile.PL or Build.PL.
 -----BEGIN PGP SIGNED MESSAGE-----
 Hash: SHA1
 
-SHA1 8209b79fe86e5a4a8698b8a3f13c6f05467bfbc8 CHANGES
+SHA1 ee66ae558ef004085fcfdd02cd48dbccfb03af99 CHANGES
 SHA1 b41fb799702683e35ca968f55018175c8c6298e9 MANIFEST
 SHA1 134aae6f44102ce9b0f7fa7a3710e41a0cd23646 MANIFEST.SKIP
-SHA1 08fcfb52a30000bd80a37f0ee91d917706690884 META.yml
+SHA1 b35ae97bcd1cc317531149f733fff1a2f28cfc5d META.yml
 SHA1 6ed187e4890948dacf792b44ab18fa143a580ace Makefile.PL
-SHA1 3ddc18f9e90d5837031fcad6c6b62076512cc75a Size.xs
+SHA1 4c4f4df3225936dc661f604629650c791af0f932 Size.xs
 SHA1 ceac99579ef3914de1936417282842c07d907a6a inc/Module/Install.pm
 SHA1 6c9471c92c28e247fb84f4ab7dc277f68b33ea95 inc/Module/Install/Base.pm
 SHA1 b2cb1026330e8c4f8533c79569498ab15f189d86 inc/Module/Install/Can.pm
@@ -28,19 +28,19 @@ SHA1 642e5b27f4cbbbe440e5dc05c639f5fb79875fe3 inc/Module/Install/Makefile.pm
 SHA1 80d024f3eccf1c825b02b5e59de236b0af7d4bfc inc/Module/Install/Metadata.pm
 SHA1 fe6780ea5cfd67c79140699fbd4f0fe262255d57 inc/Module/Install/Win32.pm
 SHA1 51d43bffcfd7ffdecb8c8e9f97f3896c31b2e1b2 inc/Module/Install/WriteAll.pm
-SHA1 11650747f74e8a932e7c35a626cf36754104264e lib/Devel/Size.pm
-SHA1 3b24073cb8b1a95aa924327aaa4463c24cbf3c47 t/basic.t
+SHA1 97173fa2e404110c943223b095662f72acc13e5f lib/Devel/Size.pm
+SHA1 69c981fd251d8017b9602799d15a7066fcd27c5e t/basic.t
 SHA1 dc638392e64661dd07deeba11f67e35650a6384a t/pod.t
-SHA1 cab9b9f7a912f8a18e5301841da22dead08d00f3 t/pod_cov.t
-SHA1 5bb930d42d5b99e7ca23283ad848dcdc6b9565bc t/recurse.t
+SHA1 f4ffad1e7160c51cefcd003f88e1deb1c897b344 t/pod_cov.t
+SHA1 4cafa040d3ab66402270c8b8f7f1c7308157f19c t/recurse.t
 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1.4.2 (GNU/Linux)
 
-iQEVAwUBRfmXY3cLPEOTuEwVAQJ9xAf6A1uUjeE5EPb3/7+DRpMfh5drJTwm8sFd
-iJr7wPHejdY5UoF6lckTCa4gA4OPuiGfTdNf1Mmy2HEFzDbxMaK1m5nCiYb9fAWG
-E7p5bFZizawI7QNHRULpWXOWAL+HH4yUL/F2LqENOVmy/PCwfjpm4VlTysvj+a1L
-AlABEuHk3T2sRkUwCrx9/ADJ0o/ZiFki7Gxky0aLI1zffMKl5+k6psZ+zuIiuzre
-gB4r6obpKIggrkVbLcftmdZQVUD/2YjH+38hziL2uAxY/iDQ6HsBRD4Ef480c5xW
-Bp6Nko65UME/OiSOEE7hbJFDGf/EKv5OXB/UXEsdBJdO9Xyk6OivxQ==
-=eNsE
+iQEVAwUBRm7/0XcLPEOTuEwVAQKEmwf+P6mE4zf9m+uH2M2avNFpoziJy58g0uUa
+D5otmranT2bXok6hALU5syPAixFzsTKnsvrdMzpIA/gtSJBNCKkBjbzaEFItw5B0
+y5D/fdA6QDpjA/2SmZGPvNwyrfy0wCcW0N6hqO8fAG4Mmvh2j8sE9JDtZVMjCQX7
+FesGUB9n/+ucj37goNk1M6f7EMSBEsdVROUNyhgicUaSdWLwfOK67M9mZIfoFadn
+DjkYQHQExtrwt/IqjKXH51gCcENJHdZ7eelTw52YHniqnh76yqXcdISQoWzpkh7i
+9kUO0Jnlk4iCS24RwRktnfiOU42+Htm41m1AUALtb0wVD3rnRZXouw==
+=xbQw
 -----END PGP SIGNATURE-----
diff --git a/Size.xs b/Size.xs
index 4fd7559..7d63f80 100644 (file)
--- a/Size.xs
+++ b/Size.xs
@@ -216,9 +216,6 @@ UV op_size(OP *baseop, HV *tracking_hash) {
   if (check_new(tracking_hash, baseop->op_next)) {
     total_size += op_size(baseop->op_next, tracking_hash);
   }
-  if (check_new(tracking_hash, baseop->op_next)) {
-    total_size += op_size(baseop->op_next, tracking_hash);
-  }
 
   switch (cc_opclass(baseop)) {
   case OPc_BASEOP:
@@ -404,7 +401,7 @@ UV thing_size(SV *orig_thing, HV *tracking_hash) {
         total_size += SvIVX(thing);
        }
     break;
-    /* A string with a float part? */
+    /* A scalar/string/reference with a float part? */
   case SVt_PVNV:
     total_size += sizeof(XPVNV);
     total_size += SvROK(thing) ? thing_size( SvRV(thing), tracking_hash) : SvLEN(thing);
@@ -432,12 +429,13 @@ UV thing_size(SV *orig_thing, HV *tracking_hash) {
     total_size += sizeof(XPVAV);
     /* Is there anything in the array? */
     if (AvMAX(thing) != -1) {
-      total_size += sizeof(SV *) * AvMAX(thing);
+      /* an array with 10 slots has AvMax() set to 9 - te 2007-04-22 */
+      total_size += sizeof(SV *) * (AvMAX(thing) + 1);
+      /* printf ("total_size: %li AvMAX: %li av_len: %i\n", total_size, AvMAX(thing), av_len(thing)); */
     }
     /* Add in the bits on the other side of the beginning */
 
-    /* 
-      printf ("total_size %li, sizeof(SV *) %li, AvARRAY(thing) %li, AvALLOC(thing)%li , sizeof(ptr) %li \n", 
+      /* printf ("total_size %li, sizeof(SV *) %li, AvARRAY(thing) %li, AvALLOC(thing)%li , sizeof(ptr) %li \n", 
        total_size, sizeof(SV*), AvARRAY(thing), AvALLOC(thing), sizeof( thing )); */
 
     /* under Perl 5.8.8 64bit threading, AvARRAY(thing) was a pointer while AvALLOC was 0,
@@ -686,6 +684,8 @@ CODE:
     if (check_new(tracking_hash, thing)) {
       /* Is it valid? */
       if (thing) {
+       /* printf ("Found type %i at %p\n", SvTYPE(thing), thing); */
+
        /* Yes, it is. So let's check the type */
        switch (SvTYPE(thing)) {
        case SVt_RV:
@@ -697,7 +697,7 @@ CODE:
          if (SvROK(thing))
            {
            av_push(pending_array, SvRV(thing));
-           }
+           } 
          break;
 
        case SVt_PVAV:
index 43b4098..cfff70c 100644 (file)
@@ -16,7 +16,7 @@ require DynaLoader;
 @EXPORT_OK = ( @{ $EXPORT_TAGS{'all'} } );
 
 @EXPORT = qw( );
-$VERSION = '0.67';
+$VERSION = '0.68';
 
 bootstrap Devel::Size $VERSION;
 
index 42c3e22..0057f8e 100644 (file)
--- a/t/basic.t
+++ b/t/basic.t
@@ -23,7 +23,7 @@ can_ok ('Devel::Size', qw/
 Devel::Size->import( qw(size total_size) );
 
 die ("Uhoh, test uses outdated version of Devel::Size")
-  unless is ($Devel::Size::VERSION, '0.67', 'VERSION MATCHES');
+  unless is ($Devel::Size::VERSION, '0.68', 'VERSION MATCHES');
 
 #############################################################################
 # some basic checks:
index bc37244..db07ad2 100644 (file)
@@ -15,9 +15,9 @@ BEGIN
 
 SKIP:
   {
-  skip("Test::Pod::Coverage 1.00 required for testing POD coverage", $tests)
+  skip("Test::Pod::Coverage 1.08 required for testing POD coverage", $tests)
     unless do {
-    eval "use Test::Pod::Coverage 1.00";
+    eval "use Test::Pod::Coverage 1.08";
     $@ ? 0 : 1;
     };
   for my $m (qw/
index af2eb39..ddee1d8 100644 (file)
@@ -1,5 +1,11 @@
 #!/usr/bin/perl -w
 
+# IMPORTANT NOTE:
+#
+# When testing total_size(), always remember that it dereferences things, so
+# total_size([]) will NOT return the size of the ref + the array, it will only
+# return the size of the array alone!
+
 use Test::More;
 use strict;
    
@@ -8,7 +14,7 @@ my $tests;
 BEGIN
    {
    chdir 't' if -d 't';
-   plan tests => 5;
+   plan tests => 6 + 4 * 12;
 
    use lib '../lib';
    use lib '../blib/arch';
@@ -23,40 +29,176 @@ can_ok ('Devel::Size', qw/
 Devel::Size->import( qw(size total_size) );
 
 die ("Uhoh, test uses outdated version of Devel::Size")
-  unless is ($Devel::Size::VERSION, '0.67', 'VERSION MATCHES');
+  unless is ($Devel::Size::VERSION, '0.68', 'VERSION MATCHES');
 
 #############################################################################
-# #24846 (Does not correctly recurse into references in a PVNV-type scalar)
+# verify that pointer sizes in array slots are sensible:
+# create an array with 4 slots, 2 of them used
+my $array = [ 1,2,3,4 ]; pop @$array; pop @$array;
+
+# the total size minus the array itself minus two scalars is 4 slots
+my $ptr_size = total_size($array) - total_size( [] ) - total_size(1) * 2;
+
+is ($ptr_size % 4, 0, '4 pointers are dividable by 4');
+isnt ($ptr_size, 0, '4 pointers are not zero');
+
+# size of one slot ptr
+$ptr_size /= 4;
+
+#############################################################################
+# assert hash and hash key size
 
-my $size = 100;
 my $hash = {};
+$hash->{a} = 1;
+is (total_size($hash), total_size( { a => undef } ) + total_size(1) - total_size(undef));
 
-my $empty_hash = total_size($hash);
+#############################################################################
+# #24846 (Does not correctly recurse into references in a PVNV-type scalar)
 
-$hash->{a} = 0/1;
-$hash->{a} = [];
+# run the following tests with different sizes
+
+for my $size (2, 3, 7, 100)
+  {
+  my $hash = { a => 1 };
+
+  # hash + key minus the value
+  my $hash_size = total_size($hash) - total_size(1);
+
+  $hash->{a} = 0/1;
+  $hash->{a} = [];
+
+  my $pvnv_size = total_size(\$hash->{a}) - total_size([]);
+  # size of one ref
+  my $ref_size = total_size(\\1) - total_size(1);
+
+  # $hash->{a} is now a PVNV, e.g. a scalar NV and a ref to an array:
+#  SV = PVNV(0x81ff9a8) at 0x8170d48
+#  REFCNT = 1
+#  FLAGS = (ROK)
+#  IV = 0
+#  NV = 0
+#  RV = 0x81717bc
+#  SV = PVAV(0x8175d6c) at 0x81717bc
+#    REFCNT = 1
+#    FLAGS = ()
+#    IV = 0
+#    NV = 0
+#    ARRAY = 0x0
+#    FILL = -1
+#    MAX = -1
+#    ARYLEN = 0x0
+#    FLAGS = (REAL)
+#  PV = 0x81717bc ""
+#  CUR = 0
+#  LEN = 0
+
+  # Compare this to a plain array ref
+#SV = RV(0x81a2834) at 0x8207a2c
+#  REFCNT = 1
+#  FLAGS = (TEMP,ROK)
+#  RV = 0x8170b44
+#  SV = PVAV(0x8175d98) at 0x8170b44
+#    REFCNT = 2
+#    FLAGS = ()
+#    IV = 0
+#    NV = 0
+#    ARRAY = 0x0
+#    FILL = -1
+#    MAX = -1
+#    ARYLEN = 0x0
+
+  # Get the size of the PVNV and the contained array
+  my $element_size = total_size(\$hash->{a});
+
+  ok ($element_size < total_size($hash), "element < hash with one element");
+  ok ($element_size > total_size(\[]), "PVNV + [] > [] alone");
+
+  # Dereferencing the PVNV (the argument to total_size) leaves us with
+  # just the array, and this should be equal to a dereferenced array:
+  is (total_size($hash->{a}), total_size([]), '[] vs. []');
+
+  # the hash with one key
+  # the PVNV in the hash
+  # the RV inside the PVNV
+  # the contents of the array (array size)
+
+  my $full_hash = total_size($hash);
+  my $array_size = total_size([]);
+  is ($full_hash, $element_size + $hash_size, 'properly recurses into PVNV');
+  is ($full_hash, $array_size + $pvnv_size + $hash_size, 'properly recurses into PVNV');
+
+  $hash->{a} = [0..$size];
+
+  # the outer references stripped away, so they should be the same
+  is (total_size([0..$size]), total_size( $hash->{a} ), "hash element vs. array");
+
+  # the outer references included, one is just a normal ref, while the other
+  # is a PVNV, so they shouldn't be the same:
+  isnt (total_size(\[0..$size]), total_size( \$hash->{a} ), "[0..size] vs PVNV");
+  # and the plain ref should be smaller
+  ok (total_size(\[0..$size]) < total_size( \$hash->{a} ), "[0..size] vs. PVNV");
+
+  $full_hash = total_size($hash);
+  $element_size = total_size(\$hash->{a});
+  $array_size = total_size(\[0..$size]);
+
+  print "# full_hash = $full_hash\n";
+  print "# hash_size = $hash_size\n";
+  print "# array size: $array_size\n";
+  print "# element size: $element_size\n";
+  print "# ref_size = $ref_size\n";
+  print "# pvnv_size: $pvnv_size\n";
+
+  # the total size is:
+
+  # the hash with one key
+  # the PVNV in the hash
+  # the RV inside the PVNV
+  # the contents of the array (array size)
+
+  is ($full_hash, $element_size + $hash_size, 'properly recurses into PVNV');
+#  is ($full_hash, $array_size + $pvnv_size + $hash_size, 'properly recurses into PVNV');
+
+#############################################################################
+# repeat the former test, but mix in some undef elements
 
-my $hash_size = total_size($hash);
-my $element_size = total_size($hash->{a});
+  $array_size = total_size(\[0..$size, undef, undef]);
 
-ok ($element_size < $hash_size, "element < hash with one element");
+  $hash->{a} = [0..$size, undef, undef];
+  $element_size = total_size(\$hash->{a});
+  $full_hash = total_size($hash);
 
-my $array_size = total_size([0..$size]) - total_size( [] );
+  print "# full_hash = $full_hash\n";
+  print "# hash_size = $hash_size\n";
+  print "# array size: $array_size\n";
+  print "# element size: $element_size\n";
+  print "# ref_size = $ref_size\n";
+  print "# pvnv_size: $pvnv_size\n";
+
+  is ($full_hash, $element_size + $hash_size, 'properly recurses into PVNV');
+
+#############################################################################
+# repeat the former test, but use a pre-extended array
 
-$hash->{a} = [0..$size];
-my $full_hash = total_size($hash);
+  $array = [ 0..$size, undef, undef ]; pop @$array;
 
-#print "$full_hash\n";
-#print "$array_size\n";
-#print "$hash_size\n";
-#print "$element_size\n";
+  $array_size = total_size($array);
+  my $scalar_size = total_size(1) * (1+$size) + total_size(undef) * 1 + $ptr_size
+    + $ptr_size * ($size + 2) + total_size([]);
+  is ($scalar_size, $array_size, "computed right size if full array");
 
-# the total size is:
+  $hash->{a} = [0..$size, undef, undef]; pop @{$hash->{a}};
+  $full_hash = total_size($hash);
+  $element_size = total_size(\$hash->{a});
+  $array_size = total_size(\$array);
 
-# the contents of the array (array size)
-# the hash
-# the PVNV in the hash
-# the RV inside the PVNV
+  print "# full_hash = $full_hash\n";
+  print "# hash_size = $hash_size\n";
+  print "# array size: $array_size\n";
+  print "# element size: $element_size\n";
+  print "# ref_size = $ref_size\n";
+  print "# pvnv_size: $pvnv_size\n";
 
-is ($full_hash, $array_size + $hash_size, 'properly recurses into PVNV');
+  is ($full_hash, $element_size + $hash_size, 'properly handles undef/non-undef inside arrays');
 
+  } # end for different sizes