Revision: 3184
Author: [email protected]
Date: Fri Oct 30 03:23:12 2009
Log: Introduce a switch for the new snapshot code and switch
it on by default.  Includes bug fixes for new snapshots.
Review URL: http://codereview.chromium.org/342054
http://code.google.com/p/v8/source/detail?r=3184

Modified:
  /branches/bleeding_edge/src/api.cc
  /branches/bleeding_edge/src/arm/assembler-arm.h
  /branches/bleeding_edge/src/flag-definitions.h
  /branches/bleeding_edge/src/global-handles.cc
  /branches/bleeding_edge/src/ia32/assembler-ia32.h
  /branches/bleeding_edge/src/mksnapshot.cc
  /branches/bleeding_edge/src/serialize.cc
  /branches/bleeding_edge/src/serialize.h
  /branches/bleeding_edge/src/snapshot-common.cc
  /branches/bleeding_edge/src/x64/assembler-x64.h
  /branches/bleeding_edge/test/cctest/test-serialize.cc

=======================================
--- /branches/bleeding_edge/src/api.cc  Tue Oct 27 01:13:59 2009
+++ /branches/bleeding_edge/src/api.cc  Fri Oct 30 03:23:12 2009
@@ -2621,11 +2621,12 @@
    if (i::V8::IsRunning()) return true;
    ENTER_V8;
    HandleScope scope;
-  if (i::Snapshot::Initialize()) {
-    return true;
+  if (i::FLAG_new_snapshot) {
+    if (i::Snapshot::Initialize2()) return true;
    } else {
-    return i::V8::Initialize(NULL);
-  }
+    if (i::Snapshot::Initialize()) return true;
+  }
+  return i::V8::Initialize(NULL);
  }


=======================================
--- /branches/bleeding_edge/src/arm/assembler-arm.h     Wed Oct 28 05:37:54 2009
+++ /branches/bleeding_edge/src/arm/assembler-arm.h     Fri Oct 30 03:23:12 2009
@@ -437,13 +437,25 @@
    INLINE(static Address target_address_at(Address pc));
    INLINE(static void set_target_address_at(Address pc, Address target));

-  // Modify the code target address in a constant pool entry.
-  inline static void set_target_at(Address constant_pool_entry, Address  
target);
+  // This sets the branch destination (which is in the constant pool on  
ARM).
+  // This is for calls and branches within generated code.
+  inline static void set_target_at(Address constant_pool_entry,
+                                   Address target) {
+    set_target_address_at(constant_pool_entry, target);
+  }
+
+  // This sets the branch destination (which is in the constant pool on  
ARM).
+  // This is for calls and branches to runtime code.
+  inline static void set_external_target_at(Address constant_pool_entry,
+                                            Address target) {
+    set_target_address_at(constant_pool_entry, target);
+  }

    // Here we are patching the address in the constant pool, not the actual  
call
    // instruction.  The address in the constant pool is the same size as a
    // pointer.
    static const int kCallTargetSize = kPointerSize;
+  static const int kExternalTargetSize = kPointerSize;

    // Size of an instruction.
    static const int kInstrSize = sizeof(Instr);
=======================================
--- /branches/bleeding_edge/src/flag-definitions.h      Tue Oct 27 07:56:50 2009
+++ /branches/bleeding_edge/src/flag-definitions.h      Fri Oct 30 03:23:12 2009
@@ -196,6 +196,7 @@

  // mksnapshot.cc
  DEFINE_bool(h, false, "print this message")
+DEFINE_bool(new_snapshot, true, "use new snapshot implementation")

  // parser.cc
  DEFINE_bool(allow_natives_syntax, false, "allow natives syntax")
=======================================
--- /branches/bleeding_edge/src/global-handles.cc       Mon Oct 26 05:54:41 2009
+++ /branches/bleeding_edge/src/global-handles.cc       Fri Oct 30 03:23:12 2009
@@ -398,6 +398,7 @@
      }
    }
  }
+

  void GlobalHandles::TearDown() {
    // Reset all the lists.
=======================================
--- /branches/bleeding_edge/src/ia32/assembler-ia32.h   Wed Oct 28 05:37:54  
2009
+++ /branches/bleeding_edge/src/ia32/assembler-ia32.h   Fri Oct 30 03:23:12  
2009
@@ -440,12 +440,21 @@
    inline static void set_target_address_at(Address pc, Address target);

    // This sets the branch destination (which is in the instruction on x86).
+  // This is for calls and branches within generated code.
    inline static void set_target_at(Address instruction_payload,
                                     Address target) {
      set_target_address_at(instruction_payload, target);
    }
+
+  // This sets the branch destination (which is in the instruction on x86).
+  // This is for calls and branches to runtime code.
+  inline static void set_external_target_at(Address instruction_payload,
+                                            Address target) {
+    set_target_address_at(instruction_payload, target);
+  }

    static const int kCallTargetSize = kPointerSize;
+  static const int kExternalTargetSize = kPointerSize;

    // Distance between the address of the code target in the call  
instruction
    // and the return address
=======================================
--- /branches/bleeding_edge/src/mksnapshot.cc   Mon Aug 24 19:54:39 2009
+++ /branches/bleeding_edge/src/mksnapshot.cc   Fri Oct 30 03:23:12 2009
@@ -109,6 +109,48 @@
  }


