Cholla 3.0.1-dev
Cholla - Massively parallel hydro on GPUs
Loading...
Searching...
No Matches
Classes
Shared Construct Group

Classes

class  SharedHandle< HandleT >
 Wraps a handles while providing shared object semantics. More...
 
class  SharedDevPtr< T >
 Wraps a device pointer while providing shared object semantics. More...
 

Detailed Description

This group describes class templates that provide shared object semantics for some kind of wrapped value that acts as "a form of reference" to some kind of computing resource.

At the time of writing, these constructs include:

These constructs act similarly to a simplified version of std::share_ptr (that also work on GPUs)

Common Operations

These constructs all provide a common set of operations:

Let's establish the basic semantics modeled by these constructs:

Now, let's describe the way that this model is implemented

IMPORTANTLY: these constructs can be used on the host and on GPUs

How it works:

At a high level, these constructs are implemented using (atomic) reference counting. Essentially, the constructs hold a pointer to a "control block" that holds a reference count. When the primary constructor is invoked, the reference count starts at one. Every drops to 0, the deleter callback is then invoked to delete the resource.

In slightly more detail, ownership is only tracked on the host. In case its not obvious why this is a viable strategy, let's make a simple assumption: let's assume for a moment that we are always extremely careful about releasing device resources until after all accesses to a resource are complete.

Under that assumption, let's consider the lifetime of a SharedHandle or a SharedDevPtr a GPU kernel:

What about our assumption? The degree of required care actually depends on the deleter callback. For example, deleters passed to SharedDevPtr that are based upon cudaFree and cudaFreeAsync will have distinct requirements.

Why Use These Constructs

These constructs are most useful as building blocks in larger components. For example, aspects of Cholla's feedback and cooling modules make use of resource allocations for the entirety of a simulation run. These constructs make it easier to build up constructs in a composable manner.

While alternatives are possible, they typically involve either (i) implementing data structures using move-semantics (like std::unique_ptr), or (ii) using global variables.

In the future, the internals of SharedDevPtr could be very useful. The View types adopted in libraries like Kokkos or Raja have the same shared object semantics as SharedDevPtr. We could reuse the machinery to accomplish similar goals: