| OLD | NEW |
| 1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 the V8 project authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <memory> | 5 #include <memory> |
| 6 | 6 |
| 7 #include "src/assembler-inl.h" | 7 #include "src/assembler-inl.h" |
| 8 #include "src/base/adapters.h" | 8 #include "src/base/adapters.h" |
| 9 #include "src/base/atomic-utils.h" | 9 #include "src/base/atomic-utils.h" |
| 10 #include "src/code-stubs.h" | 10 #include "src/code-stubs.h" |
| (...skipping 2331 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2342 if (compiled_max_pages != 0) return compiled_max_pages; | 2342 if (compiled_max_pages != 0) return compiled_max_pages; |
| 2343 return FLAG_wasm_max_mem_pages; | 2343 return FLAG_wasm_max_mem_pages; |
| 2344 } | 2344 } |
| 2345 | 2345 |
| 2346 Handle<JSArrayBuffer> GrowMemoryBuffer(Isolate* isolate, | 2346 Handle<JSArrayBuffer> GrowMemoryBuffer(Isolate* isolate, |
| 2347 MaybeHandle<JSArrayBuffer> buffer, | 2347 MaybeHandle<JSArrayBuffer> buffer, |
| 2348 uint32_t pages, uint32_t max_pages) { | 2348 uint32_t pages, uint32_t max_pages) { |
| 2349 Handle<JSArrayBuffer> old_buffer; | 2349 Handle<JSArrayBuffer> old_buffer; |
| 2350 Address old_mem_start = nullptr; | 2350 Address old_mem_start = nullptr; |
| 2351 uint32_t old_size = 0; | 2351 uint32_t old_size = 0; |
| 2352 if (buffer.ToHandle(&old_buffer) && old_buffer->backing_store() != nullptr) { | 2352 if (buffer.ToHandle(&old_buffer) && old_buffer->backing_store() != nullptr && |
| 2353 old_buffer->byte_length()->IsNumber()) { |
| 2353 old_mem_start = static_cast<Address>(old_buffer->backing_store()); | 2354 old_mem_start = static_cast<Address>(old_buffer->backing_store()); |
| 2354 DCHECK_NOT_NULL(old_mem_start); | 2355 DCHECK_NOT_NULL(old_mem_start); |
| 2355 old_size = old_buffer->byte_length()->Number(); | 2356 old_size = old_buffer->byte_length()->Number(); |
| 2356 } | 2357 } |
| 2357 DCHECK(old_size + pages * WasmModule::kPageSize <= | 2358 DCHECK(old_size + pages * WasmModule::kPageSize <= |
| 2358 std::numeric_limits<uint32_t>::max()); | 2359 std::numeric_limits<uint32_t>::max()); |
| 2359 uint32_t new_size = old_size + pages * WasmModule::kPageSize; | 2360 uint32_t new_size = old_size + pages * WasmModule::kPageSize; |
| 2360 if (new_size <= old_size || max_pages * WasmModule::kPageSize < new_size || | 2361 if (new_size <= old_size || max_pages * WasmModule::kPageSize < new_size || |
| 2361 FLAG_wasm_max_mem_pages * WasmModule::kPageSize < new_size) { | 2362 FLAG_wasm_max_mem_pages * WasmModule::kPageSize < new_size) { |
| 2362 return Handle<JSArrayBuffer>::null(); | 2363 return Handle<JSArrayBuffer>::null(); |
| (...skipping 22 matching lines...) Expand all Loading... |
| 2385 uint32_t new_size = mem_buffer->byte_length()->Number(); | 2386 uint32_t new_size = mem_buffer->byte_length()->Number(); |
| 2386 Address new_mem_start = static_cast<Address>(mem_buffer->backing_store()); | 2387 Address new_mem_start = static_cast<Address>(mem_buffer->backing_store()); |
| 2387 DCHECK_NOT_NULL(new_mem_start); | 2388 DCHECK_NOT_NULL(new_mem_start); |
| 2388 Zone specialization_zone(isolate->allocator(), ZONE_NAME); | 2389 Zone specialization_zone(isolate->allocator(), ZONE_NAME); |
| 2389 CodeSpecialization code_specialization(isolate, &specialization_zone); | 2390 CodeSpecialization code_specialization(isolate, &specialization_zone); |
| 2390 code_specialization.RelocateMemoryReferences(old_mem_start, old_size, | 2391 code_specialization.RelocateMemoryReferences(old_mem_start, old_size, |
| 2391 new_mem_start, new_size); | 2392 new_mem_start, new_size); |
| 2392 code_specialization.ApplyToWholeInstance(*instance); | 2393 code_specialization.ApplyToWholeInstance(*instance); |
| 2393 } | 2394 } |
| 2394 | 2395 |
| 2395 void DetachArrayBuffer(Isolate* isolate, Handle<JSArrayBuffer> buffer) { | 2396 void wasm::DetachWebAssemblyMemoryBuffer(Isolate* isolate, |
| 2396 const bool has_guard_regions = | 2397 Handle<JSArrayBuffer> buffer) { |
| 2397 (!buffer.is_null() && buffer->has_guard_region()); | 2398 int64_t byte_length = |
| 2399 buffer->byte_length()->IsNumber() |
| 2400 ? static_cast<uint32_t>(buffer->byte_length()->Number()) |
| 2401 : 0; |
| 2402 if (buffer.is_null() || byte_length == 0) return; |
| 2403 const bool has_guard_regions = buffer->has_guard_region(); |
| 2398 const bool is_external = buffer->is_external(); | 2404 const bool is_external = buffer->is_external(); |
| 2399 void* backing_store = buffer->backing_store(); | 2405 void* backing_store = buffer->backing_store(); |
| 2400 if (backing_store != nullptr) { | 2406 DCHECK(!buffer->is_neuterable()); |
| 2401 DCHECK(!buffer->is_neuterable()); | 2407 if (!has_guard_regions && !is_external) { |
| 2402 int64_t byte_length = NumberToSize(buffer->byte_length()); | 2408 buffer->set_is_external(true); |
| 2403 buffer->set_is_neuterable(true); | 2409 isolate->heap()->UnregisterArrayBuffer(*buffer); |
| 2404 if (!has_guard_regions && !is_external) { | 2410 } |
| 2405 buffer->set_is_external(true); | 2411 buffer->set_is_neuterable(true); |
| 2406 isolate->heap()->UnregisterArrayBuffer(*buffer); | 2412 buffer->Neuter(); |
| 2407 } | 2413 if (has_guard_regions) { |
| 2408 buffer->Neuter(); | 2414 base::OS::Free(backing_store, RoundUp(i::wasm::kWasmMaxHeapOffset, |
| 2409 if (has_guard_regions) { | 2415 base::OS::CommitPageSize())); |
| 2410 base::OS::Free(backing_store, RoundUp(i::wasm::kWasmMaxHeapOffset, | 2416 reinterpret_cast<v8::Isolate*>(isolate) |
| 2411 base::OS::CommitPageSize())); | 2417 ->AdjustAmountOfExternalAllocatedMemory(-byte_length); |
| 2412 reinterpret_cast<v8::Isolate*>(isolate) | 2418 } else if (!has_guard_regions && !is_external) { |
| 2413 ->AdjustAmountOfExternalAllocatedMemory(-byte_length); | 2419 isolate->array_buffer_allocator()->Free(backing_store, byte_length); |
| 2414 } else if (!has_guard_regions && !is_external) { | |
| 2415 isolate->array_buffer_allocator()->Free(backing_store, byte_length); | |
| 2416 } | |
| 2417 } | 2420 } |
| 2418 } | 2421 } |
| 2419 | 2422 |
| 2420 int32_t wasm::GrowWebAssemblyMemory(Isolate* isolate, | 2423 int32_t wasm::GrowWebAssemblyMemory(Isolate* isolate, |
| 2421 Handle<WasmMemoryObject> receiver, | 2424 Handle<WasmMemoryObject> receiver, |
| 2422 uint32_t pages) { | 2425 uint32_t pages) { |
| 2423 DCHECK(WasmJs::IsWasmMemoryObject(isolate, receiver)); | 2426 DCHECK(WasmJs::IsWasmMemoryObject(isolate, receiver)); |
| 2424 Handle<WasmMemoryObject> memory_object = | 2427 Handle<WasmMemoryObject> memory_object = |
| 2425 handle(WasmMemoryObject::cast(*receiver)); | 2428 handle(WasmMemoryObject::cast(*receiver)); |
| 2426 MaybeHandle<JSArrayBuffer> memory_buffer = handle(memory_object->buffer()); | 2429 MaybeHandle<JSArrayBuffer> memory_buffer = handle(memory_object->buffer()); |
| 2427 Handle<JSArrayBuffer> old_buffer; | 2430 Handle<JSArrayBuffer> old_buffer; |
| 2428 uint32_t old_size = 0; | 2431 uint32_t old_size = 0; |
| 2429 Address old_mem_start = nullptr; | 2432 Address old_mem_start = nullptr; |
| 2433 // Force byte_length to 0, if byte_length fails IsNumber() check. |
| 2430 if (memory_buffer.ToHandle(&old_buffer) && | 2434 if (memory_buffer.ToHandle(&old_buffer) && |
| 2431 old_buffer->backing_store() != nullptr) { | 2435 old_buffer->backing_store() != nullptr && |
| 2436 old_buffer->byte_length()->IsNumber()) { |
| 2432 old_size = old_buffer->byte_length()->Number(); | 2437 old_size = old_buffer->byte_length()->Number(); |
| 2433 old_mem_start = static_cast<Address>(old_buffer->backing_store()); | 2438 old_mem_start = static_cast<Address>(old_buffer->backing_store()); |
| 2434 } | 2439 } |
| 2435 Handle<JSArrayBuffer> new_buffer; | 2440 Handle<JSArrayBuffer> new_buffer; |
| 2436 // Return current size if grow by 0 | 2441 // Return current size if grow by 0 |
| 2437 if (pages == 0) { | 2442 if (pages == 0) { |
| 2438 if (!old_buffer.is_null() && old_buffer->backing_store() != nullptr) { | 2443 if (!old_buffer.is_null() && old_buffer->backing_store() != nullptr) { |
| 2439 new_buffer = SetupArrayBuffer(isolate, old_buffer->backing_store(), | 2444 new_buffer = SetupArrayBuffer(isolate, old_buffer->backing_store(), |
| 2440 old_size, old_buffer->is_external(), | 2445 old_size, old_buffer->is_external(), |
| 2441 old_buffer->has_guard_region()); | 2446 old_buffer->has_guard_region()); |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2481 while (instance_wrapper->has_next()) { | 2486 while (instance_wrapper->has_next()) { |
| 2482 instance_wrapper = instance_wrapper->next_wrapper(); | 2487 instance_wrapper = instance_wrapper->next_wrapper(); |
| 2483 DCHECK(WasmInstanceWrapper::IsWasmInstanceWrapper(*instance_wrapper)); | 2488 DCHECK(WasmInstanceWrapper::IsWasmInstanceWrapper(*instance_wrapper)); |
| 2484 Handle<WasmInstanceObject> instance = instance_wrapper->instance_object(); | 2489 Handle<WasmInstanceObject> instance = instance_wrapper->instance_object(); |
| 2485 DCHECK(IsWasmInstance(*instance)); | 2490 DCHECK(IsWasmInstance(*instance)); |
| 2486 SetInstanceMemory(instance, *new_buffer); | 2491 SetInstanceMemory(instance, *new_buffer); |
| 2487 UncheckedUpdateInstanceMemory(isolate, instance, old_mem_start, old_size); | 2492 UncheckedUpdateInstanceMemory(isolate, instance, old_mem_start, old_size); |
| 2488 } | 2493 } |
| 2489 } | 2494 } |
| 2490 memory_object->set_buffer(*new_buffer); | 2495 memory_object->set_buffer(*new_buffer); |
| 2491 DetachArrayBuffer(isolate, old_buffer); | |
| 2492 DCHECK(old_size % WasmModule::kPageSize == 0); | 2496 DCHECK(old_size % WasmModule::kPageSize == 0); |
| 2493 return (old_size / WasmModule::kPageSize); | 2497 return (old_size / WasmModule::kPageSize); |
| 2494 } | 2498 } |
| 2495 | 2499 |
| 2496 int32_t wasm::GrowMemory(Isolate* isolate, Handle<WasmInstanceObject> instance, | 2500 int32_t wasm::GrowMemory(Isolate* isolate, Handle<WasmInstanceObject> instance, |
| 2497 uint32_t pages) { | 2501 uint32_t pages) { |
| 2498 if (!IsWasmInstance(*instance)) return -1; | 2502 if (!IsWasmInstance(*instance)) return -1; |
| 2499 if (pages == 0) return GetInstanceMemorySize(isolate, instance); | 2503 if (pages == 0) return GetInstanceMemorySize(isolate, instance); |
| 2500 Handle<WasmInstanceObject> instance_obj(WasmInstanceObject::cast(*instance)); | 2504 Handle<WasmInstanceObject> instance_obj(WasmInstanceObject::cast(*instance)); |
| 2501 if (!instance_obj->has_memory_object()) { | 2505 if (!instance_obj->has_memory_object()) { |
| (...skipping 700 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3202 callee_compiled->instruction_start()); | 3206 callee_compiled->instruction_start()); |
| 3203 } | 3207 } |
| 3204 DCHECK_EQ(non_compiled_functions.size(), idx); | 3208 DCHECK_EQ(non_compiled_functions.size(), idx); |
| 3205 } | 3209 } |
| 3206 | 3210 |
| 3207 Code* ret = | 3211 Code* ret = |
| 3208 Code::cast(compiled_module->code_table()->get(func_to_return_idx)); | 3212 Code::cast(compiled_module->code_table()->get(func_to_return_idx)); |
| 3209 DCHECK_EQ(Code::WASM_FUNCTION, ret->kind()); | 3213 DCHECK_EQ(Code::WASM_FUNCTION, ret->kind()); |
| 3210 return handle(ret, isolate); | 3214 return handle(ret, isolate); |
| 3211 } | 3215 } |
| OLD | NEW |