+class CppByteSink : public i::SnapshotByteSink {
+ public:
+  explicit CppByteSink(const char* snapshot_file) : bytes_written_(0) {
+    fp_ = i::OS::FOpen(snapshot_file, "wb");
+    if (fp_ == NULL) {
+      i::PrintF("Unable to write to snapshot file \"%s\"\n",  
snapshot_file);
+      exit(1);
+    }
+    fprintf(fp_, "// Autogenerated snapshot file. Do not edit.\n\n");
+    fprintf(fp_, "#include \"v8.h\"\n");
+    fprintf(fp_, "#include \"platform.h\"\n\n");
+    fprintf(fp_, "#include \"snapshot.h\"\n\n");
+    fprintf(fp_, "namespace v8 {\nnamespace internal {\n\n");
+    fprintf(fp_, "const byte Snapshot::data_[] = {");
+  }
+
+  virtual ~CppByteSink() {
+    if (fp_ != NULL) {
+      fprintf(fp_, "};\n\n");
+      fprintf(fp_, "int Snapshot::size_ = %d;\n\n", bytes_written_);
+      fprintf(fp_, "} }  // namespace v8::internal\n");
+      fclose(fp_);
+    }
+  }
+
+  virtual void Put(int byte, const char* description) {
+    if (bytes_written_ != 0) {
+      fprintf(fp_, ",");
+    }
+    fprintf(fp_, "%d", byte);
+    bytes_written_++;
+    if ((bytes_written_ & 0x3f) == 0) {
+      fprintf(fp_, "\n");
+    }
+  }
+
+ private:
+  FILE* fp_;
+  int bytes_written_;
+};
+
+
  // Write C++ code that defines Snapshot::snapshot_ to contain the snapshot
  // to the file given by filename. Only the first size chars are written.
  static int WriteInternalSnapshotToFile(const char* filename,
@@ -116,7 +158,7 @@
                                         int size) {
    FILE* f = i::OS::FOpen(filename, "wb");
    if (f == NULL) {
-    i::OS::PrintError("Cannot open file %s for reading.\n", filename);
+    i::OS::PrintError("Cannot open file %s for writing.\n", filename);
      return 0;
    }
    fprintf(f, "// Autogenerated snapshot file. Do not edit.\n\n");
@@ -138,6 +180,23 @@
    fclose(f);
    return written;
  }
+
+
+int main2(int argc, char** argv) {
+  i::Serializer::Enable();
+  Persistent<Context> context = v8::Context::New();
+  // Make sure all builtin scripts are cached.
+  { HandleScope scope;
+    for (int i = 0; i < i::Natives::GetBuiltinsCount(); i++) {
+      i::Bootstrapper::NativesSourceLookup(i);
+    }
+  }
+  context.Dispose();
+  CppByteSink sink(argv[1]);
+  i::Serializer2 ser(&sink);
+  ser.Serialize();
+  return 0;
+}


  int main(int argc, char** argv) {
@@ -153,6 +212,10 @@
      i::FlagList::PrintHelp();
      return !i::FLAG_help;
    }
+
+  if (i::FLAG_new_snapshot) {
+    return main2(argc, argv);
+  }

    v8::V8::SetCounterFunction(counter_callback);
    v8::HandleScope scope;
=======================================
--- /branches/bleeding_edge/src/serialize.cc    Wed Oct 28 05:37:54 2009
+++ /branches/bleeding_edge/src/serialize.cc    Fri Oct 30 03:23:12 2009
@@ -1927,10 +1927,8 @@
        case RAW_DATA_SERIALIZATION: {
          int size = source_->GetInt();
          byte* raw_data_out = reinterpret_cast<byte*>(current);
-        for (int j = 0; j < size; j++) {
-          *raw_data_out++ = source_->Get();
-        }
-        current = reinterpret_cast<Object**>(raw_data_out);
+        source_->CopyRaw(raw_data_out, size);
+        current = reinterpret_cast<Object**>(raw_data_out + size);
          break;
        }
        case OBJECT_SERIALIZATION: {
@@ -1984,6 +1982,15 @@
          *current++ = reinterpret_cast<Object*>(address);
          break;
        }
+      case EXTERNAL_BRANCH_TARGET_SERIALIZATION: {
+        int reference_id = source_->GetInt();
+        Address address =  
external_reference_decoder_->Decode(reference_id);
+        Address location_of_branch_data =  
reinterpret_cast<Address>(current);
+        Assembler::set_external_target_at(location_of_branch_data,  
address);
+        location_of_branch_data += Assembler::kExternalTargetSize;
+        current = reinterpret_cast<Object**>(location_of_branch_data);
+        break;
+      }
        default:
          UNREACHABLE();
      }
@@ -2157,6 +2164,18 @@
    }
    bytes_processed_so_far_ += (end - start) * kPointerSize;
  }
