-
Notifications
You must be signed in to change notification settings - Fork 18
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Declarative side effects #68
Conversation
d0f80e9
to
bc757a4
Compare
From today's Celerity meeting:
|
One more thing from the discussion: If we do end up using the existing deduction tags, we should probably opt for the |
84c8c95
to
c20f377
Compare
From yesterday's Celerity meeting:
|
cce282c
to
702d31f
Compare
This has now left the RFC phase and is ready for review. |
1760326
to
f4ed645
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks pretty good to me. The introduction of task_geometry
also cleans that part up a bit.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Apart from some minor bikeshedding, this looks good to me.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM!
…t_order; split side_effect.h
Currently, state that is not managed by Celerity must be modified through reference-captures in host tasks. This is opaque to the runtime and does not allow us to detect dependencies on global state between tasks and commands. SYCL proposes
handler::depends_on
for this purpose, mostly motivated by USM. In Celerity however, we want to avoid control-flow dependencies if possible and focus on data flow.New Public APIs
This PR introduces new declarative APIs for host-task side-effects.
celerity::experimental::host_object<T>
wraps and manages an arbitrary value which should be tracked by the runtime. This has roughly the semantics of a buffer. Specializations exists forhost_object<T&>
which tracks a user-owned value andhost_object<void>
which tracks access to global state.celerity::experimental::side_effect
in a host-task kernel declares that the task will affect the host object, and that a dependency exists to preceding and following tasks affecting the same host object. Aside_effect
has roughly the semantics of an accessor.This eliminates some use cases for reference-captures and properly solves the ordering problem in the
wave_sim
example that is being worked around in #66.So far, side effects always generate true-dependencies to the last task that affected the same host object. We are aware that this might be overly restrictive for uses that do not care about access ordering or are fully thread-safe. A backwards-compatible API for specifying constraints (similar to
celerity::access_mode
orstd::memory_order
) will be investigated in a future RFC.Internal additions
host_object_manager
that manages thehost_object_id
s and knows when the last host-object goes out of scope to (potentially) initiate runtime shutdown.celerity::handler
tracks aside_effect_map
similar to thebuffer_access_map
and passes it to thetask
on creation.task_manager
andgraph_generator
track the last task / command affecting each host object to properly generate dependencies.For an example usage, see the wave_sim example.
Resolved Questions
side_effect_order
).void
specialization for side effects on globals)experimental::
namespace? (=> experimental namespace for now)shared
vsexclusive
dichotomy be better than the current classification intoread
andwrite
side effects (we were re-using access_mode in the first design iteration)? We use these to control concurrency, but if a mutating kernel does so atomically, we do not need to serialize it. Classifying it as a read would be counter-intuitive. Also, will exclusive vs. shared also change dependency generation in any way? (=> Will be solved in a future RFC)host_object
is not very descriptive, although it highlights the connection tohost_task
. The name needs to clarify that, unlike a buffer, this type is neither replicated nor distributed. (=> Good for now, though we might change the name before stabilization).sequential
order on side effects. Is that a good idea? (=> Yes, similar tomemory_order::seq_cst
being the default for atomics, this should only cause inefficiency, never incorrectness).