From 0e97463207941ed7215e7394756e1a60115373a6 Mon Sep 17 00:00:00 2001 From: zhangyukun Date: Fri, 24 Sep 2021 14:48:14 +0800 Subject: [PATCH] Add thread check of ecmascript Signed-off-by: zhangyukun Change-Id: I6b954f23e79c0fb98091dc25bc772047489d35bc --- ecmascript/base/config.h | 1 + ecmascript/ecma_vm.h | 10 ++++++++++ ecmascript/js_thread.cpp | 2 +- ecmascript/js_thread.h | 10 ++++++++++ ecmascript/napi/jsnapi.cpp | 4 ++-- ecmascript/napi/test/jsnapi_tests.cpp | 12 ++++++++++++ ecmascript/thread/thread_pool.h | 10 ++++++++++ 7 files changed, 46 insertions(+), 3 deletions(-) diff --git a/ecmascript/base/config.h b/ecmascript/base/config.h index c8d03a02be..229c2eba8c 100644 --- a/ecmascript/base/config.h +++ b/ecmascript/base/config.h @@ -22,6 +22,7 @@ namespace panda::ecmascript { #define ECMASCRIPT_ENABLE_RUNTIME_STAT 0 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) #define ECMASCRIPT_ENABLE_IC 1 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) +#define ECMASCRIPT_ENABLE_THREAD_CHECK 0 } // namespace panda::ecmascript #endif // ECMASCRIPT_BASE_CONFIG_H diff --git a/ecmascript/ecma_vm.h b/ecmascript/ecma_vm.h index afa964b5a1..94c5079c85 100644 --- a/ecmascript/ecma_vm.h +++ b/ecmascript/ecma_vm.h @@ -18,6 +18,7 @@ #include +#include "ecmascript/base/config.h" #include "ecmascript/ecma_string_table.h" #include "ecmascript/global_handle_collection.h" #include "ecmascript/js_handle.h" @@ -27,6 +28,7 @@ #include "ecmascript/mem/c_string.h" #include "ecmascript/mem/chunk_containers.h" #include "ecmascript/mem/gc_stats.h" +#include "ecmascript/mem/heap.h" #include "ecmascript/mem/heap_roots.h" #include "ecmascript/mem/space.h" #include "ecmascript/snapshot/mem/snapshot_serialize.h" @@ -239,6 +241,14 @@ public: JSThread *GetJSThread() const { +#if defined(ECMASCRIPT_ENABLE_THREAD_CHECK) && ECMASCRIPT_ENABLE_THREAD_CHECK + ThreadPool *pool = GetHeap()->GetThreadPool(); + // Exclude GC thread + if (!pool->IsInThreadPool(std::this_thread::get_id()) && + thread_->GetThreadId() != JSThread::GetCurrentThreadId()) { + LOG(FATAL, RUNTIME) << "Fatal: ecma_vm cannot run in multi-thread!"; + } +#endif return thread_; } diff --git a/ecmascript/js_thread.cpp b/ecmascript/js_thread.cpp index f2352867b9..86022c9170 100644 --- a/ecmascript/js_thread.cpp +++ b/ecmascript/js_thread.cpp @@ -36,7 +36,7 @@ JSThread *JSThread::Create(Runtime *runtime, PandaVM *vm) } JSThread::JSThread(Runtime *runtime, PandaVM *vm) - : ManagedThread(NON_INITIALIZED_THREAD_ID, runtime->GetInternalAllocator(), vm, + : ManagedThread(GetCurrentThreadId(), runtime->GetInternalAllocator(), vm, Thread::ThreadType::THREAD_TYPE_MANAGED) { SetLanguageContext(runtime->GetLanguageContext(panda_file::SourceLang::ECMASCRIPT)); diff --git a/ecmascript/js_thread.h b/ecmascript/js_thread.h index eef175a525..647440ba56 100644 --- a/ecmascript/js_thread.h +++ b/ecmascript/js_thread.h @@ -178,6 +178,16 @@ public: return internalCallParams_; } + ThreadId GetThreadId() const + { + return GetId(); + } + + static ThreadId GetCurrentThreadId() + { + return os::thread::GetCurrentThreadId(); + } + void IterateWeakEcmaGlobalStorage(const WeakRootVisitor &visitor); private: diff --git a/ecmascript/napi/jsnapi.cpp b/ecmascript/napi/jsnapi.cpp index b2c50569f4..d0a1a458e5 100644 --- a/ecmascript/napi/jsnapi.cpp +++ b/ecmascript/napi/jsnapi.cpp @@ -901,7 +901,7 @@ int32_t ArrayRef::Length([[maybe_unused]] const EcmaVM *vm) Local ArrayRef::GetValueAt(const EcmaVM *vm, Local obj, uint32_t index) { - JSThread *thread = vm->GetAssociatedJSThread(); + JSThread *thread = vm->GetJSThread(); JSHandle object = JSNApiHelper::ToJSHandle(obj); JSHandle result = JSArray::FastGetPropertyByValue(thread, object, index); return JSNApiHelper::ToLocal(result); @@ -909,7 +909,7 @@ Local ArrayRef::GetValueAt(const EcmaVM *vm, Local obj, bool ArrayRef::SetValueAt(const EcmaVM *vm, Local obj, uint32_t index, Local value) { - JSThread *thread = vm->GetAssociatedJSThread(); + JSThread *thread = vm->GetJSThread(); JSHandle objectHandle = JSNApiHelper::ToJSHandle(obj); JSHandle valueHandle = JSNApiHelper::ToJSHandle(value); return JSArray::FastSetPropertyByValue(thread, objectHandle, index, valueHandle); diff --git a/ecmascript/napi/test/jsnapi_tests.cpp b/ecmascript/napi/test/jsnapi_tests.cpp index a8eb17ef37..8e146169a4 100644 --- a/ecmascript/napi/test/jsnapi_tests.cpp +++ b/ecmascript/napi/test/jsnapi_tests.cpp @@ -66,6 +66,11 @@ Local FunctionCallback(EcmaVM *vm, Local, const LocalGetJSThread()->GetThreadId() != JSThread::GetCurrentThreadId()); +} + HWTEST_F_L0(JSNApiTests, GetGlobalObject) { LocalScope scope(vm_); @@ -74,6 +79,13 @@ HWTEST_F_L0(JSNApiTests, GetGlobalObject) ASSERT_TRUE(globalObject->IsObject()); } +HWTEST_F_L0(JSNApiTests, ThreadIdCheck) +{ + EXPECT_TRUE(vm_->GetJSThread()->GetThreadId() == JSThread::GetCurrentThreadId()); + std::thread testThread(ThreadCheck, vm_); + testThread.join(); +} + HWTEST_F_L0(JSNApiTests, RegisterFunction) { LocalScope scope(vm_); diff --git a/ecmascript/thread/thread_pool.h b/ecmascript/thread/thread_pool.h index 7af95c55db..ee14791b12 100644 --- a/ecmascript/thread/thread_pool.h +++ b/ecmascript/thread/thread_pool.h @@ -112,6 +112,16 @@ public: return threadNum_; } + bool IsInThreadPool(std::thread::id id) const + { + for (auto &worker : workers_) { + if (worker.get_id() == id) { + return true; + } + } + return false; + } + private: NO_COPY_SEMANTIC(ThreadPool); NO_MOVE_SEMANTIC(ThreadPool); -- Gitee