Revision: 4806
Author: [email protected]
Date: Mon Jun  7 02:36:30 2010
Log: Revert r4782. Fix issues 728, 732.

Review URL: http://codereview.chromium.org/2701003
http://code.google.com/p/v8/source/detail?r=4806

Modified:
 /branches/bleeding_edge/src/arm/ic-arm.cc
 /branches/bleeding_edge/src/ia32/ic-ia32.cc
 /branches/bleeding_edge/src/objects-inl.h
 /branches/bleeding_edge/src/objects.cc
 /branches/bleeding_edge/src/objects.h
 /branches/bleeding_edge/src/utils.h
 /branches/bleeding_edge/src/x64/ic-x64.cc

=======================================
--- /branches/bleeding_edge/src/arm/ic-arm.cc   Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/arm/ic-arm.cc   Mon Jun  7 02:36:30 2010
@@ -849,8 +849,8 @@

   // Is the string an array index, with cached numeric value?
   __ ldr(r3, FieldMemOperand(r0, String::kHashFieldOffset));
-  __ tst(r3, Operand(String::kIsArrayIndexMask));
-  __ b(ne, &index_string);
+  __ tst(r3, Operand(String::kContainsCachedArrayIndexMask));
+  __ b(eq, &index_string);

   // Is the string a symbol?
   // r2: key map
=======================================
--- /branches/bleeding_edge/src/ia32/ic-ia32.cc Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/ia32/ic-ia32.cc Mon Jun  7 02:36:30 2010
@@ -404,8 +404,8 @@
   __ j(above_equal, &slow);
   // Is the string an array index, with cached numeric value?
   __ mov(ebx, FieldOperand(eax, String::kHashFieldOffset));
-  __ test(ebx, Immediate(String::kIsArrayIndexMask));
-  __ j(not_zero, &index_string, not_taken);
+  __ test(ebx, Immediate(String::kContainsCachedArrayIndexMask));
+  __ j(zero, &index_string, not_taken);

   // Is the string a symbol?
   // ecx: key map.
=======================================
--- /branches/bleeding_edge/src/objects-inl.h   Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/objects-inl.h   Mon Jun  7 02:36:30 2010
@@ -2987,8 +2987,7 @@
   : length_(length),
     raw_running_hash_(0),
     array_index_(0),
-    is_array_index_(0 < length_ &&
-                    length_ <= String::kMaxCachedArrayIndexLength),
+    is_array_index_(0 < length_ && length_ <= String::kMaxArrayIndexSize),
     is_first_char_(true),
     is_valid_(true) { }

@@ -3051,7 +3050,9 @@

 bool String::AsArrayIndex(uint32_t* index) {
   uint32_t field = hash_field();
- if (IsHashFieldComputed(field) && !(field & kIsArrayIndexMask)) return false;
+  if (IsHashFieldComputed(field) && (field & kIsNotArrayIndexMask)) {
+    return false;
+  }
   return SlowAsArrayIndex(index);
 }

=======================================
--- /branches/bleeding_edge/src/objects.cc      Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/objects.cc      Mon Jun  7 02:36:30 2010
@@ -4850,7 +4850,7 @@
   if (length() <= kMaxCachedArrayIndexLength) {
     Hash();  // force computation of hash code
     uint32_t field = hash_field();
-    if ((field & kIsArrayIndexMask) == 0) return false;
+    if ((field & kIsNotArrayIndexMask) != 0) return false;
     // Isolate the array index form the full hash field.
     *index = (kArrayIndexHashMask & field) >> kHashShift;
     return true;
@@ -4869,10 +4869,14 @@
// For array indexes mix the length into the hash as an array index could
     // be zero.
     ASSERT(length > 0);
+    ASSERT(length <= String::kMaxArrayIndexSize);
     ASSERT(TenToThe(String::kMaxCachedArrayIndexLength) <
            (1 << String::kArrayIndexValueBits));
-    result |= String::kIsArrayIndexMask;
+ ASSERT(String::kMaxArrayIndexSize < (1 << String::kArrayIndexValueBits));
+    result &= ~String::kIsNotArrayIndexMask;
     result |= length << String::kArrayIndexHashLengthShift;
+  } else {
+    result |= String::kIsNotArrayIndexMask;
   }
   return result;
 }
