0
0
Fork 0
mirror of https://github.com/matrix-construct/construct synced 2024-11-16 23:10:54 +01:00

ircd::ctx: Minor cleanup / struct packing / type.

This commit is contained in:
Jason Volk 2018-12-07 10:13:29 -08:00
parent 4e01d2c0a4
commit 3af70e75c3
3 changed files with 35 additions and 33 deletions

View file

@ -49,7 +49,7 @@ namespace ircd::ctx
string_view name(const ctx &); // User's optional label for context string_view name(const ctx &); // User's optional label for context
const size_t &stack_max(const ctx &); // Returns stack size allocated for ctx const size_t &stack_max(const ctx &); // Returns stack size allocated for ctx
const size_t &stack_at(const ctx &); // Stack at last sleep (also see this_ctx.h) const size_t &stack_at(const ctx &); // Stack at last sleep (also see this_ctx.h)
const int64_t &notes(const ctx &); // Peeks at internal semaphore count const int32_t &notes(const ctx &); // Peeks at internal semaphore count
const uint64_t &yields(const ctx &); // Context switching counter const uint64_t &yields(const ctx &); // Context switching counter
const ulong &cycles(const ctx &); // Accumulated tsc (not counting cur slice) const ulong &cycles(const ctx &); // Accumulated tsc (not counting cur slice)
bool interruptible(const ctx &) noexcept; // Context can throw at interruption point bool interruptible(const ctx &) noexcept; // Context can throw at interruption point

View file

@ -118,33 +118,6 @@ catch(const std::exception &e)
return; return;
} }
/// Direct context switch to this context.
///
/// This currently doesn't work yet because the suspension state of this
/// context has to be ready to be jumped to and that isn't implemented yet.
void
ircd::ctx::ctx::jump()
{
assert(this->yc);
assert(current != this); // can't jump to self
auto &yc(*this->yc);
auto &target(*yc.coro_.lock());
// Jump from the currently running context (source) to *this (target)
// with continuation of source after target
{
current->notes = 0; // Unconditionally cleared here
const continuation continuation;
target();
}
assert(current != this);
assert(current->notes == 1); // notes = 1; set by continuation dtor on wakeup
interruption_point();
}
/// Yield (suspend) this context until notified. /// Yield (suspend) this context until notified.
/// ///
/// This context must be currently running otherwise bad things. Returns false /// This context must be currently running otherwise bad things. Returns false
@ -180,6 +153,33 @@ ircd::ctx::ctx::wait()
return true; return true;
} }
/// Direct context switch to this context.
///
/// This currently doesn't work yet because the suspension state of this
/// context has to be ready to be jumped to and that isn't implemented yet.
void
ircd::ctx::ctx::jump()
{
assert(this->yc);
assert(current != this); // can't jump to self
auto &yc(*this->yc);
auto &target(*yc.coro_.lock());
// Jump from the currently running context (source) to *this (target)
// with continuation of source after target
{
current->notes = 0; // Unconditionally cleared here
const continuation continuation;
target();
}
assert(current != this);
assert(current->notes == 1); // notes = 1; set by continuation dtor on wakeup
interruption_point();
}
/// Notifies this context to resume (wake up from waiting). /// Notifies this context to resume (wake up from waiting).
/// ///
/// Returns true if this note was the first note received by this context /// Returns true if this note was the first note received by this context
@ -465,7 +465,7 @@ ircd::ctx::yields(const ctx &ctx)
} }
/// Returns the notification count for `ctx` /// Returns the notification count for `ctx`
const int64_t & const int32_t &
ircd::ctx::notes(const ctx &ctx) ircd::ctx::notes(const ctx &ctx)
{ {
return ctx.notes; return ctx.notes;

View file

@ -40,16 +40,18 @@ struct ircd::ctx::profile
struct ircd::ctx::ctx struct ircd::ctx::ctx
:instance_list<ctx> :instance_list<ctx>
{ {
using flags_t = std::underlying_type<context::flags>::type;
static uint64_t id_ctr; // monotonic static uint64_t id_ctr; // monotonic
uint64_t id {++id_ctr}; // Unique runtime ID uint64_t id {++id_ctr}; // Unique runtime ID
const char *name {nullptr}; // User given name (optional) const char *name {nullptr}; // User given name (optional)
context::flags flags {(context::flags)0}; // User given flags flags_t flags {0}; // User given flags
int32_t notes {0}; // norm: 0 = asleep; 1 = awake; inc by others; dec by self
boost::asio::io_service::strand strand; // mutex/serializer boost::asio::io_service::strand strand; // mutex/serializer
boost::asio::steady_timer alarm; // acting semaphore (64B) boost::asio::steady_timer alarm; // acting semaphore (64B)
boost::asio::yield_context *yc {nullptr}; // boost interface boost::asio::yield_context *yc {nullptr}; // boost interface
continuation *cont {nullptr}; // valid when asleep; invalid when awake continuation *cont {nullptr}; // valid when asleep; invalid when awake
int64_t notes {0}; // norm: 0 = asleep; 1 = awake; inc by others; dec by self
ircd::ctx::stack stack; // stack related structure ircd::ctx::stack stack; // stack related structure
ircd::ctx::profile profile; // prof related structure ircd::ctx::profile profile; // prof related structure
list::node node; // node for ctx::list list::node node; // node for ctx::list
@ -62,10 +64,10 @@ struct ircd::ctx::ctx
bool termination_point(std::nothrow_t); // Check for terminate bool termination_point(std::nothrow_t); // Check for terminate
void interruption_point(); // throws interrupted or terminated void interruption_point(); // throws interrupted or terminated
bool wait(); // yield context to ios queue (returns on this resume)
void jump(); // jump to context directly (returns on your resume)
void wake(); // jump to context by queueing with ios (use note()) void wake(); // jump to context by queueing with ios (use note())
bool note(); // properly request wake() bool note(); // properly request wake()
void jump(); // jump to context directly (returns on your resume)
bool wait(); // yield context to ios queue (returns on this resume)
void operator()(boost::asio::yield_context, const std::function<void ()>) noexcept; void operator()(boost::asio::yield_context, const std::function<void ()>) noexcept;