Skip to content

Commit cc0c33b

Browse files
[SYCL] Add sycl-ls utility for listing devices discovered/selected by SYCL RT (#1575)
Signed-off-by: Sergey V Maslov <[email protected]>
1 parent a61d2c7 commit cc0c33b

8 files changed

+237
-1
lines changed

sycl/CMakeLists.txt

+2
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,7 @@ add_custom_target( sycl-toolchain
232232
llvm-link
233233
llvm-objcopy
234234
sycl-post-link
235+
sycl-ls
235236
COMMENT "Building SYCL compiler toolchain..."
236237
)
237238

@@ -281,6 +282,7 @@ set( SYCL_TOOLCHAIN_DEPLOY_COMPONENTS
281282
llvm-link
282283
llvm-objcopy
283284
sycl-post-link
285+
sycl-ls
284286
clang-resource-headers
285287
opencl-headers
286288
sycl-headers
+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
// REQUIRES: gpu, cuda
2+
3+
// RUN: env SYCL_BE=PI_CUDA sycl-ls --verbose >%t.cuda.out
4+
// RUN: FileCheck %s --check-prefixes=CHECK-BUILTIN-GPU-CUDA,CHECK-CUSTOM-GPU-CUDA --input-file %t.cuda.out
5+
6+
// CHECK-BUILTIN-GPU-CUDA: gpu_selector(){{.*}}GPU :{{.*}}CUDA
7+
// CHECK-CUSTOM-GPU-CUDA: custom_selector(gpu){{.*}}GPU :{{.*}}CUDA
8+
9+
//==---- sycl-ls-gpu-cuda.cpp - SYCL test for discovered/selected devices --==//
10+
//
11+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
12+
// See https://llvm.org/LICENSE.txt for license information.
13+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
14+
//
15+
//===----------------------------------------------------------------------===//
+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// REQUIRES: gpu, opencl
2+
3+
// RUN: sycl-ls --verbose >%t.default.out
4+
// RUN: FileCheck %s --check-prefixes=CHECK-GPU-BUILTIN,CHECK-GPU-CUSTOM --input-file %t.default.out
5+
6+
// RUN: env SYCL_BE=PI_OPENCL sycl-ls --verbose >%t.opencl.out
7+
// RUN: FileCheck %s --check-prefixes=CHECK-GPU-BUILTIN,CHECK-GPU-CUSTOM --input-file %t.opencl.out
8+
9+
// CHECK-GPU-BUILTIN: gpu_selector(){{.*}}GPU : OpenCL
10+
// CHECK-GPU-CUSTOM: custom_selector(gpu){{.*}}GPU : OpenCL
11+
12+
//==-- sycl-ls-gpu-opencl.cpp - SYCL test for discovered/selected devices -===//
13+
//
14+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
15+
// See https://llvm.org/LICENSE.txt for license information.
16+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
17+
//
18+
//===----------------------------------------------------------------------===//
+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
// REQUIRES: gpu, cuda, opencl
2+
3+
// RUN: sycl-ls --verbose >%t.default.out
4+
// RUN: FileCheck %s --check-prefixes=CHECK-BUILTIN-GPU-OPENCL,CHECK-CUSTOM-GPU-OPENCL --input-file %t.default.out
5+
6+
// RUN: env SYCL_BE=PI_OPENCL sycl-ls --verbose >%t.opencl.out
7+
// RUN: FileCheck %s --check-prefixes=CHECK-BUILTIN-GPU-OPENCL,CHECK-CUSTOM-GPU-OPENCL --input-file %t.opencl.out
8+
9+
// CHECK-BUILTIN-GPU-OPENCL: gpu_selector(){{.*}}GPU : OpenCL
10+
// CHECK-CUSTOM-GPU-OPENCL: custom_selector(gpu){{.*}}GPU : OpenCL
11+
12+
// RUN: env SYCL_BE=PI_CUDA sycl-ls --verbose >%t.cuda.out
13+
// RUN: FileCheck %s --check-prefixes=CHECK-BUILTIN-GPU-CUDA,CHECK-CUSTOM-GPU-CUDA --input-file %t.cuda.out
14+
15+
// CHECK-BUILTIN-GPU-CUDA: gpu_selector(){{.*}}GPU : CUDA
16+
// CHECK-CUSTOM-GPU-CUDA: custom_selector(gpu){{.*}}GPU : CUDA
17+
18+
//==---- sycl-ls-gpu-sycl-be.cpp - SYCL test for discovered/selected devices --==//
19+
//
20+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
21+
// See https://llvm.org/LICENSE.txt for license information.
22+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
23+
//
24+
//===----------------------------------------------------------------------===//

sycl/test/plugins/sycl-ls.cpp

+11
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
// RUN: sycl-ls --verbose | grep "Device \[" | wc -l >%t.verbose.out
2+
// RUN: sycl-ls | wc -l >%t.concise.out
3+
// RUN: diff %t.verbose.out %t.concise.out
4+
5+
//==---- sycl-ls.cpp - SYCL test for consistency of sycl-ls output ---------==//
6+
//
7+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
8+
// See https://llvm.org/LICENSE.txt for license information.
9+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
10+
//
11+
//===----------------------------------------------------------------------===//

sycl/tools/CMakeLists.txt

+2-1
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,9 @@ set(CMAKE_CXX_STANDARD 11)
22
set(CMAKE_CXX_STANDARD_REQUIRED ON)
33
set(CMAKE_CXX_EXTENSIONS OFF)
44

5-
# TODO: move each tool in its own sub-directory
5+
add_subdirectory(sycl-ls)
66

7+
# TODO: move each tool in its own sub-directory
78
add_executable(get_device_count_by_type get_device_count_by_type.cpp)
89
add_dependencies(get_device_count_by_type ocl-headers ocl-icd)
910

sycl/tools/sycl-ls/CMakeLists.txt

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
add_executable(sycl-ls sycl-ls.cpp)
2+
add_dependencies(sycl-ls sycl)
3+
target_include_directories(sycl-ls PRIVATE "${sycl_inc_dir}")
4+
target_link_libraries(sycl-ls
5+
PRIVATE
6+
sycl
7+
OpenCL::Headers
8+
)

sycl/tools/sycl-ls/sycl-ls.cpp

+157
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,157 @@
1+
//==----------- sycl-ls.cpp ------------------------------------------------==//
2+
//
3+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
//
9+
// The "sycl-ls" utility lists all platforms/devices discovered by SYCL similar
10+
// to how clinfo prints this for OpenCL devices.
11+
//
12+
// There are two types of output:
13+
// concise (default) and
14+
// verbose (enabled with --verbose).
15+
//
16+
// In verbose mode it also prints, which devices would be chosen by various SYCL
17+
// device selectors.
18+
//
19+
#include <CL/sycl.hpp>
20+
21+
#include <cstdlib>
22+
#include <iostream>
23+
#include <stdlib.h>
24+
25+
using namespace cl::sycl;
26+
27+
// Controls verbose output vs. concise.
28+
bool verbose;
29+
30+
// Trivial custom selector that selects a device of the given type.
31+
class custom_selector : public device_selector {
32+
info::device_type MType;
33+
34+
public:
35+
custom_selector(info::device_type Type) : MType(Type) {}
36+
int operator()(const device &Dev) const override {
37+
return Dev.get_info<info::device::device_type>() == MType ? 1 : -1;
38+
}
39+
};
40+
41+
static void printDeviceInfo(const device &Device, const std::string &Prepend) {
42+
auto DeviceType = Device.get_info<info::device::device_type>();
43+
std::string DeviceTypeName;
44+
switch (DeviceType) {
45+
case info::device_type::cpu:
46+
DeviceTypeName = "CPU ";
47+
break;
48+
case info::device_type::gpu:
49+
DeviceTypeName = "GPU ";
50+
break;
51+
case info::device_type::host:
52+
DeviceTypeName = "HOST";
53+
break;
54+
case info::device_type::accelerator:
55+
DeviceTypeName = "ACC ";
56+
break;
57+
default:
58+
DeviceTypeName = "UNKNOWN";
59+
break;
60+
}
61+
62+
auto DeviceVersion = Device.get_info<info::device::version>();
63+
auto DeviceName = Device.get_info<info::device::name>();
64+
auto DeviceVendor = Device.get_info<info::device::vendor>();
65+
auto DeviceDriverVersion = Device.get_info<info::device::driver_version>();
66+
67+
if (verbose) {
68+
std::cout << Prepend << "Type : " << DeviceTypeName << std::endl;
69+
std::cout << Prepend << "Version : " << DeviceVersion << std::endl;
70+
std::cout << Prepend << "Name : " << DeviceName << std::endl;
71+
std::cout << Prepend << "Vendor : " << DeviceVendor << std::endl;
72+
std::cout << Prepend << "Driver : " << DeviceDriverVersion << std::endl;
73+
} else {
74+
std::cout << Prepend << DeviceTypeName << ": " << DeviceVersion << "[ "
75+
<< DeviceDriverVersion << " ]" << std::endl;
76+
}
77+
}
78+
79+
static void printSelectorChoice(const device_selector &Selector,
80+
const std::string &Prepend) {
81+
try {
82+
const auto &Dev = device(Selector);
83+
printDeviceInfo(Dev, Prepend);
84+
85+
} catch (const cl::sycl::runtime_error &Exception) {
86+
// Truncate long string so it can fit in one-line
87+
std::string What = Exception.what();
88+
if (What.length() > 50)
89+
What = What.substr(0, 50) + "...";
90+
std::cout << Prepend << What << std::endl;
91+
}
92+
}
93+
94+
int main(int argc, char **argv) {
95+
96+
// See if verbose output is requested
97+
if (argc == 1)
98+
verbose = false;
99+
else if (argc == 2 && std::string(argv[1]) == "--verbose")
100+
verbose = true;
101+
else {
102+
std::cout << "Usage: sycl-ls [--verbose]" << std::endl;
103+
return EXIT_FAILURE;
104+
}
105+
106+
auto Platforms = platform::get_platforms();
107+
if (verbose)
108+
std::cout << "Platforms: " << Platforms.size() << std::endl;
109+
110+
uint32_t PlatformNum = 0;
111+
for (const auto &Platform : Platforms) {
112+
++PlatformNum;
113+
if (verbose) {
114+
auto PlatformVersion = Platform.get_info<info::platform::version>();
115+
auto PlatformName = Platform.get_info<info::platform::name>();
116+
auto PlatformVendor = Platform.get_info<info::platform::vendor>();
117+
std::cout << "Platform [#" << PlatformNum << "]:" << std::endl;
118+
std::cout << " Version : " << PlatformVersion << std::endl;
119+
std::cout << " Name : " << PlatformName << std::endl;
120+
std::cout << " Vendor : " << PlatformVendor << std::endl;
121+
}
122+
auto Devices = Platform.get_devices();
123+
if (verbose)
124+
std::cout << " Devices : " << Devices.size() << std::endl;
125+
uint32_t DeviceNum = 0;
126+
for (const auto &Device : Devices) {
127+
++DeviceNum;
128+
if (verbose)
129+
std::cout << " Device [#" << DeviceNum << "]:" << std::endl;
130+
printDeviceInfo(Device, verbose ? " " : "");
131+
}
132+
}
133+
134+
if (!verbose) {
135+
return EXIT_SUCCESS;
136+
}
137+
138+
// Print the selectors choice in one-line always
139+
verbose = false;
140+
141+
// Print built-in device selectors choice
142+
printSelectorChoice(default_selector(), "default_selector() : ");
143+
printSelectorChoice(host_selector(), "host_selector() : ");
144+
printSelectorChoice(accelerator_selector(), "accelerator_selector() : ");
145+
printSelectorChoice(cpu_selector(), "cpu_selector() : ");
146+
printSelectorChoice(gpu_selector(), "gpu_selector() : ");
147+
148+
// Print trivial custom selectors choice
149+
printSelectorChoice(custom_selector(info::device_type::gpu),
150+
"custom_selector(gpu) : ");
151+
printSelectorChoice(custom_selector(info::device_type::cpu),
152+
"custom_selector(cpu) : ");
153+
printSelectorChoice(custom_selector(info::device_type::accelerator),
154+
"custom_selector(acc) : ");
155+
156+
return EXIT_SUCCESS;
157+
}

0 commit comments

Comments
 (0)