1 // Copyright 2012 the V8 project authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef V8_SNAPSHOT_SOURCE_SINK_H_ 6 #define V8_SNAPSHOT_SOURCE_SINK_H_ 7 8 #include "src/base/logging.h" 9 #include "src/utils.h" 10 11 namespace v8 { 12 namespace internal { 13 14 15 /** 16 * Source to read snapshot and builtins files from. 17 * 18 * Note: Memory ownership remains with callee. 19 */ 20 class SnapshotByteSource FINAL { 21 public: 22 SnapshotByteSource(const byte* array, int length); 23 ~SnapshotByteSource(); 24 HasMore()25 bool HasMore() { return position_ < length_; } 26 Get()27 int Get() { 28 DCHECK(position_ < length_); 29 return data_[position_++]; 30 } 31 32 int32_t GetUnalignedInt(); 33 Advance(int by)34 void Advance(int by) { position_ += by; } 35 36 void CopyRaw(byte* to, int number_of_bytes); 37 GetInt()38 inline int GetInt() { 39 // This way of variable-length encoding integers does not suffer from branch 40 // mispredictions. 41 uint32_t answer = GetUnalignedInt(); 42 int bytes = answer & 3; 43 Advance(bytes); 44 uint32_t mask = 0xffffffffu; 45 mask >>= 32 - (bytes << 3); 46 answer &= mask; 47 answer >>= 2; 48 return answer; 49 } 50 51 bool GetBlob(const byte** data, int* number_of_bytes); 52 53 bool AtEOF(); 54 position()55 int position() { return position_; } 56 57 private: 58 const byte* data_; 59 int length_; 60 int position_; 61 62 DISALLOW_COPY_AND_ASSIGN(SnapshotByteSource); 63 }; 64 65 66 /** 67 * Sink to write snapshot files to. 68 * 69 * Subclasses must implement actual storage or i/o. 70 */ 71 class SnapshotByteSink { 72 public: ~SnapshotByteSink()73 virtual ~SnapshotByteSink() { } 74 virtual void Put(byte b, const char* description) = 0; PutSection(int b,const char * description)75 virtual void PutSection(int b, const char* description) { 76 DCHECK_LE(b, kMaxUInt8); 77 Put(static_cast<byte>(b), description); 78 } 79 void PutInt(uintptr_t integer, const char* description); 80 void PutRaw(byte* data, int number_of_bytes, const char* description); 81 void PutBlob(byte* data, int number_of_bytes, const char* description); 82 virtual int Position() = 0; 83 }; 84 85 86 class DummySnapshotSink : public SnapshotByteSink { 87 public: DummySnapshotSink()88 DummySnapshotSink() : length_(0) {} ~DummySnapshotSink()89 virtual ~DummySnapshotSink() {} Put(byte b,const char * description)90 virtual void Put(byte b, const char* description) { length_++; } Position()91 virtual int Position() { return length_; } 92 93 private: 94 int length_; 95 }; 96 97 98 // Wrap a SnapshotByteSink into a DebugSnapshotSink to get debugging output. 99 class DebugSnapshotSink : public SnapshotByteSink { 100 public: DebugSnapshotSink(SnapshotByteSink * chained)101 explicit DebugSnapshotSink(SnapshotByteSink* chained) : sink_(chained) {} 102 virtual void Put(byte b, const char* description) OVERRIDE; Position()103 virtual int Position() OVERRIDE { return sink_->Position(); } 104 105 private: 106 SnapshotByteSink* sink_; 107 }; 108 109 110 class ListSnapshotSink : public i::SnapshotByteSink { 111 public: ListSnapshotSink(i::List<byte> * data)112 explicit ListSnapshotSink(i::List<byte>* data) : data_(data) {} Put(byte b,const char * description)113 virtual void Put(byte b, const char* description) OVERRIDE { 114 data_->Add(b); 115 } Position()116 virtual int Position() OVERRIDE { return data_->length(); } 117 118 private: 119 i::List<byte>* data_; 120 }; 121 122 } // namespace v8::internal 123 } // namespace v8 124 125 #endif // V8_SNAPSHOT_SOURCE_SINK_H_ 126