+
+
+void Serializer2::ObjectSerializer::VisitRuntimeEntry(RelocInfo* rinfo) {
+  Address target_start = rinfo->target_address_address();
+  OutputRawData(target_start);
+  Address target = rinfo->target_address();
+  uint32_t encoding = serializer_->EncodeExternalReference(target);
+  CHECK(target == NULL ? encoding == 0 : encoding != 0);
+  sink_->Put(EXTERNAL_BRANCH_TARGET_SERIALIZATION, "External reference");
+  sink_->PutInt(encoding, "reference id");
+  bytes_processed_so_far_ += Assembler::kExternalTargetSize;
+}


  void Serializer2::ObjectSerializer::VisitCodeTarget(RelocInfo* rinfo) {
@@ -2183,8 +2202,8 @@
        unsigned int data = object_start[bytes_processed_so_far_ + i];
        sink_->Put(data, "byte");
      }
-  }
-  bytes_processed_so_far_ += skipped;
+    bytes_processed_so_far_ += skipped;
+  }
  }


=======================================
--- /branches/bleeding_edge/src/serialize.h     Tue Oct 27 04:54:01 2009
+++ /branches/bleeding_edge/src/serialize.h     Fri Oct 30 03:23:12 2009
@@ -362,6 +362,11 @@
      ASSERT(position_ < length_);
      return data_[position_++];
    }
+
+  void CopyRaw(byte* to, int number_of_bytes) {
+    memcpy(to, data_ + position_, number_of_bytes);
+    position_ += number_of_bytes;
+  }

    int GetInt() {
      // A little unwind to catch the really small ints.
@@ -405,6 +410,7 @@
      BACKREF_SERIALIZATION,
      CODE_BACKREF_SERIALIZATION,
      EXTERNAL_REFERENCE_SERIALIZATION,
+    EXTERNAL_BRANCH_TARGET_SERIALIZATION,
      SYNCHRONIZE
    };
    // Our Smi encoding is much more efficient for small positive integers  
than it
@@ -521,6 +527,7 @@
      void VisitPointers(Object** start, Object** end);
      void VisitExternalReferences(Address* start, Address* end);
      void VisitCodeTarget(RelocInfo* target);
+    void VisitRuntimeEntry(RelocInfo* reloc);

     private:
      void OutputRawData(Address up_to);
=======================================
--- /branches/bleeding_edge/src/snapshot-common.cc      Tue Oct 27 06:19:14 2009
+++ /branches/bleeding_edge/src/snapshot-common.cc      Fri Oct 30 03:23:12 2009
@@ -73,10 +73,12 @@
      if (!str) return false;
      Deserialize2(str, len);
      DeleteArray(str);
+    return true;
    } else if (size_ > 0) {
      Deserialize2(data_, size_);
-  }
-  return true;
+    return true;
+  }
+  return false;
  }


=======================================
--- /branches/bleeding_edge/src/x64/assembler-x64.h     Wed Oct 28 05:37:54 2009
+++ /branches/bleeding_edge/src/x64/assembler-x64.h     Fri Oct 30 03:23:12 2009
@@ -458,14 +458,25 @@
    // the relative displacements stored in the code.
    static inline Address target_address_at(Address pc);
    static inline void set_target_address_at(Address pc, Address target);
+
    // This sets the branch destination (which is in the instruction on x64).
+  // This is for calls and branches within generated code.
    inline static void set_target_at(Address instruction_payload,
                                     Address target) {
      set_target_address_at(instruction_payload, target);
    }
+
+  // This sets the branch destination (which is a load instruction on x64).
+  // This is for calls and branches to runtime code.
+  inline static void set_external_target_at(Address instruction_payload,
+                                            Address target) {
+    *reinterpret_cast<Address*>(instruction_payload) = target;
+  }
+
    inline Handle<Object> code_target_object_handle_at(Address pc);
    // Number of bytes taken up by the branch target in the code.
-  static const int kCallTargetSize = 4;  // Use 32-bit displacement.
+  static const int kCallTargetSize = 4;      // Use 32-bit displacement.
+  static const int kExternalTargetSize = 8;  // Use 64-bit absolute.
    // Distance between the address of the code target in the call  
instruction
    // and the return address pushed on the stack.
    static const int kCallTargetAddressOffset = 4;  // Use 32-bit  
displacement.
=======================================
--- /branches/bleeding_edge/test/cctest/test-serialize.cc       Tue Oct 27  
04:54:01 2009
+++ /branches/bleeding_edge/test/cctest/test-serialize.cc       Fri Oct 30  
03:23:12 2009
@@ -195,15 +195,6 @@
    env.Dispose();
    Snapshot::WriteToFile2(FLAG_testing_serialization_file);
  }
-
-
-// Test that the whole heap can be serialized when running from the
-// internal snapshot.
-// (Smoke test.)
-TEST(SerializeInternal) {
-  Snapshot::Initialize(NULL);
-  Serialize();
-}


  // Test that the whole heap can be serialized when running from a

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

Reply via email to