Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Get device capability #734

Merged
merged 7 commits into from
Nov 20, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .Rbuildignore
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ tools/torchgen/.Rbuildignore
# ^vignettes/using-autograd\.Rmd

# uncomment below for CRAN submission
^inst/deps/.*
#^inst/deps/.*
^doc$
^Meta$
^vignettes/rsconnect*
Expand Down
1 change: 1 addition & 0 deletions NAMESPACE
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@ export(backends_openmp_is_available)
export(contrib_sort_vertices)
export(cuda_current_device)
export(cuda_device_count)
export(cuda_get_device_capability)
export(cuda_is_available)
export(dataloader)
export(dataloader_make_iter)
Expand Down
4 changes: 4 additions & 0 deletions R/RcppExports.R
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,10 @@ cpp_cuda_current_device <- function() {
.Call('_torch_cpp_cuda_current_device', PACKAGE = 'torchpkg')
}

cpp_cuda_get_device_capability <- function(device) {
.Call('_torch_cpp_cuda_get_device_capability', PACKAGE = 'torchpkg', device)
}

cpp_device_type_to_string <- function(device) {
.Call('_torch_cpp_device_type_to_string', PACKAGE = 'torchpkg', device)
}
Expand Down
14 changes: 14 additions & 0 deletions R/cuda.R
Original file line number Diff line number Diff line change
Expand Up @@ -17,4 +17,18 @@ cuda_current_device <- function() {
#' @export
cuda_device_count <- function() {
cpp_cuda_device_count()
}

#' Returns the major and minor CUDA capability of `device`
#'
#' @param device Integer value of the CUDA device to return capabilities of.
#'
#' @export
cuda_get_device_capability <- function(device = cuda_current_device()) {
if(device < 0 | device >= cuda_device_count()) {
stop(paste("device must be an integer between 0 and the number of devices minus 1"))
}
res <- as.integer(cpp_cuda_get_device_capability(device))
names(res) <- c("Major", "Minor")
res
}
3 changes: 2 additions & 1 deletion lantern/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -129,7 +129,8 @@ if(DEFINED ENV{CUDA})
src/Contrib/SortVertices/sort_vert_kernel.cu
src/Contrib/SortVertices/sort_vert.cpp
)


set_source_files_properties(src/Cuda.cpp PROPERTIES COMPILE_DEFINITIONS __NVCC__)
cuda_add_library(lantern SHARED ${LANTERN_SRC})
else()
set(LANTERN_SRC
Expand Down
10 changes: 10 additions & 0 deletions lantern/include/lantern/lantern.h
Original file line number Diff line number Diff line change
Expand Up @@ -2163,6 +2163,15 @@ HOST_API void* lantern_optional_tensor_value (void* x)
return ret;
}

LANTERN_API void* (LANTERN_PTR _lantern_cuda_get_device_capability) (int64_t device);
HOST_API void* lantern_cuda_get_device_capability (int64_t device)
{
LANTERN_CHECK_LOADED
void* ret = _lantern_cuda_get_device_capability(device);
LANTERN_HOST_HANDLER;
return ret;
}

/* Autogen Headers -- Start */
LANTERN_API void* (LANTERN_PTR _lantern__cast_byte_tensor_bool)(void* self, void* non_blocking);
HOST_API void* lantern__cast_byte_tensor_bool(void* self, void* non_blocking) { LANTERN_CHECK_LOADED void* ret = _lantern__cast_byte_tensor_bool(self, non_blocking); LANTERN_HOST_HANDLER return ret; }
Expand Down Expand Up @@ -7749,6 +7758,7 @@ LOAD_SYMBOL(_lantern_OptionalTensorList_size);
LOAD_SYMBOL(_lantern_OptionalTensorList_at);
LOAD_SYMBOL(_lantern_OptionalTensorList_at_is_null);
LOAD_SYMBOL(_lantern_optional_tensor_value);
LOAD_SYMBOL(_lantern_cuda_get_device_capability);
/* Autogen Symbols -- Start */
LOAD_SYMBOL(_lantern__cast_byte_tensor_bool)
LOAD_SYMBOL(_lantern__cast_char_tensor_bool)
Expand Down
17 changes: 16 additions & 1 deletion lantern/src/Cuda.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@
#define LANTERN_BUILD

#include "lantern/lantern.h"

#ifdef __NVCC__
#include <ATen/cuda/CUDAContext.h>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You will need to wrap this around something like #ifdef __CUDACC__ to not include this header when CUDA is not available.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, good point. I only tested this on cuda compiled torch previously, and I didn't think about this. This makes perfect sense. Done.

#endif
#include <torch/torch.h>

#include "utils.hpp"
Expand Down Expand Up @@ -35,3 +37,16 @@ void _lantern_cuda_show_config()
std::cout << at::detail::getCUDAHooks().showConfig() << std::endl;
LANTERN_FUNCTION_END_VOID
}

