0
0
Fork 0
mirror of https://github.com/matrix-construct/construct synced 2025-03-13 21:10:32 +01:00

ircd:Ⓜ️:vm::eval: Add pointer to parent eval; related utils.

ircd:Ⓜ️:vm::eval: Add pointer to child evals; maintain stack.
This commit is contained in:
Jason Volk 2020-05-12 17:49:15 -07:00
parent 32c4ee29c5
commit 987a3eeb6b
2 changed files with 62 additions and 0 deletions

View file

@ -77,6 +77,8 @@ struct ircd::m::vm::eval
const vm::opts *opts {&default_opts};
const vm::copts *copts {nullptr};
ctx::ctx *ctx {ctx::current};
vm::eval *parent {nullptr};
vm::eval *child {nullptr};
uint64_t id {++id_ctr};
uint64_t sequence {0};
uint64_t sequence_shared[2] {0}; // min, max
@ -116,6 +118,8 @@ struct ircd::m::vm::eval
~eval() noexcept;
static bool for_each(const ctx::ctx *const &, const std::function<bool (eval &)> &);
static eval *find_parent(const eval &, const ctx::ctx & = ctx::cur());
static eval *find_root(const eval &, const ctx::ctx & = ctx::cur());
static size_t count(const ctx::ctx *const &);
static bool for_each(const std::function<bool (eval &)> &);

View file

@ -271,6 +271,40 @@ ircd::m::vm::eval::count(const ctx::ctx *const &c)
});
}
ircd::m::vm::eval *
ircd::m::vm::eval::find_root(const eval &a,
const ctx::ctx &c)
{
eval *ret {nullptr}, *parent {nullptr}; do
{
if(!(parent = find_parent(a, c)))
return ret;
ret = parent;
}
while(1);
}
ircd::m::vm::eval *
ircd::m::vm::eval::find_parent(const eval &a,
const ctx::ctx &c)
{
eval *ret {nullptr};
for_each(&c, [&ret, &a]
(eval &eval)
{
const bool cond
{
(&eval != &a) && (!ret || eval.id > ret->id)
};
ret = cond? &eval : ret;
return true;
});
return ret;
}
bool
ircd::m::vm::eval::for_each(const ctx::ctx *const &c,
const std::function<bool (eval &)> &closure)
@ -289,13 +323,31 @@ ircd::m::vm::eval::for_each(const ctx::ctx *const &c,
ircd::m::vm::eval::eval(const vm::opts &opts)
:opts{&opts}
,parent
{
find_parent(*this)
}
{
if(parent)
{
assert(!parent->child);
parent->child = this;
}
}
ircd::m::vm::eval::eval(const vm::copts &opts)
:opts{&opts}
,copts{&opts}
,parent
{
find_parent(*this)
}
{
if(parent)
{
assert(!parent->child);
parent->child = this;
}
}
ircd::m::vm::eval::eval(json::iov &event,
@ -334,6 +386,12 @@ ircd::m::vm::eval::eval(const vector_view<m::event> &events,
ircd::m::vm::eval::~eval()
noexcept
{
assert(!child);
if(parent)
{
assert(parent->child == this);
parent->child = nullptr;
}
}
size_t