summaryrefslogtreecommitdiff
path: root/src/interp
diff options
context:
space:
mode:
authorZoltan Herczeg <zherczeg.u-szeged@partner.samsung.com>2022-02-04 16:59:35 +0100
committerGitHub <noreply@github.com>2022-02-04 15:59:35 +0000
commitc2aec5aef9a476c5be41525236af259edb6aad6c (patch)
treee048d1550eeac2bcb392966b1fc0eb51b63d2126 /src/interp
parent6da72bf1ae1a2c25c91bde23a190c4acab888904 (diff)
downloadwabt-c2aec5aef9a476c5be41525236af259edb6aad6c.tar.gz
wabt-c2aec5aef9a476c5be41525236af259edb6aad6c.tar.bz2
wabt-c2aec5aef9a476c5be41525236af259edb6aad6c.zip
Change Thread in interpreter to a normal object (#1809)
Improves memory consumption since thread instances are freed without running garbage collector.
Diffstat (limited to 'src/interp')
-rw-r--r--src/interp/interp-inl.h14
-rw-r--r--src/interp/interp.cc32
-rw-r--r--src/interp/interp.h22
3 files changed, 33 insertions, 35 deletions
diff --git a/src/interp/interp-inl.h b/src/interp/interp-inl.h
index 1237d811..49d85662 100644
--- a/src/interp/interp-inl.h
+++ b/src/interp/interp-inl.h
@@ -467,6 +467,10 @@ inline const Features& Store::features() const {
return features_;
}
+inline std::set<Thread*>& Store::threads() {
+ return threads_;
+}
+
//// Object ////
// static
inline bool Object::classof(const Object* obj) {
@@ -938,16 +942,6 @@ inline std::vector<DataSegment>& Instance::datas() {
}
//// Thread ////
-// static
-inline bool Thread::classof(const Object* obj) {
- return obj->kind() == skind;
-}
-
-// static
-inline Thread::Ptr Thread::New(Store& store, const Options& options) {
- return store.Alloc<Thread>(store, options);
-}
-
inline Store& Thread::store() {
return store_;
}
diff --git a/src/interp/interp.cc b/src/interp/interp.cc
index bba27c9b..bd9fbb2c 100644
--- a/src/interp/interp.cc
+++ b/src/interp/interp.cc
@@ -256,6 +256,10 @@ void Store::Collect() {
}
}
+ for (auto thread : threads_) {
+ thread->Mark();
+ }
+
// TODO: better GC algo.
// Loop through all newly marked objects and mark their referents.
std::vector<bool> all_marked(object_count, false);
@@ -366,10 +370,8 @@ Result Func::Call(Store& store,
Values& results,
Trap::Ptr* out_trap,
Stream* trace_stream) {
- Thread::Options options;
- options.trace_stream = trace_stream;
- Thread::Ptr thread = Thread::New(store, options);
- return DoCall(*thread, params, results, out_trap);
+ Thread thread(store, trace_stream);
+ return DoCall(thread, params, results, out_trap);
}
Result Func::Call(Thread& thread,
@@ -934,24 +936,30 @@ void Instance::Mark(Store& store) {
}
//// Thread ////
-Thread::Thread(Store& store, const Options& options)
- : Object(skind), store_(store) {
+Thread::Thread(Store& store, Stream* trace_stream)
+ : store_(store), trace_stream_(trace_stream) {
+ store.threads().insert(this);
+
+ Thread::Options options;
frames_.reserve(options.call_stack_size);
values_.reserve(options.value_stack_size);
- trace_stream_ = options.trace_stream;
- if (options.trace_stream) {
+ if (trace_stream) {
trace_source_ = MakeUnique<TraceSource>(this);
}
}
-void Thread::Mark(Store& store) {
+Thread::~Thread() {
+ store_.threads().erase(this);
+}
+
+void Thread::Mark() {
for (auto&& frame : frames_) {
- frame.Mark(store);
+ frame.Mark(store_);
}
for (auto index : refs_) {
- store.Mark(values_[index].Get<Ref>());
+ store_.Mark(values_[index].Get<Ref>());
}
- store.Mark(exceptions_);
+ store_.Mark(exceptions_);
}
void Thread::PushValues(const ValueTypes& types, const Values& values) {
diff --git a/src/interp/interp.h b/src/interp/interp.h
index 5c7dd8d3..270228f5 100644
--- a/src/interp/interp.h
+++ b/src/interp/interp.h
@@ -20,6 +20,7 @@
#include <cstdint>
#include <functional>
#include <memory>
+#include <set>
#include <string>
#include <type_traits>
#include <vector>
@@ -90,7 +91,6 @@ enum class ObjectKind {
Tag,
Module,
Instance,
- Thread,
};
const char* GetName(Mutability);
@@ -500,11 +500,15 @@ class Store {
const Features& features() const;
void setFeatures(const Features& features) { features_ = features; }
+ std::set<Thread*>& threads();
+
private:
template <typename T>
friend class RefPtr;
Features features_;
+ // This set contains the currently active Thread objects.
+ std::set<Thread*> threads_;
ObjectList objects_;
RootList roots_;
std::vector<bool> marks_;
@@ -1086,15 +1090,8 @@ enum class RunResult {
Exception,
};
-// TODO: Kinda weird to have a thread as an object, but it makes reference
-// marking simpler.
-class Thread : public Object {
+class Thread {
public:
- static bool classof(const Object* obj);
- static const ObjectKind skind = ObjectKind::Thread;
- static const char* GetTypeName() { return "Thread"; }
- using Ptr = RefPtr<Thread>;
-
struct Options {
static const u32 kDefaultValueStackSize = 64 * 1024 / sizeof(Value);
static const u32 kDefaultCallStackSize = 64 * 1024 / sizeof(Frame);
@@ -1104,13 +1101,15 @@ class Thread : public Object {
Stream* trace_stream = nullptr;
};
- static Thread::Ptr New(Store&, const Options&);
+ Thread(Store& store, Stream* trace_stream = nullptr);
+ ~Thread();
RunResult Run(Trap::Ptr* out_trap);
RunResult Run(int num_instructions, Trap::Ptr* out_trap);
RunResult Step(Trap::Ptr* out_trap);
Store& store();
+ void Mark();
Instance* GetCallerInstance();
@@ -1120,9 +1119,6 @@ class Thread : public Object {
struct TraceSource;
- explicit Thread(Store&, const Options&);
- void Mark(Store&) override;
-
RunResult PushCall(Ref func, u32 offset, Trap::Ptr* out_trap);
RunResult PushCall(const DefinedFunc&, Trap::Ptr* out_trap);
RunResult PushCall(const HostFunc&, Trap::Ptr* out_trap);