This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
Update Compress-Raw-Bzip2 to CPAN version 2.063
[perl5.git] / hv.h
diff --git a/hv.h b/hv.h
index dddeb02..d5632be 100644 (file)
--- a/hv.h
+++ b/hv.h
@@ -8,6 +8,26 @@
  *
  */
 
+/* These control hash traversal randomization and the environment variable PERL_PERTURB_KEYS.
+ * Currently disabling this functionality will break a few tests, but should otherwise work fine.
+ * See perlrun for more details. */
+
+#if defined(PERL_PERTURB_KEYS_DISABLED)
+#   define PL_HASH_RAND_BITS_ENABLED        0
+#   define PERL_HASH_ITER_BUCKET(iter)      ((iter)->xhv_riter)
+#else
+#   define PERL_HASH_RANDOMIZE_KEYS         1
+#   if defined(PERL_PERTURB_KEYS_RANDOM)
+#       define PL_HASH_RAND_BITS_ENABLED    1
+#   elif defined(PERL_PERTURB_KEYS_DETERMINISTIC)
+#       define PL_HASH_RAND_BITS_ENABLED    2
+#   else
+#       define USE_PERL_PERTURB_KEYS        1
+#       define PL_HASH_RAND_BITS_ENABLED    PL_hash_rand_bits_enabled
+#   endif
+#   define PERL_HASH_ITER_BUCKET(iter)      (((iter)->xhv_riter) ^ ((iter)->xhv_rand))
+#endif
+
 /* entry in hash value chain */
 struct he {
     /* Keep hent_next first in this structure, because sv_free_arenas take
@@ -61,6 +81,8 @@ struct mro_meta {
     U32     pkg_gen;         /* Bumps when local methods/@ISA change */
     const struct mro_alg *mro_which; /* which mro alg is in use? */
     HV      *isa;            /* Everything this class @ISA */
+    HV      *super;          /* SUPER method cache */
+    U32     destroy_gen;     /* Generation number of DESTROY cache */
 };
 
 #define MRO_GET_PRIVATE_DATA(smeta, which)                \
@@ -91,7 +113,12 @@ struct xpvhv_aux {
  */
     I32                xhv_name_count;
     struct mro_meta *xhv_mro_meta;
-    HV *       xhv_super;      /* SUPER method cache */
+#ifdef PERL_HASH_RANDOMIZE_KEYS
+    U32         xhv_rand;       /* random value for hash traversal */
+    U32         xhv_last_rand;  /* last random value for hash traversal,
+                                   used to detect each() after insert for warnings */
+#endif
+    U32         xhv_fill_lazy;
 };
 
 /* hash structure: */
@@ -205,6 +232,8 @@ C<SV*>.
 =cut
 */
 
+#define PERL_HASH_DEFAULT_HvMAX 7
+
 /* these hash entry flags ride on hent_klen (for use only in magic/tied HVs) */
 #define HEf_SVKEY      -2      /* hent_key is an SV* */
 
@@ -212,7 +241,7 @@ C<SV*>.
 #  define Nullhv Null(HV*)
 #endif
 #define HvARRAY(hv)    ((hv)->sv_u.svu_hash)
-#define HvFILL(hv)     Perl_hv_fill(aTHX_ (const HV *)(hv))
+#define HvFILL(hv)     Perl_hv_fill(aTHX_ MUTABLE_HV(hv))
 #define HvMAX(hv)      ((XPVHV*)  SvANY(hv))->xhv_max
 /* This quite intentionally does no flag checking first. That's your
    responsibility.  */
@@ -223,6 +252,9 @@ C<SV*>.
 #define HvEITER_set(hv,e)      Perl_hv_eiter_set(aTHX_ MUTABLE_HV(hv), e)
 #define HvRITER_get(hv)        (SvOOK(hv) ? HvAUX(hv)->xhv_riter : -1)
 #define HvEITER_get(hv)        (SvOOK(hv) ? HvAUX(hv)->xhv_eiter : NULL)
+#define HvRAND_get(hv) (SvOOK(hv) ? HvAUX(hv)->xhv_rand : 0)
+#define HvLASTRAND_get(hv)     (SvOOK(hv) ? HvAUX(hv)->xhv_last_rand : 0)
+
 #define HvNAME(hv)     HvNAME_get(hv)
 #define HvNAMELEN(hv)   HvNAMELEN_get(hv)
 #define HvENAME(hv)    HvENAME_get(hv)
@@ -335,7 +367,9 @@ C<SV*>.
                                 ((HeKLEN(he) == HEf_SVKEY) ?           \
                                  HeKEY_sv(he) :                        \
                                  newSVpvn_flags(HeKEY(he),             \
-                                                HeKLEN(he), SVs_TEMP)) : \
+                                                 HeKLEN(he),            \
+                                                 SVs_TEMP |             \
+                                      ( HeKUTF8(he) ? SVf_UTF8 : 0 ))) : \
                                 &PL_sv_undef)
 #define HeSVKEY_set(he,sv)     ((HeKLEN(he) = HEf_SVKEY), (HeKEY_sv(he) = sv))
 
@@ -436,6 +470,12 @@ C<SV*>.
     (MUTABLE_SV(hv_common_key_len((hv), (key), (klen),                 \
                                  (flags) | HV_DELETE, NULL, 0)))
 
+#ifdef PERL_CORE
+# define hv_deletehek(hv, hek, flags) \
+    hv_common(hv, NULL, HEK_KEY(hek), HEK_LEN(hek), HEK_UTF8(hek), \
+             (flags)|HV_DELETE, NULL, HEK_HASH(hek))
+#endif
+
 /* This refcounted he structure is used for storing the hints used for lexical
    pragmas. Without threads, it's basically struct he + refcount.
    With threads, life gets more complex as the structure needs to be shared