=======================================
--- /branches/bleeding_edge/src/objects.h       Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/objects.h       Mon Jun  7 02:36:30 2010
@@ -4194,11 +4194,11 @@
   // computed the 2nd bit tells whether the string can be used as an
   // array index.
   static const int kHashNotComputedMask = 1;
-  static const int kIsArrayIndexMask = 1 << 1;
-  static const int kNofLengthBitFields = 2;
+  static const int kIsNotArrayIndexMask = 1 << 1;
+  static const int kNofHashBitFields = 2;

   // Shift constant retrieving hash code from hash field.
-  static const int kHashShift = kNofLengthBitFields;
+  static const int kHashShift = kNofHashBitFields;

   // Array index strings this short can keep their index in the hash
   // field.
@@ -4207,18 +4207,35 @@
// For strings which are array indexes the hash value has the string length // mixed into the hash, mainly to avoid a hash value of zero which would be // the case for the string '0'. 24 bits are used for the array index value.
-  static const int kArrayIndexHashLengthShift = 24 + kNofLengthBitFields;
+  static const int kArrayIndexValueBits = 24;
+  static const int kArrayIndexLengthBits =
+      kBitsPerInt - kArrayIndexValueBits - kNofHashBitFields;
+
+  STATIC_CHECK((kArrayIndexLengthBits > 0));
+
+  static const int kArrayIndexHashLengthShift =
+      kArrayIndexValueBits + kNofHashBitFields;
+
static const int kArrayIndexHashMask = (1 << kArrayIndexHashLengthShift) - 1;
-  static const int kArrayIndexValueBits =
-      kArrayIndexHashLengthShift - kHashShift;
+
   static const int kArrayIndexValueMask =
       ((1 << kArrayIndexValueBits) - 1) << kHashShift;

+  // Check that kMaxCachedArrayIndexLength + 1 is a power of two so we
+ // could use a mask to test if the length of string is less than or equal to
+  // kMaxCachedArrayIndexLength.
+  STATIC_CHECK(IS_POWER_OF_TWO(kMaxCachedArrayIndexLength + 1));
+
+  static const int kContainsCachedArrayIndexMask =
+      (~kMaxCachedArrayIndexLength << kArrayIndexHashLengthShift) |
+      kIsNotArrayIndexMask;
+
   // Value of empty hash field indicating that the hash is not computed.
-  static const int kEmptyHashField = kHashNotComputedMask;
+  static const int kEmptyHashField =
+      kIsNotArrayIndexMask | kHashNotComputedMask;

   // Value of hash field containing computed hash equal to zero.
-  static const int kZeroHash = 0;
+  static const int kZeroHash = kIsNotArrayIndexMask;

   // Maximal string length.
   static const int kMaxLength = (1 << (32 - 2)) - 1;
=======================================
--- /branches/bleeding_edge/src/utils.h Fri Jun  4 04:30:55 2010
+++ /branches/bleeding_edge/src/utils.h Mon Jun  7 02:36:30 2010
@@ -37,11 +37,13 @@
// ----------------------------------------------------------------------------
 // General helper functions

+#define IS_POWER_OF_TWO(x) (((x) & ((x) - 1)) == 0)
+
 // Returns true iff x is a power of 2 (or zero). Cannot be used with the
 // maximally negative value of the type T (the -1 overflows).
 template <typename T>
 static inline bool IsPowerOf2(T x) {
-  return (x & (x - 1)) == 0;
+  return IS_POWER_OF_TWO(x);
 }


=======================================
--- /branches/bleeding_edge/src/x64/ic-x64.cc   Mon Jun  7 01:27:32 2010
+++ /branches/bleeding_edge/src/x64/ic-x64.cc   Mon Jun  7 02:36:30 2010
@@ -442,8 +442,8 @@
   __ j(above_equal, &slow);
   // Is the string an array index, with cached numeric value?
   __ movl(rbx, FieldOperand(rax, String::kHashFieldOffset));
-  __ testl(rbx, Immediate(String::kIsArrayIndexMask));
- __ j(not_zero, &index_string); // The value in rbx is used at jump target.
+  __ testl(rbx, Immediate(String::kContainsCachedArrayIndexMask));
+  __ j(zero, &index_string);  // The value in rbx is used at jump target.

   // Is the string a symbol?
   ASSERT(kSymbolTag != 0);

--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev

Reply via email to