Commit d06f1db3 authored by yangguo's avatar yangguo Committed by Commit bot

Fix unsafe unaligned accesses in the serializer/deserializer.

R=svenpanne@chromium.org
BUG=v8:3771
LOG=N

Review URL: https://codereview.chromium.org/841943002

Cr-Commit-Position: refs/heads/master@{#25995}
parent b4bc9c1a
...@@ -614,7 +614,9 @@ void Deserializer::DecodeReservation( ...@@ -614,7 +614,9 @@ void Deserializer::DecodeReservation(
DCHECK_EQ(0, reservations_[NEW_SPACE].length()); DCHECK_EQ(0, reservations_[NEW_SPACE].length());
STATIC_ASSERT(NEW_SPACE == 0); STATIC_ASSERT(NEW_SPACE == 0);
int current_space = NEW_SPACE; int current_space = NEW_SPACE;
for (const auto& r : res) { for (int i = 0; i < res.length(); i++) {
SerializedData::Reservation r(0);
memcpy(&r, res.start() + i, sizeof(r));
reservations_[current_space].Add({r.chunk_size(), NULL, NULL}); reservations_[current_space].Add({r.chunk_size(), NULL, NULL});
if (r.is_last()) current_space++; if (r.is_last()) current_space++;
} }
...@@ -860,7 +862,8 @@ void Deserializer::ReadObject(int space_number, Object** write_back) { ...@@ -860,7 +862,8 @@ void Deserializer::ReadObject(int space_number, Object** write_back) {
// Fix up strings from serialized user code. // Fix up strings from serialized user code.
if (deserializing_user_code()) obj = ProcessNewObjectFromSerializedCode(obj); if (deserializing_user_code()) obj = ProcessNewObjectFromSerializedCode(obj);
*write_back = obj; Object* write_back_obj = obj;
UnalignedCopy(write_back, &write_back_obj);
#ifdef DEBUG #ifdef DEBUG
if (obj->IsCode()) { if (obj->IsCode()) {
DCHECK(space_number == CODE_SPACE || space_number == LO_SPACE); DCHECK(space_number == CODE_SPACE || space_number == LO_SPACE);
...@@ -1003,7 +1006,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1003,7 +1006,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
current = reinterpret_cast<Object**>(location_of_branch_data); \ current = reinterpret_cast<Object**>(location_of_branch_data); \
current_was_incremented = true; \ current_was_incremented = true; \
} else { \ } else { \
*current = new_object; \ UnalignedCopy(current, &new_object); \
} \ } \
} \ } \
if (emit_write_barrier && write_barrier_needed) { \ if (emit_write_barrier && write_barrier_needed) { \
...@@ -1104,7 +1107,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1104,7 +1107,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
int root_id = RootArrayConstantFromByteCode(data); int root_id = RootArrayConstantFromByteCode(data);
Object* object = isolate->heap()->roots_array_start()[root_id]; Object* object = isolate->heap()->roots_array_start()[root_id];
DCHECK(!isolate->heap()->InNewSpace(object)); DCHECK(!isolate->heap()->InNewSpace(object));
*current++ = object; UnalignedCopy(current++, &object);
break; break;
} }
...@@ -1116,7 +1119,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1116,7 +1119,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
reinterpret_cast<intptr_t>(current) + skip); reinterpret_cast<intptr_t>(current) + skip);
Object* object = isolate->heap()->roots_array_start()[root_id]; Object* object = isolate->heap()->roots_array_start()[root_id];
DCHECK(!isolate->heap()->InNewSpace(object)); DCHECK(!isolate->heap()->InNewSpace(object));
*current++ = object; UnalignedCopy(current++, &object);
break; break;
} }
...@@ -1124,8 +1127,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1124,8 +1127,7 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
int repeats = source_.GetInt(); int repeats = source_.GetInt();
Object* object = current[-1]; Object* object = current[-1];
DCHECK(!isolate->heap()->InNewSpace(object)); DCHECK(!isolate->heap()->InNewSpace(object));
for (int i = 0; i < repeats; i++) current[i] = object; for (int i = 0; i < repeats; i++) UnalignedCopy(current++, &object);
current += repeats;
break; break;
} }
...@@ -1139,10 +1141,10 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1139,10 +1141,10 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
case kFixedRepeat + 13: case kFixedRepeat + 13:
case kFixedRepeat + 14: { case kFixedRepeat + 14: {
int repeats = RepeatsForCode(data); int repeats = RepeatsForCode(data);
Object* object = current[-1]; Object* object;
UnalignedCopy(&object, current - 1);
DCHECK(!isolate->heap()->InNewSpace(object)); DCHECK(!isolate->heap()->InNewSpace(object));
for (int i = 0; i < repeats; i++) current[i] = object; for (int i = 0; i < repeats; i++) UnalignedCopy(current++, &object);
current += repeats;
break; break;
} }
...@@ -1254,7 +1256,8 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1254,7 +1256,8 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
new NativesExternalStringResource(isolate->bootstrapper(), new NativesExternalStringResource(isolate->bootstrapper(),
source_vector.start(), source_vector.start(),
source_vector.length()); source_vector.length());
*current++ = reinterpret_cast<Object*>(resource); Object* resource_obj = reinterpret_cast<Object*>(resource);
UnalignedCopy(current++, &resource_obj);
break; break;
} }
...@@ -1282,8 +1285,9 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space, ...@@ -1282,8 +1285,9 @@ void Deserializer::ReadData(Object** current, Object** limit, int source_space,
FOUR_CASES(kHotObject) FOUR_CASES(kHotObject)
FOUR_CASES(kHotObject + 4) { FOUR_CASES(kHotObject + 4) {
int index = data & kHotObjectIndexMask; int index = data & kHotObjectIndexMask;
*current = hot_objects_.Get(index); Object* hot_object = hot_objects_.Get(index);
if (write_barrier_needed && isolate->heap()->InNewSpace(*current)) { UnalignedCopy(current, &hot_object);
if (write_barrier_needed && isolate->heap()->InNewSpace(hot_object)) {
Address current_address = reinterpret_cast<Address>(current); Address current_address = reinterpret_cast<Address>(current);
isolate->heap()->RecordWrite( isolate->heap()->RecordWrite(
current_object_address, current_object_address,
......
...@@ -482,11 +482,13 @@ class SerializedData { ...@@ -482,11 +482,13 @@ class SerializedData {
protected: protected:
void SetHeaderValue(int offset, int value) { void SetHeaderValue(int offset, int value) {
reinterpret_cast<int*>(data_)[offset] = value; memcpy(reinterpret_cast<int*>(data_) + offset, &value, sizeof(value));
} }
int GetHeaderValue(int offset) const { int GetHeaderValue(int offset) const {
return reinterpret_cast<const int*>(data_)[offset]; int value;
memcpy(&value, reinterpret_cast<int*>(data_) + offset, sizeof(value));
return value;
} }
void AllocateData(int size); void AllocateData(int size);
...@@ -544,6 +546,10 @@ class Deserializer: public SerializerDeserializer { ...@@ -544,6 +546,10 @@ class Deserializer: public SerializerDeserializer {
bool ReserveSpace(); bool ReserveSpace();
void UnalignedCopy(Object** dest, Object** src) {
memcpy(dest, src, sizeof(*src));
}
// Allocation sites are present in the snapshot, and must be linked into // Allocation sites are present in the snapshot, and must be linked into
// a list at deserialization time. // a list at deserialization time.
void RelinkAllocationSite(AllocationSite* site); void RelinkAllocationSite(AllocationSite* site);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment