Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(59)

Side by Side Diff: src/wasm/wasm-module.cc

Issue 2394663008: [wasm] Extend wasm object validation to WasmCompiledModule (Closed)
Patch Set: Remove debug code Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/wasm/wasm-module.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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/base/atomic-utils.h" 7 #include "src/base/atomic-utils.h"
8 #include "src/code-stubs.h" 8 #include "src/code-stubs.h"
9 9
10 #include "src/macro-assembler.h" 10 #include "src/macro-assembler.h"
(...skipping 1109 matching lines...) Expand 10 before | Expand all | Expand 10 after
1120 // TODO(wasm): saving the module bytes for debugging is wasteful. We should 1120 // TODO(wasm): saving the module bytes for debugging is wasteful. We should
1121 // consider downloading this on-demand. 1121 // consider downloading this on-demand.
1122 { 1122 {
1123 size_t module_bytes_len = module_end - module_start; 1123 size_t module_bytes_len = module_end - module_start;
1124 DCHECK_LE(module_bytes_len, static_cast<size_t>(kMaxInt)); 1124 DCHECK_LE(module_bytes_len, static_cast<size_t>(kMaxInt));
1125 Vector<const uint8_t> module_bytes_vec(module_start, 1125 Vector<const uint8_t> module_bytes_vec(module_start,
1126 static_cast<int>(module_bytes_len)); 1126 static_cast<int>(module_bytes_len));
1127 Handle<String> module_bytes_string = 1127 Handle<String> module_bytes_string =
1128 factory->NewStringFromOneByte(module_bytes_vec, TENURED) 1128 factory->NewStringFromOneByte(module_bytes_vec, TENURED)
1129 .ToHandleChecked(); 1129 .ToHandleChecked();
1130 ret->set_module_bytes(module_bytes_string); 1130 DCHECK(module_bytes_string->IsSeqOneByteString());
1131 ret->set_module_bytes(Handle<SeqOneByteString>::cast(module_bytes_string));
1131 } 1132 }
1132 1133
1133 Handle<ByteArray> function_name_table = 1134 Handle<ByteArray> function_name_table =
1134 BuildFunctionNamesTable(isolate, module_env.module); 1135 BuildFunctionNamesTable(isolate, module_env.module);
1135 ret->set_function_names(function_name_table); 1136 ret->set_function_names(function_name_table);
1136 if (data_segments.size() > 0) SaveDataSegmentInfo(factory, this, ret); 1137 if (data_segments.size() > 0) SaveDataSegmentInfo(factory, this, ret);
1137 DCHECK_EQ(ret->default_mem_size(), temp_instance.mem_size); 1138 DCHECK_EQ(ret->default_mem_size(), temp_instance.mem_size);
1138 return ret; 1139 return ret;
1139 } 1140 }
1140 1141
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after
1301 if (num_imported_functions < 0) return nothing; 1302 if (num_imported_functions < 0) return nothing;
1302 1303
1303 //-------------------------------------------------------------------------- 1304 //--------------------------------------------------------------------------
1304 // Process the initialization for the module's globals. 1305 // Process the initialization for the module's globals.
1305 //-------------------------------------------------------------------------- 1306 //--------------------------------------------------------------------------
1306 ProcessInits(globals); 1307 ProcessInits(globals);
1307 1308
1308 //-------------------------------------------------------------------------- 1309 //--------------------------------------------------------------------------
1309 // Set up the debug support for the new instance. 1310 // Set up the debug support for the new instance.
1310 //-------------------------------------------------------------------------- 1311 //--------------------------------------------------------------------------
1311 // TODO(wasm): avoid referencing this stuff from the instance, use it off 1312 // TODO(clemensh): avoid referencing this stuff from the instance, use it
1312 // the compiled module instead. See the following 3 assignments: 1313 // off the compiled module instead. See the following 3 assignments:
1313 if (compiled_module_->has_module_bytes()) { 1314 if (compiled_module_->has_module_bytes()) {
1314 instance->SetInternalField(kWasmModuleBytesString, 1315 instance->SetInternalField(kWasmModuleBytesString,
1315 compiled_module_->ptr_to_module_bytes()); 1316 compiled_module_->ptr_to_module_bytes());
1316 } 1317 }
1317 1318
1318 if (compiled_module_->has_function_names()) { 1319 if (compiled_module_->has_function_names()) {
1319 instance->SetInternalField(kWasmFunctionNamesArray, 1320 instance->SetInternalField(kWasmFunctionNamesArray,
1320 compiled_module_->ptr_to_function_names()); 1321 compiled_module_->ptr_to_function_names());
1321 } 1322 }
1322 1323
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
1406 Handle<Object> undefined = factory->undefined_value(); 1407 Handle<Object> undefined = factory->undefined_value();
1407 MaybeHandle<Object> retval = 1408 MaybeHandle<Object> retval =
1408 Execution::Call(isolate_, startup_fct, undefined, 0, nullptr); 1409 Execution::Call(isolate_, startup_fct, undefined, 0, nullptr);
1409 1410
1410 if (retval.is_null()) { 1411 if (retval.is_null()) {
1411 thrower_->Error("WASM.instantiateModule(): start function failed"); 1412 thrower_->Error("WASM.instantiateModule(): start function failed");
1412 return nothing; 1413 return nothing;
1413 } 1414 }
1414 } 1415 }
1415 1416
1416 DCHECK(wasm::IsWasmObject(*instance));
1417
1418 { 1417 {
1419 Handle<WeakCell> link_to_owner = factory->NewWeakCell(instance); 1418 Handle<WeakCell> link_to_owner = factory->NewWeakCell(instance);
1420 1419
1421 Handle<Object> global_handle = 1420 Handle<Object> global_handle =
1422 isolate_->global_handles()->Create(*instance); 1421 isolate_->global_handles()->Create(*instance);
1423 Handle<WeakCell> link_to_clone = factory->NewWeakCell(compiled_module_); 1422 Handle<WeakCell> link_to_clone = factory->NewWeakCell(compiled_module_);
1424 { 1423 {
1425 DisallowHeapAllocation no_gc; 1424 DisallowHeapAllocation no_gc;
1426 compiled_module_->set_weak_owning_instance(link_to_owner); 1425 compiled_module_->set_weak_owning_instance(link_to_owner);
1427 Handle<WeakCell> next; 1426 Handle<WeakCell> next;
1428 if (link_to_original.ToHandle(&next) && !next->cleared()) { 1427 if (link_to_original.ToHandle(&next) && !next->cleared()) {
1429 WasmCompiledModule* original = 1428 WasmCompiledModule* original =
1430 WasmCompiledModule::cast(next->value()); 1429 WasmCompiledModule::cast(next->value());
1431 DCHECK(original->has_weak_owning_instance()); 1430 DCHECK(original->has_weak_owning_instance());
1432 DCHECK(!original->weak_owning_instance()->cleared()); 1431 DCHECK(!original->weak_owning_instance()->cleared());
1433 compiled_module_->set_weak_next_instance(next); 1432 compiled_module_->set_weak_next_instance(next);
1434 original->set_weak_prev_instance(link_to_clone); 1433 original->set_weak_prev_instance(link_to_clone);
1435 } 1434 }
1436 1435
1437 compiled_module_->set_weak_owning_instance(link_to_owner); 1436 compiled_module_->set_weak_owning_instance(link_to_owner);
1438 instance->SetInternalField(kWasmCompiledModule, *compiled_module_); 1437 instance->SetInternalField(kWasmCompiledModule, *compiled_module_);
1439 GlobalHandles::MakeWeak(global_handle.location(), 1438 GlobalHandles::MakeWeak(global_handle.location(),
1440 global_handle.location(), &InstanceFinalizer, 1439 global_handle.location(), &InstanceFinalizer,
1441 v8::WeakCallbackType::kFinalizer); 1440 v8::WeakCallbackType::kFinalizer);
1442 } 1441 }
1443 } 1442 }
1443
1444 DCHECK(wasm::IsWasmObject(*instance));
1445
1444 TRACE("Finishing instance %d\n", compiled_module_->instance_id()); 1446 TRACE("Finishing instance %d\n", compiled_module_->instance_id());
1445 TRACE_CHAIN(WasmCompiledModule::cast(module_object_->GetInternalField(0))); 1447 TRACE_CHAIN(WasmCompiledModule::cast(module_object_->GetInternalField(0)));
1446 return instance; 1448 return instance;
1447 } 1449 }
1448 1450
1449 private: 1451 private:
1450 Isolate* isolate_; 1452 Isolate* isolate_;
1451 ErrorThrower* thrower_; 1453 ErrorThrower* thrower_;
1452 Handle<JSObject> module_object_; 1454 Handle<JSObject> module_object_;
1453 Handle<JSReceiver> ffi_; 1455 Handle<JSReceiver> ffi_;
(...skipping 410 matching lines...) Expand 10 before | Expand all | Expand 10 after
1864 isolate->factory()->NewFixedArray(PropertyIndices::Count, TENURED); 1866 isolate->factory()->NewFixedArray(PropertyIndices::Count, TENURED);
1865 // Globals size is expected to fit into an int without overflow. This is not 1867 // Globals size is expected to fit into an int without overflow. This is not
1866 // supported by the spec at the moment, however, we don't support array 1868 // supported by the spec at the moment, however, we don't support array
1867 // buffer sizes over 1g, so, for now, we avoid alocating a HeapNumber for 1869 // buffer sizes over 1g, so, for now, we avoid alocating a HeapNumber for
1868 // the globals size. The CHECK guards this assumption. 1870 // the globals size. The CHECK guards this assumption.
1869 CHECK_GE(static_cast<int>(globals_size), 0); 1871 CHECK_GE(static_cast<int>(globals_size), 0);
1870 ret->set(kID_min_memory_pages, 1872 ret->set(kID_min_memory_pages,
1871 Smi::FromInt(static_cast<int>(min_memory_pages))); 1873 Smi::FromInt(static_cast<int>(min_memory_pages)));
1872 ret->set(kID_globals_size, Smi::FromInt(static_cast<int>(globals_size))); 1874 ret->set(kID_globals_size, Smi::FromInt(static_cast<int>(globals_size)));
1873 ret->set(kID_origin, Smi::FromInt(static_cast<int>(origin))); 1875 ret->set(kID_origin, Smi::FromInt(static_cast<int>(origin)));
1874 WasmCompiledModule::cast(*ret)->Init(); 1876
1875 return handle(WasmCompiledModule::cast(*ret)); 1877 // WasmCompiledModule::cast would fail since module bytes are not set yet.
1878 Handle<WasmCompiledModule> module(reinterpret_cast<WasmCompiledModule*>(*ret),
1879 isolate);
1880 module->Init();
1881 return module;
1876 } 1882 }
1877 1883
1878 void WasmCompiledModule::Init() { 1884 void WasmCompiledModule::Init() {
1879 #if DEBUG 1885 #if DEBUG
1880 static uint32_t instance_id_counter = 0; 1886 static uint32_t instance_id_counter = 0;
1881 set(kID_instance_id, Smi::FromInt(instance_id_counter++)); 1887 set(kID_instance_id, Smi::FromInt(instance_id_counter++));
1882 TRACE("New compiled module id: %d\n", instance_id()); 1888 TRACE("New compiled module id: %d\n", instance_id());
1883 #endif 1889 #endif
1884 } 1890 }
1885 1891
1892 bool WasmCompiledModule::IsWasmCompiledModule(Object* obj) {
1893 if (!obj->IsFixedArray()) return false;
1894 FixedArray* arr = FixedArray::cast(obj);
1895 if (arr->length() != PropertyIndices::Count) return false;
1896 Isolate* isolate = arr->GetIsolate();
1897 #define WCM_CHECK_SMALL_NUMBER(TYPE, NAME) \
1898 if (!arr->get(kID_##NAME)->IsSmi()) return false;
1899 #define WCM_CHECK_OBJECT_OR_WEAK(TYPE, NAME) \
1900 if (!arr->get(kID_##NAME)->IsUndefined(isolate) && \
1901 !arr->get(kID_##NAME)->Is##TYPE()) \
1902 return false;
1903 #define WCM_CHECK_OBJECT(TYPE, NAME) WCM_CHECK_OBJECT_OR_WEAK(TYPE, NAME)
1904 #define WCM_CHECK_WEAK_LINK(TYPE, NAME) WCM_CHECK_OBJECT_OR_WEAK(WeakCell, NAME)
1905 #define WCM_CHECK(KIND, TYPE, NAME) WCM_CHECK_##KIND(TYPE, NAME)
1906 WCM_PROPERTY_TABLE(WCM_CHECK)
1907 #undef WCM_CHECK
1908
1909 WasmCompiledModule* compiled_module =
1910 reinterpret_cast<WasmCompiledModule*>(obj);
1911 if (!compiled_module->has_module_bytes()) return false;
1912 SeqOneByteString* module_bytes = compiled_module->ptr_to_module_bytes();
1913 if (module_bytes->length() < 4) return false;
1914 if (memcmp(module_bytes->GetChars(), "\0asm", 4)) return false;
1915
1916 // All checks passed.
1917 return true;
1918 }
1919
1886 void WasmCompiledModule::PrintInstancesChain() { 1920 void WasmCompiledModule::PrintInstancesChain() {
1887 #if DEBUG 1921 #if DEBUG
1888 if (!FLAG_trace_wasm_instances) return; 1922 if (!FLAG_trace_wasm_instances) return;
1889 for (WasmCompiledModule* current = this; current != nullptr;) { 1923 for (WasmCompiledModule* current = this; current != nullptr;) {
1890 PrintF("->%d", current->instance_id()); 1924 PrintF("->%d", current->instance_id());
1891 if (current->ptr_to_weak_next_instance() == nullptr) break; 1925 if (current->ptr_to_weak_next_instance() == nullptr) break;
1892 CHECK(!current->ptr_to_weak_next_instance()->cleared()); 1926 CHECK(!current->ptr_to_weak_next_instance()->cleared());
1893 current = 1927 current =
1894 WasmCompiledModule::cast(current->ptr_to_weak_next_instance()->value()); 1928 WasmCompiledModule::cast(current->ptr_to_weak_next_instance()->value());
1895 } 1929 }
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
1928 bool IsWasmObject(Object* object) { 1962 bool IsWasmObject(Object* object) {
1929 if (!object->IsJSObject()) return false; 1963 if (!object->IsJSObject()) return false;
1930 1964
1931 JSObject* obj = JSObject::cast(object); 1965 JSObject* obj = JSObject::cast(object);
1932 Isolate* isolate = obj->GetIsolate(); 1966 Isolate* isolate = obj->GetIsolate();
1933 if (obj->GetInternalFieldCount() != kWasmModuleInternalFieldCount) { 1967 if (obj->GetInternalFieldCount() != kWasmModuleInternalFieldCount) {
1934 return false; 1968 return false;
1935 } 1969 }
1936 1970
1937 Object* mem = obj->GetInternalField(kWasmMemArrayBuffer); 1971 Object* mem = obj->GetInternalField(kWasmMemArrayBuffer);
1938 if (obj->GetInternalField(kWasmModuleCodeTable)->IsFixedArray() && 1972 if (!obj->GetInternalField(kWasmModuleCodeTable)->IsFixedArray() ||
1939 (mem->IsUndefined(isolate) || mem->IsJSArrayBuffer()) && 1973 !(mem->IsUndefined(isolate) || mem->IsJSArrayBuffer()) ||
1940 obj->GetInternalField(kWasmFunctionNamesArray)->IsByteArray()) { 1974 !obj->GetInternalField(kWasmFunctionNamesArray)->IsByteArray() ||
1941 Object* debug_bytes = obj->GetInternalField(kWasmModuleBytesString); 1975 !WasmCompiledModule::IsWasmCompiledModule(
1942 if (!debug_bytes->IsUndefined(isolate)) { 1976 obj->GetInternalField(kWasmCompiledModule))) {
1943 if (!debug_bytes->IsSeqOneByteString()) { 1977 return false;
1944 return false;
1945 }
1946 DisallowHeapAllocation no_gc;
1947 SeqOneByteString* bytes = SeqOneByteString::cast(debug_bytes);
1948 if (bytes->length() < 4) return false;
1949 if (memcmp(bytes->GetChars(), "\0asm", 4)) return false;
1950 // All checks passed.
1951 }
1952 return true;
1953 } 1978 }
1954 return false; 1979
1980 // All checks passed.
1981 return true;
1955 } 1982 }
1956 1983
1957 SeqOneByteString* GetWasmBytes(JSObject* wasm) { 1984 SeqOneByteString* GetWasmBytes(JSObject* wasm) {
1958 return SeqOneByteString::cast(wasm->GetInternalField(kWasmModuleBytesString)); 1985 return SeqOneByteString::cast(wasm->GetInternalField(kWasmModuleBytesString));
1959 } 1986 }
1960 1987
1961 Handle<WasmDebugInfo> GetDebugInfo(Handle<JSObject> wasm) { 1988 Handle<WasmDebugInfo> GetDebugInfo(Handle<JSObject> wasm) {
1962 Handle<Object> info(wasm->GetInternalField(kWasmDebugInfo), 1989 Handle<Object> info(wasm->GetInternalField(kWasmDebugInfo),
1963 wasm->GetIsolate()); 1990 wasm->GetIsolate());
1964 if (!info->IsUndefined(wasm->GetIsolate())) 1991 if (!info->IsUndefined(wasm->GetIsolate()))
(...skipping 259 matching lines...) Expand 10 before | Expand all | Expand 10 after
2224 WasmCompiledModule* compiled_module = 2251 WasmCompiledModule* compiled_module =
2225 WasmCompiledModule::cast(instance->GetInternalField(kWasmCompiledModule)); 2252 WasmCompiledModule::cast(instance->GetInternalField(kWasmCompiledModule));
2226 CHECK(compiled_module->has_weak_module_object()); 2253 CHECK(compiled_module->has_weak_module_object());
2227 CHECK(compiled_module->ptr_to_weak_module_object()->cleared()); 2254 CHECK(compiled_module->ptr_to_weak_module_object()->cleared());
2228 } 2255 }
2229 2256
2230 } // namespace testing 2257 } // namespace testing
2231 } // namespace wasm 2258 } // namespace wasm
2232 } // namespace internal 2259 } // namespace internal
2233 } // namespace v8 2260 } // namespace v8
OLDNEW
« no previous file with comments | « src/wasm/wasm-module.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698