My setup for SYCL development on linux. I have a minimal setup to play around and work on SYCL.
What is SYCL?
- SYCL is basically cross platform framework that enables parallel programming same code to run on different gpus and cpus. It isn’t used much but it is helpful in learning about parallel programming and gpu programming. In case you only have Intel integrated gpus this can be a good alternative.
How I installed it?
- There are a couple of ways to install and run sycl one is adaptivecpp which I haven’t used the other is Intel One Api Toolkit You can download a script that when I executed I got compiler and other stuff installed in home directory I added source env_var to ~/.bashrc to make my system simpler.
source ~/intel/oneapi/setvars.sh
I haven’t used modules but I have setup my cmake to enable modules as well this is my minimal cmake setup
cmake_minimum_required(VERSION 4.3.2)
set(CMAKE_EXPERIMENTAL_CXX_IMPORT_STD "451f2fe2-a8a2-47c3-bc32-94786d8fc91b")
project(one_api)
project(one_api LANGUAGES CXX)
set(CMAKE_CXX_MODULE_STD ON)
SET(BOOST_UT_CXX_MODULES ON)
set(CMAKE_CXX_STANDARD 26)
set(CMAKE_BUILD_WITH_INSTALL_RPATH TRUE)
add_executable(my_program main.cpp)
target_compile_features(my_program PRIVATE cxx_std_26)
target_compile_options(my_program PRIVATE -fsycl -Wno-reserved-module-identifier)
target_link_options(my_program PRIVATE -fsycl -Wno-reserved-module-identifier)
#target_sources(my_program PUBLIC FILE_SET all_my_modules TYPE CXX_MODULES FILES)
A note on code
Just to test my setup i have this code to find number of cores in gpu and cpu, it uses c++20 onwards.
#include<print>
#include<sycl/sycl.hpp>
int main() {
const sycl::device dev{sycl::gpu_selector_v};
const sycl::device host{sycl::cpu_selector_v};
auto dev_cores = dev.get_info<sycl::info::device::max_compute_units>();
auto host_cores = host.get_info<sycl::info::device::max_compute_units>();
std::println("gpu cores {}", dev_cores);
std::println("cpu cores {}", host_cores);
}
Helpful Links
Part Two
date: 2026-07-29
In part two I am reading data parallel C++ initially lets talk about an issue with parallel programming namely race condition.
Race Condition
So when two different threads access and try to modify same data there is a possible race condition which can be thought of as lack of consistency in output.
Example
Lets assume we have shared memory C = 1 thread A adds 1 and thread b adds 2 without proper synchronization it’s a possibility that the either add goes through on different runs and not both of them as expected.
Tools
Intel Inspector available with oneapi toolkit might be discussed later or interesting thing to look at.
C++ Lambdas
Anonymous functions defined in between the flow rather than proper syntax for functions or methods.
[capture_list](parameters)->return type{statements};
capture_list being the variables in surrounding environment of lambda and how them are provided = is for copy & is for reference and you can also go for individual variables. sycl captures it almost always with = by value. parameters just work like normal parameters statements is where the real juice is and all logic.
Concurrency VS Parallelism
Concurrency ➡ multiple processes doing things separately by switching context etc. Parallelism ➡ multiple processes/threads progressing at the same time altogether.
Part Three Date: 29/07/2026
Methods of running code.
- Run code anywhere device is chosen by runtime.
- Debugging code by running on host device.
- Dispatch code to gpu or another accelerator.
- Dispatch to heterogenous devices.
- Selecting specific device from a list.
Method two is most commonly used for debugging and after that step method 3-5 follow.
Method 1 Binding to any device
Queue
Abstraction on which methods are submitted to run on a specific device runtime checks for prereqs like input data and then task on queue is run.
- Can only be bound to one device
- Chosen at construction of queue
- multiple queues can bind to one device
static void binding_to_any_device() {
sycl::queue q;
std::print("Selected Device: {}", q.get_device().get_info<sycl::info::device::name>());
}
Method 2 Binding to Host Device
- For debugging
- Will surely run
- Performance not a consideration
static void bind_to_cpu_device() {
const sycl::queue q{sycl::cpu_selector_v};
std::println("Selected Device: {}", q.get_device().get_info<sycl::info::device::name>());
std::println("Device Vendor: {}", q.get_device().get_info<sycl::info::device::vendor>());
}
Method 3 Using a GPU or other accelerator
- use gpu_selector_v
- If gpu selector is used and no gpu is present runtime error
- use gpu_selector_v for this
Method 4 bind multiple devices
- bind both gpu and fpga
- replace code with fpga when available
static void using_multiple_devices() {
// cpu device
const sycl::queue cpu_queue{sycl::cpu_selector_v};
// gpu device
const sycl::queue gpu_queue{sycl::gpu_selector_v};
std::println("Selected Device: {}", cpu_queue.get_device().get_info<sycl::info::device::name>());
std::println("Selected Device: {}", gpu_queue.get_device().get_info<sycl::info::device::name>());
}
Method 5 Custom selector
-
Inherit from device_selector base class
-
overload operator ()
-
deprecated now
-
Provides different device selectors
-
Code with callables
static void custom_device_selector() {
const auto selector = [](const sycl::device &dev) -> int {
if (dev.is_gpu() && dev.get_info<sycl::info::device::vendor>().contains("Intel"))
return 100;
if (dev.is_gpu())
return 50;
return -1;
};
const sycl::queue q{selector};
std::println("Selected Device: {}", q.get_device().get_info<sycl::info::device::name>());
}
Creating Work on Device
- We submit device code for execution Examples:
- Task Graphs Defines actions to perform on one or more devices and also dependencies of tasks on each other
-
Device code is located inside the lambda inside parallel for or any other handler method similarly queue can be used to dispatch to device too.
-
Command group is submitted to the queue or anything it should only have one operation kernel launch or explicit memory operation.
-
The code will run async when DAG node dependencies have been met.
Fallback
- Fallback queue is provided not recommended use errors and catching errors for more control.