GPU Porting

High performance software with FLOP heavy but parallelization workloads can benefit from using GPU hardware. It is easier to develop a project with GPU support from the beginning; however it can be impractical to restart an existing project from scratch, especially a large project with hundreds of thousands or millions of lines of code representing years or decades of development effort.

In this post, we explore different approaches to extending existing software to run on GPU hardware. There are two general families of approaches under consideration here - native support via the hardware specific language, such as CUDA, ROCm, or SYCL, and performance portability libraries, such as Kokkos or Raja.

Note: ROCm and SYCL have the ability to target different hardware rather than just AMD devices (ROCm) or Intel devices (SYCL) so in some sense they can be thought of having some capabilities in common with a performance portability library. However, that capability will not be the full focus of our discussion here, as the ability to target different hardware is not the only distinction under consideration.

We will outline some pros and cons to consider when deciding what approach to take when extending existing software to run on GPU hardware.

Native GPU Support

Hardware specific languages include CUDA, ROCm, or SYCL <https://www.khronos.org/sycl>, or SYCL. These packages allow more direct control over usage of the device and how the kernels are launched. As a drawback however, these languages are more intrusive to integrate into your code. Additionally, these languages are often paired with specific hardware, though this requirement is sometimes relaxed.

Performance Portability Libraries

Performance portability libraries include Kokkos and Raja. With these libraries, incorporating GPU capabilities is less obtrusive, and these libraries typically support a wider variety of hardware instead of only hardware from a particular manufacturer. Also, the specifics of some of the common details, such of memory management and synchronization, are handled for the users. However, these libraries typically do not offer as direct of control over the configuration of the device kernels, as a natural byproduct of their generality and flexibility.

Additionally, using one of these performance portability libraries requires both the appropriate dependency for the hardware (CUDA, ROCm, SYCL, etc) and the performance portability library. This means that the dependency stack is deeper, which adds more to configure and manage, especially for legacy software projects which may already have a heavy dependency stack.

Demo

A small demo application exploring some of the challenges to in-place modification of legacy CPU based code can be found here. This demo uses Kokkos and can be used to target any device that Kokkos (and your hardware) supports. The source code has several comments discussing common points to consider when porting legacy CPU based code to GPUs.

Metadata

Started: 11 Mar 2026

Last edited: 16 Jul 2026