-
Notifications
You must be signed in to change notification settings - Fork 16
The ArrayIR class and YAKL Interoperation with Kokkos and other portability libraries
Please see the following page for full API documentation of ArrayIR
: https://mrnorman.github.io/yakl_api/html/namespaceArrayIR.html
In the file YAKL/external/ArrayIR.h
, you'll find an ArrayIR
namespace and class that have no dependencies on YAKL or any other portability library. It provides an "intermediate representation" of any portable library's multi-dimensional array object. It contains a data type and rank (both template parameters) as well as:
- A data pointer
- A set of dimension sizes represented as a
std::array<size_t,rank>
with the right-most varying the fastest (C-style) - A memory type specifier that declares whether the data pointer is valid only on the host (
ArrayIR::MEMORY_HOST
), only on the device (ArrayIR::MEMORY_DEVICE
), or on both the host and device (ArrayIR::MEMORY_SHARED
) - A
char const *
label used for debugging purposes if the user wants
You can create an ArrayIR
object directly from a YAKL CArray
or FArray
object with the array object's create_ArrayIR()
member function, and you can change the cv qualifiers if you want, e.g. my_obj.create_ArrayIR<float const>()
, but that template parameter is optional and defaults to the type of the array object the method is called on. An FArray
object will reverse its dimension sizes when creating an ArrayIR
object to maintain the C-style expectations.
YAKL CArray
and FArray
objects can accept an ArrayIR
object in their constructors. An FArray
object will reverse the dimension sizes since it expects column-major indexing, and it will also accept an optional std::vector<int>
parameter of lower bounds if you do not want the default of 1
. There is also error checking to ensure you are not creating a memDevice
Array
of host only ArrayIR data or a memHost
Array
of device-only data.
ArrayIR
objects are considered to be un-owned, and they do not manage or guarantee the validity or lifetimes of the data they point to. This is virtually impossible to guarantee across portability frameworks anyway. All data pointed to in an ArrayIR
object is assumed to be contiguous in memory with no striding, and this corresponds to a YAKL Array
object of styleC
and a Kokkos View
object of LayoutRight
. All information must be provided to the ArrayIR
constructor. Once an object is constructed, it cannot be modified (for safety), and only read-only accessors to information can be used afterward. The ArrayIR class may only be used from the host and not the device. It is only intended to hold array metadata to be transformed from one portability framework to another. Please create your portability framework's array object from the ArrayIR
object, and then use that on the device. The ArrayIR class purposefully does not provide an overload of operator()
because you should not be using it to access the data itself. It is only holding the array object's metadata.
It really is best not to try to use YAKL and another portability framework in the same CMake build directory (or to include YAKL and another portability framework in the same file). This is especially true with Kokkos because Kokkos and YAKL have different approaches to the build process for some backends. For instance, Kokkos wants to use the CXXFLAGS
environment variable for files that use Kokkos, and with the CUDA backend, Kokkos wants to use nvcc_wrapper
to compile all C++ files in the entire project. YAKL is a bit less invasive with respect to these issues. You provide the flags you want for YAKL files via the YAKL_[LANG]_FLAGS
CMake variable, and they are only applied to C++ files actually using YAKL. Also, YAKL declared CUDA files as the CUDA language in CMake and lets CMake handle them accordingly. Older Kokkos versions require c++14 while newer versions require c++17 (the same is true for YAKL), and if that isn't compatible, the build will be difficult to manage.
The ArrayIR
class, which has no c++ portability library dependencies allows users to pass Arrays between portability libraries without forcing them to directly interact in a build system.
API documentation:
ArrayIR
namespaceArrayIR
classyakl::CArray::create_ArrayIR()
yakl::CArray::CArray(ArrayIR::ArrayIR)
yakl::FArray::create_ArrayIR()
yakl::FArray::CArray(ArrayIR::ArrayIR)
YAKL parallel_for
launchers can use Kokkos View
objects, and Kokkos parallel_for
and parallel_reduce
launchers can use YAKL Array
objects.
You can use YAKL atomic functions inside Kokkos parallel_for
launchers.
You can use YAKL SArray
and FSArray
objects inside Kokkos parallel_for
launchers.
YAKL and Kokkos fence()
operations are pretty much equivalent and can be used in either framework.
YAKL's YAKL_INLINE
is similar to Kokkos's KOKKOS_INLINE_FUNCTION
.
YAKL's YAKL_LAMBDA
is similar to the Kokkos KOKKOS_LAMBDA