void* _lantern_cuda_get_device_capability(int64_t device)
{
LANTERN_FUNCTION_START
#ifdef __NVCC__
cudaDeviceProp * devprop = at::cuda::getDeviceProperties(device);
std::vector<int64_t> cap = {devprop->major, devprop->minor};
return (void*) new LanternObject<std::vector<int64_t>>(cap);
#else
throw std::runtime_error("`cuda_get_device` is only supported on CUDA runtimes.");
#endif
LANTERN_FUNCTION_END
}
14 changes: 14 additions & 0 deletions man/cuda_get_device_capability.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

12 changes: 12 additions & 0 deletions src/RcppExports.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -478,6 +478,17 @@ BEGIN_RCPP
return rcpp_result_gen;
END_RCPP
}
// cpp_cuda_get_device_capability
XPtrTorchvector_int64_t cpp_cuda_get_device_capability(int64_t device);
RcppExport SEXP _torch_cpp_cuda_get_device_capability(SEXP deviceSEXP) {
BEGIN_RCPP
Rcpp::RObject rcpp_result_gen;
Rcpp::RNGScope rcpp_rngScope_gen;
Rcpp::traits::input_parameter< int64_t >::type device(deviceSEXP);
rcpp_result_gen = Rcpp::wrap(cpp_cuda_get_device_capability(device));
return rcpp_result_gen;
END_RCPP
}
// cpp_device_type_to_string
std::string cpp_device_type_to_string(Rcpp::XPtr<XPtrTorchDevice> device);
RcppExport SEXP _torch_cpp_device_type_to_string(SEXP deviceSEXP) {
Expand Down Expand Up @@ -35172,6 +35183,7 @@ static const R_CallMethodDef CallEntries[] = {
{"_torch_cpp_cuda_is_available", (DL_FUNC) &_torch_cpp_cuda_is_available, 0},
{"_torch_cpp_cuda_device_count", (DL_FUNC) &_torch_cpp_cuda_device_count, 0},
{"_torch_cpp_cuda_current_device", (DL_FUNC) &_torch_cpp_cuda_current_device, 0},
{"_torch_cpp_cuda_get_device_capability", (DL_FUNC) &_torch_cpp_cuda_get_device_capability, 1},
{"_torch_cpp_device_type_to_string", (DL_FUNC) &_torch_cpp_device_type_to_string, 1},
{"_torch_cpp_device_index_to_int", (DL_FUNC) &_torch_cpp_device_index_to_int, 1},
{"_torch_cpp_torch_device", (DL_FUNC) &_torch_cpp_torch_device, 2},
Expand Down
5 changes: 5 additions & 0 deletions src/cuda.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,3 +15,8 @@ int cpp_cuda_device_count () {
int64_t cpp_cuda_current_device() {
return lantern_cuda_current_device();
}

// [[Rcpp::export]]
XPtrTorchvector_int64_t cpp_cuda_get_device_capability(int64_t device) {
return lantern_cuda_get_device_capability(device);
}
10 changes: 10 additions & 0 deletions src/lantern/lantern.h
Original file line number Diff line number Diff line change
Expand Up @@ -2163,6 +2163,15 @@ HOST_API void* lantern_optional_tensor_value (void* x)
return ret;
}

LANTERN_API void* (LANTERN_PTR _lantern_cuda_get_device_capability) (int64_t device);
HOST_API void* lantern_cuda_get_device_capability (int64_t device)
{
LANTERN_CHECK_LOADED
void* ret = _lantern_cuda_get_device_capability(device);
LANTERN_HOST_HANDLER;
return ret;
}

/* Autogen Headers -- Start */
LANTERN_API void* (LANTERN_PTR _lantern__cast_byte_tensor_bool)(void* self, void* non_blocking);
HOST_API void* lantern__cast_byte_tensor_bool(void* self, void* non_blocking) { LANTERN_CHECK_LOADED void* ret = _lantern__cast_byte_tensor_bool(self, non_blocking); LANTERN_HOST_HANDLER return ret; }
Expand Down Expand Up @@ -7749,6 +7758,7 @@ LOAD_SYMBOL(_lantern_OptionalTensorList_size);
LOAD_SYMBOL(_lantern_OptionalTensorList_at);
LOAD_SYMBOL(_lantern_OptionalTensorList_at_is_null);
LOAD_SYMBOL(_lantern_optional_tensor_value);
LOAD_SYMBOL(_lantern_cuda_get_device_capability);
/* Autogen Symbols -- Start */
LOAD_SYMBOL(_lantern__cast_byte_tensor_bool)
LOAD_SYMBOL(_lantern__cast_char_tensor_bool)
Expand Down
5 changes: 5 additions & 0 deletions tests/testthat/test-cuda.R
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,11 @@ test_that("cuda", {
expect_true(cuda_device_count() > 0)
expect_true(cuda_current_device() >= 0)
expect_true(cuda_is_available())

capability <- cuda_get_device_capability(cuda_current_device())
expect_type(capability, "integer")
expect_length(capability, 2)
expect_error(cuda_get_device_capability(cuda_device_count() + 1), "device must be an integer between 0 and")
})

test_that("cuda tensors", {
Expand Down