lavu/hwcontext_cuda: refactor context initialisation

There's enough going on here now that it should not be duplicated
between cuda_device_create and cuda_device_derive.
This commit is contained in:
Philip Langdale 2019-12-31 09:41:57 -08:00 committed by Lynne
parent 907ae87d6e
commit 7f149b0452
1 changed files with 58 additions and 72 deletions

View File

@ -336,17 +336,63 @@ error:
return ret; return ret;
} }
static int cuda_context_init(AVHWDeviceContext *device_ctx, int flags) {
AVCUDADeviceContext *hwctx = device_ctx->hwctx;
CudaFunctions *cu;
CUcontext dummy;
int ret, dev_active = 0;
unsigned int dev_flags = 0;
const unsigned int desired_flags = CU_CTX_SCHED_BLOCKING_SYNC;
cu = hwctx->internal->cuda_dl;
hwctx->internal->flags = flags;
if (flags & AV_CUDA_USE_PRIMARY_CONTEXT) {
ret = CHECK_CU(cu->cuDevicePrimaryCtxGetState(hwctx->internal->cuda_device,
&dev_flags, &dev_active));
if (ret < 0)
return ret;
if (dev_active && dev_flags != desired_flags) {
av_log(device_ctx, AV_LOG_ERROR, "Primary context already active with incompatible flags.\n");
return AVERROR(ENOTSUP);
} else if (dev_flags != desired_flags) {
ret = CHECK_CU(cu->cuDevicePrimaryCtxSetFlags(hwctx->internal->cuda_device,
desired_flags));
if (ret < 0)
return ret;
}
ret = CHECK_CU(cu->cuDevicePrimaryCtxRetain(&hwctx->cuda_ctx,
hwctx->internal->cuda_device));
if (ret < 0)
return ret;
} else {
ret = CHECK_CU(cu->cuCtxCreate(&hwctx->cuda_ctx, desired_flags,
hwctx->internal->cuda_device));
if (ret < 0)
return ret;
CHECK_CU(cu->cuCtxPopCurrent(&dummy));
}
hwctx->internal->is_allocated = 1;
// Setting stream to NULL will make functions automatically use the default CUstream
hwctx->stream = NULL;
return 0;
}
static int cuda_device_create(AVHWDeviceContext *device_ctx, static int cuda_device_create(AVHWDeviceContext *device_ctx,
const char *device, const char *device,
AVDictionary *opts, int flags) AVDictionary *opts, int flags)
{ {
AVCUDADeviceContext *hwctx = device_ctx->hwctx; AVCUDADeviceContext *hwctx = device_ctx->hwctx;
CudaFunctions *cu; CudaFunctions *cu;
CUcontext dummy; int ret, device_idx = 0;
int ret, dev_active = 0, device_idx = 0;
unsigned int dev_flags = 0;
const unsigned int desired_flags = CU_CTX_SCHED_BLOCKING_SYNC;
if (device) if (device)
device_idx = strtol(device, NULL, 0); device_idx = strtol(device, NULL, 0);
@ -364,37 +410,9 @@ static int cuda_device_create(AVHWDeviceContext *device_ctx,
if (ret < 0) if (ret < 0)
goto error; goto error;
hwctx->internal->flags = flags; ret = cuda_context_init(device_ctx, flags);
if (ret < 0)
if (flags & AV_CUDA_USE_PRIMARY_CONTEXT) { goto error;
ret = CHECK_CU(cu->cuDevicePrimaryCtxGetState(hwctx->internal->cuda_device, &dev_flags, &dev_active));
if (ret < 0)
goto error;
if (dev_active && dev_flags != desired_flags) {
av_log(device_ctx, AV_LOG_ERROR, "Primary context already active with incompatible flags.\n");
goto error;
} else if (dev_flags != desired_flags) {
ret = CHECK_CU(cu->cuDevicePrimaryCtxSetFlags(hwctx->internal->cuda_device, desired_flags));
if (ret < 0)
goto error;
}
ret = CHECK_CU(cu->cuDevicePrimaryCtxRetain(&hwctx->cuda_ctx, hwctx->internal->cuda_device));
if (ret < 0)
goto error;
} else {
ret = CHECK_CU(cu->cuCtxCreate(&hwctx->cuda_ctx, desired_flags, hwctx->internal->cuda_device));
if (ret < 0)
goto error;
CHECK_CU(cu->cuCtxPopCurrent(&dummy));
}
hwctx->internal->is_allocated = 1;
// Setting stream to NULL will make functions automatically use the default CUstream
hwctx->stream = NULL;
return 0; return 0;
@ -409,11 +427,7 @@ static int cuda_device_derive(AVHWDeviceContext *device_ctx,
AVCUDADeviceContext *hwctx = device_ctx->hwctx; AVCUDADeviceContext *hwctx = device_ctx->hwctx;
CudaFunctions *cu; CudaFunctions *cu;
const char *src_uuid = NULL; const char *src_uuid = NULL;
CUcontext dummy; int ret, i, device_count;
int ret, i, device_count, dev_active = 0;
unsigned int dev_flags = 0;
const unsigned int desired_flags = CU_CTX_SCHED_BLOCKING_SYNC;
#if CONFIG_VULKAN #if CONFIG_VULKAN
VkPhysicalDeviceIDProperties vk_idp = { VkPhysicalDeviceIDProperties vk_idp = {
@ -481,37 +495,9 @@ static int cuda_device_derive(AVHWDeviceContext *device_ctx,
goto error; goto error;
} }
hwctx->internal->flags = flags; ret = cuda_context_init(device_ctx, flags);
if (ret < 0)
if (flags & AV_CUDA_USE_PRIMARY_CONTEXT) { goto error;
ret = CHECK_CU(cu->cuDevicePrimaryCtxGetState(hwctx->internal->cuda_device, &dev_flags, &dev_active));
if (ret < 0)
goto error;
if (dev_active && dev_flags != desired_flags) {
av_log(device_ctx, AV_LOG_ERROR, "Primary context already active with incompatible flags.\n");
goto error;
} else if (dev_flags != desired_flags) {
ret = CHECK_CU(cu->cuDevicePrimaryCtxSetFlags(hwctx->internal->cuda_device, desired_flags));
if (ret < 0)
goto error;
}
ret = CHECK_CU(cu->cuDevicePrimaryCtxRetain(&hwctx->cuda_ctx, hwctx->internal->cuda_device));
if (ret < 0)
goto error;
} else {
ret = CHECK_CU(cu->cuCtxCreate(&hwctx->cuda_ctx, desired_flags, hwctx->internal->cuda_device));
if (ret < 0)
goto error;
CHECK_CU(cu->cuCtxPopCurrent(&dummy));
}
hwctx->internal->is_allocated = 1;
// Setting stream to NULL will make functions automatically use the default CUstream
hwctx->stream = NULL;
return 0; return 0;