2 * Copyright (C) 2019 Seungha Yang <seungha.yang@navercorp.com>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
24 #include "gstcudaloader.h"
27 GST_DEBUG_CATEGORY_EXTERN (gst_nvcodec_debug);
28 #define GST_CAT_DEFAULT gst_nvcodec_debug
31 #define CUDA_LIBNAME "libcuda.so.1"
33 #define CUDA_LIBNAME "nvcuda.dll"
36 #define LOAD_SYMBOL(name,func) G_STMT_START { \
37 if (!g_module_symbol (module, G_STRINGIFY (name), (gpointer *) &vtable->func)) { \
38 GST_ERROR ("Failed to load '%s' from %s, %s", G_STRINGIFY (name), filename, g_module_error()); \
44 typedef struct _GstNvCodecCudaVTable
48 CUresult (CUDAAPI * CuInit) (unsigned int Flags);
49 CUresult (CUDAAPI * CuGetErrorName) (CUresult error, const char **pStr);
50 CUresult (CUDAAPI * CuGetErrorString) (CUresult error, const char **pStr);
52 CUresult (CUDAAPI * CuCtxCreate) (CUcontext * pctx, unsigned int flags,
54 CUresult (CUDAAPI * CuCtxDestroy) (CUcontext ctx);
55 CUresult (CUDAAPI * CuCtxPopCurrent) (CUcontext * pctx);
56 CUresult (CUDAAPI * CuCtxPushCurrent) (CUcontext ctx);
58 CUresult (CUDAAPI * CuCtxEnablePeerAccess) (CUcontext peerContext,
60 CUresult (CUDAAPI * CuCtxDisablePeerAccess) (CUcontext peerContext);
61 CUresult (CUDAAPI * CuGraphicsMapResources) (unsigned int count,
62 CUgraphicsResource * resources, CUstream hStream);
63 CUresult (CUDAAPI * CuGraphicsUnmapResources) (unsigned int count,
64 CUgraphicsResource * resources, CUstream hStream);
66 CuGraphicsResourceSetMapFlags) (CUgraphicsResource resource,
68 CUresult (CUDAAPI * CuGraphicsSubResourceGetMappedArray) (CUarray * pArray,
69 CUgraphicsResource resource, unsigned int arrayIndex,
70 unsigned int mipLevel);
71 CUresult (CUDAAPI * CuGraphicsResourceGetMappedPointer) (CUdeviceptr *
72 pDevPtr, size_t * pSize, CUgraphicsResource resource);
74 CuGraphicsUnregisterResource) (CUgraphicsResource resource);
76 CUresult (CUDAAPI * CuMemAlloc) (CUdeviceptr * dptr, unsigned int bytesize);
77 CUresult (CUDAAPI * CuMemAllocPitch) (CUdeviceptr * dptr, size_t * pPitch,
78 size_t WidthInBytes, size_t Height, unsigned int ElementSizeBytes);
79 CUresult (CUDAAPI * CuMemAllocHost) (void **pp, unsigned int bytesize);
80 CUresult (CUDAAPI * CuMemcpy2D) (const CUDA_MEMCPY2D * pCopy);
81 CUresult (CUDAAPI * CuMemcpy2DAsync) (const CUDA_MEMCPY2D * pCopy,
84 CUresult (CUDAAPI * CuMemFree) (CUdeviceptr dptr);
85 CUresult (CUDAAPI * CuMemFreeHost) (void *p);
87 CUresult (CUDAAPI * CuStreamCreate) (CUstream * phStream,
89 CUresult (CUDAAPI * CuStreamDestroy) (CUstream hStream);
90 CUresult (CUDAAPI * CuStreamSynchronize) (CUstream hStream);
92 CUresult (CUDAAPI * CuDeviceGet) (CUdevice * device, int ordinal);
93 CUresult (CUDAAPI * CuDeviceGetCount) (int *count);
94 CUresult (CUDAAPI * CuDeviceGetName) (char *name, int len, CUdevice dev);
95 CUresult (CUDAAPI * CuDeviceGetAttribute) (int *pi,
96 CUdevice_attribute attrib, CUdevice dev);
97 CUresult (CUDAAPI * CuDeviceCanAccessPeer) (int *canAccessPeer,
98 CUdevice dev, CUdevice peerDev);
99 CUresult (CUDAAPI * CuDriverGetVersion) (int *driverVersion);
101 CUresult (CUDAAPI * CuModuleLoadData) (CUmodule * module,
103 CUresult (CUDAAPI * CuModuleUnload) (CUmodule module);
104 CUresult (CUDAAPI * CuModuleGetFunction) (CUfunction * hfunc,
105 CUmodule hmod, const char *name);
106 CUresult (CUDAAPI * CuTexObjectCreate) (CUtexObject * pTexObject,
107 const CUDA_RESOURCE_DESC * pResDesc, const CUDA_TEXTURE_DESC * pTexDesc,
108 const CUDA_RESOURCE_VIEW_DESC * pResViewDesc);
109 CUresult (CUDAAPI * CuTexObjectDestroy) (CUtexObject texObject);
110 CUresult (CUDAAPI * CuLaunchKernel) (CUfunction f, unsigned int gridDimX,
111 unsigned int gridDimY, unsigned int gridDimZ,
112 unsigned int blockDimX, unsigned int blockDimY, unsigned int blockDimZ,
113 unsigned int sharedMemBytes, CUstream hStream, void **kernelParams,
116 CUresult (CUDAAPI * CuGraphicsGLRegisterImage) (CUgraphicsResource *
117 pCudaResource, unsigned int image, unsigned int target,
119 CUresult (CUDAAPI * CuGraphicsGLRegisterBuffer) (CUgraphicsResource *
120 pCudaResource, unsigned int buffer, unsigned int Flags);
121 CUresult (CUDAAPI * CuGLGetDevices) (unsigned int *pCudaDeviceCount,
122 CUdevice * pCudaDevices, unsigned int cudaDeviceCount,
123 CUGLDeviceList deviceList);
125 CUresult (CUDAAPI * CuGraphicsD3D11RegisterResource) (CUgraphicsResource *
126 pCudaResource, gpointer pD3DResource, unsigned int Flags);
127 CUresult (CUDAAPI * CuD3D11GetDevice) (CUdevice * device,
129 CUresult (CUDAAPI * CuD3D11GetDevices) (unsigned int *pCudaDeviceCount,
130 CUdevice * pCudaDevices, unsigned int cudaDeviceCount,
131 gpointer pD3D11Device, CUD3D11DeviceList deviceList);
132 } GstNvCodecCudaVTable;
135 static GstNvCodecCudaVTable gst_cuda_vtable = { 0, };
138 gst_cuda_load_library (void)
141 const gchar *filename = CUDA_LIBNAME;
142 GstNvCodecCudaVTable *vtable;
144 if (gst_cuda_vtable.loaded)
147 module = g_module_open (filename, G_MODULE_BIND_LAZY);
148 if (module == NULL) {
149 GST_WARNING ("Could not open library %s, %s", filename, g_module_error ());
153 vtable = &gst_cuda_vtable;
156 LOAD_SYMBOL (cuInit, CuInit);
157 LOAD_SYMBOL (cuGetErrorName, CuGetErrorName);
158 LOAD_SYMBOL (cuGetErrorString, CuGetErrorString);
159 LOAD_SYMBOL (cuCtxCreate, CuCtxCreate);
160 LOAD_SYMBOL (cuCtxDestroy, CuCtxDestroy);
161 LOAD_SYMBOL (cuCtxPopCurrent, CuCtxPopCurrent);
162 LOAD_SYMBOL (cuCtxPushCurrent, CuCtxPushCurrent);
163 LOAD_SYMBOL (cuCtxEnablePeerAccess, CuCtxEnablePeerAccess);
164 LOAD_SYMBOL (cuCtxDisablePeerAccess, CuCtxDisablePeerAccess);
166 LOAD_SYMBOL (cuGraphicsMapResources, CuGraphicsMapResources);
167 LOAD_SYMBOL (cuGraphicsUnmapResources, CuGraphicsUnmapResources);
168 LOAD_SYMBOL (cuGraphicsResourceSetMapFlags, CuGraphicsResourceSetMapFlags);
169 LOAD_SYMBOL (cuGraphicsSubResourceGetMappedArray,
170 CuGraphicsSubResourceGetMappedArray);
171 LOAD_SYMBOL (cuGraphicsResourceGetMappedPointer,
172 CuGraphicsResourceGetMappedPointer);
173 LOAD_SYMBOL (cuGraphicsUnregisterResource, CuGraphicsUnregisterResource);
175 LOAD_SYMBOL (cuMemAlloc, CuMemAlloc);
176 LOAD_SYMBOL (cuMemAllocPitch, CuMemAllocPitch);
177 LOAD_SYMBOL (cuMemAllocHost, CuMemAllocHost);
178 LOAD_SYMBOL (cuMemcpy2D, CuMemcpy2D);
179 LOAD_SYMBOL (cuMemcpy2DAsync, CuMemcpy2DAsync);
181 LOAD_SYMBOL (cuMemFree, CuMemFree);
182 LOAD_SYMBOL (cuMemFreeHost, CuMemFreeHost);
184 LOAD_SYMBOL (cuStreamCreate, CuStreamCreate);
185 LOAD_SYMBOL (cuStreamDestroy, CuStreamDestroy);
186 LOAD_SYMBOL (cuStreamSynchronize, CuStreamSynchronize);
188 LOAD_SYMBOL (cuDeviceGet, CuDeviceGet);
189 LOAD_SYMBOL (cuDeviceGetCount, CuDeviceGetCount);
190 LOAD_SYMBOL (cuDeviceGetName, CuDeviceGetName);
191 LOAD_SYMBOL (cuDeviceGetAttribute, CuDeviceGetAttribute);
192 LOAD_SYMBOL (cuDeviceCanAccessPeer, CuDeviceCanAccessPeer);
194 LOAD_SYMBOL (cuDriverGetVersion, CuDriverGetVersion);
196 LOAD_SYMBOL (cuModuleLoadData, CuModuleLoadData);
197 LOAD_SYMBOL (cuModuleUnload, CuModuleUnload);
198 LOAD_SYMBOL (cuModuleGetFunction, CuModuleGetFunction);
199 LOAD_SYMBOL (cuTexObjectCreate, CuTexObjectCreate);
200 LOAD_SYMBOL (cuTexObjectDestroy, CuTexObjectDestroy);
201 LOAD_SYMBOL (cuLaunchKernel, CuLaunchKernel);
204 LOAD_SYMBOL (cuGraphicsGLRegisterImage, CuGraphicsGLRegisterImage);
205 LOAD_SYMBOL (cuGraphicsGLRegisterBuffer, CuGraphicsGLRegisterBuffer);
206 LOAD_SYMBOL (cuGLGetDevices, CuGLGetDevices);
208 #ifdef HAVE_NVCODEC_GST_D3D11
210 LOAD_SYMBOL (cuGraphicsD3D11RegisterResource,
211 CuGraphicsD3D11RegisterResource);
212 LOAD_SYMBOL (cuD3D11GetDevice, CuD3D11GetDevice);
213 LOAD_SYMBOL (cuD3D11GetDevices, CuD3D11GetDevices);
216 vtable->loaded = TRUE;
221 g_module_close (module);
227 CuInit (unsigned int Flags)
229 g_assert (gst_cuda_vtable.CuInit != NULL);
231 return gst_cuda_vtable.CuInit (Flags);
235 CuGetErrorName (CUresult error, const char **pStr)
237 g_assert (gst_cuda_vtable.CuGetErrorName != NULL);
239 return gst_cuda_vtable.CuGetErrorName (error, pStr);
243 CuGetErrorString (CUresult error, const char **pStr)
245 g_assert (gst_cuda_vtable.CuGetErrorString != NULL);
247 return gst_cuda_vtable.CuGetErrorString (error, pStr);
251 CuCtxCreate (CUcontext * pctx, unsigned int flags, CUdevice dev)
253 g_assert (gst_cuda_vtable.CuCtxCreate != NULL);
255 return gst_cuda_vtable.CuCtxCreate (pctx, flags, dev);
259 CuCtxDestroy (CUcontext ctx)
261 g_assert (gst_cuda_vtable.CuCtxDestroy != NULL);
263 return gst_cuda_vtable.CuCtxDestroy (ctx);
267 CuCtxPopCurrent (CUcontext * pctx)
269 g_assert (gst_cuda_vtable.CuCtxPopCurrent != NULL);
271 return gst_cuda_vtable.CuCtxPopCurrent (pctx);
275 CuCtxPushCurrent (CUcontext ctx)
277 g_assert (gst_cuda_vtable.CuCtxPushCurrent != NULL);
279 return gst_cuda_vtable.CuCtxPushCurrent (ctx);
283 CuCtxEnablePeerAccess (CUcontext peerContext, unsigned int Flags)
285 g_assert (gst_cuda_vtable.CuCtxEnablePeerAccess != NULL);
287 return gst_cuda_vtable.CuCtxEnablePeerAccess (peerContext, Flags);
291 CuCtxDisablePeerAccess (CUcontext peerContext)
293 g_assert (gst_cuda_vtable.CuCtxDisablePeerAccess != NULL);
295 return gst_cuda_vtable.CuCtxDisablePeerAccess (peerContext);
299 CuGraphicsMapResources (unsigned int count, CUgraphicsResource * resources,
302 g_assert (gst_cuda_vtable.CuGraphicsMapResources != NULL);
304 return gst_cuda_vtable.CuGraphicsMapResources (count, resources, hStream);
308 CuGraphicsUnmapResources (unsigned int count, CUgraphicsResource * resources,
311 g_assert (gst_cuda_vtable.CuGraphicsUnmapResources != NULL);
313 return gst_cuda_vtable.CuGraphicsUnmapResources (count, resources, hStream);
317 CuGraphicsResourceSetMapFlags (CUgraphicsResource resource, unsigned int flags)
319 g_assert (gst_cuda_vtable.CuGraphicsResourceSetMapFlags != NULL);
321 return gst_cuda_vtable.CuGraphicsResourceSetMapFlags (resource, flags);
325 CuGraphicsSubResourceGetMappedArray (CUarray * pArray,
326 CUgraphicsResource resource, unsigned int arrayIndex, unsigned int mipLevel)
328 g_assert (gst_cuda_vtable.CuGraphicsSubResourceGetMappedArray != NULL);
330 return gst_cuda_vtable.CuGraphicsSubResourceGetMappedArray (pArray, resource,
331 arrayIndex, mipLevel);
336 CuGraphicsResourceGetMappedPointer (CUdeviceptr * pDevPtr, size_t * pSize,
337 CUgraphicsResource resource)
339 g_assert (gst_cuda_vtable.CuGraphicsResourceGetMappedPointer != NULL);
341 return gst_cuda_vtable.CuGraphicsResourceGetMappedPointer (pDevPtr, pSize,
347 CuGraphicsUnregisterResource (CUgraphicsResource resource)
349 g_assert (gst_cuda_vtable.CuGraphicsUnregisterResource != NULL);
351 return gst_cuda_vtable.CuGraphicsUnregisterResource (resource);
355 CuMemAlloc (CUdeviceptr * dptr, unsigned int bytesize)
357 g_assert (gst_cuda_vtable.CuMemAlloc != NULL);
359 return gst_cuda_vtable.CuMemAlloc (dptr, bytesize);
364 CuMemAllocPitch (CUdeviceptr * dptr, size_t * pPitch, size_t WidthInBytes,
365 size_t Height, unsigned int ElementSizeBytes)
367 g_assert (gst_cuda_vtable.CuMemAllocPitch != NULL);
369 return gst_cuda_vtable.CuMemAllocPitch (dptr, pPitch, WidthInBytes, Height,
375 CuMemAllocHost (void **pp, unsigned int bytesize)
377 g_assert (gst_cuda_vtable.CuMemAllocHost != NULL);
379 return gst_cuda_vtable.CuMemAllocHost (pp, bytesize);
383 CuMemcpy2D (const CUDA_MEMCPY2D * pCopy)
385 g_assert (gst_cuda_vtable.CuMemcpy2D != NULL);
387 return gst_cuda_vtable.CuMemcpy2D (pCopy);
391 CuMemcpy2DAsync (const CUDA_MEMCPY2D * pCopy, CUstream hStream)
393 g_assert (gst_cuda_vtable.CuMemcpy2DAsync != NULL);
395 return gst_cuda_vtable.CuMemcpy2DAsync (pCopy, hStream);
399 CuMemFree (CUdeviceptr dptr)
401 g_assert (gst_cuda_vtable.CuMemFree != NULL);
403 return gst_cuda_vtable.CuMemFree (dptr);
407 CuMemFreeHost (void *p)
409 g_assert (gst_cuda_vtable.CuMemFreeHost != NULL);
411 return gst_cuda_vtable.CuMemFreeHost (p);
415 CuStreamCreate (CUstream * phStream, unsigned int Flags)
417 g_assert (gst_cuda_vtable.CuStreamCreate != NULL);
419 return gst_cuda_vtable.CuStreamCreate (phStream, Flags);
423 CuStreamDestroy (CUstream hStream)
425 g_assert (gst_cuda_vtable.CuStreamDestroy != NULL);
427 return gst_cuda_vtable.CuStreamDestroy (hStream);
431 CuStreamSynchronize (CUstream hStream)
433 g_assert (gst_cuda_vtable.CuStreamSynchronize != NULL);
435 return gst_cuda_vtable.CuStreamSynchronize (hStream);
439 CuDeviceGet (CUdevice * device, int ordinal)
441 g_assert (gst_cuda_vtable.CuDeviceGet != NULL);
443 return gst_cuda_vtable.CuDeviceGet (device, ordinal);
447 CuDeviceGetCount (int *count)
449 g_assert (gst_cuda_vtable.CuDeviceGetCount != NULL);
451 return gst_cuda_vtable.CuDeviceGetCount (count);
455 CuDeviceGetName (char *name, int len, CUdevice dev)
457 g_assert (gst_cuda_vtable.CuDeviceGetName != NULL);
459 return gst_cuda_vtable.CuDeviceGetName (name, len, dev);
463 CuDeviceGetAttribute (int *pi, CUdevice_attribute attrib, CUdevice dev)
465 g_assert (gst_cuda_vtable.CuDeviceGetAttribute != NULL);
467 return gst_cuda_vtable.CuDeviceGetAttribute (pi, attrib, dev);
471 CuDeviceCanAccessPeer (int *canAccessPeer, CUdevice dev, CUdevice peerDev)
473 g_assert (gst_cuda_vtable.CuDeviceCanAccessPeer != NULL);
475 return gst_cuda_vtable.CuDeviceCanAccessPeer (canAccessPeer, dev, peerDev);
479 CuDriverGetVersion (int *driverVersion)
481 g_assert (gst_cuda_vtable.CuDriverGetVersion != NULL);
483 return gst_cuda_vtable.CuDriverGetVersion (driverVersion);
487 CuModuleLoadData (CUmodule * module, const void *image)
489 g_assert (gst_cuda_vtable.CuModuleLoadData != NULL);
491 return gst_cuda_vtable.CuModuleLoadData (module, image);
495 CuModuleUnload (CUmodule module)
497 g_assert (gst_cuda_vtable.CuModuleUnload != NULL);
499 return gst_cuda_vtable.CuModuleUnload (module);
503 CuModuleGetFunction (CUfunction * hfunc, CUmodule hmod, const char *name)
505 g_assert (gst_cuda_vtable.CuModuleGetFunction != NULL);
507 return gst_cuda_vtable.CuModuleGetFunction (hfunc, hmod, name);
511 CuTexObjectCreate (CUtexObject * pTexObject,
512 const CUDA_RESOURCE_DESC * pResDesc, const CUDA_TEXTURE_DESC * pTexDesc,
513 const CUDA_RESOURCE_VIEW_DESC * pResViewDesc)
515 g_assert (gst_cuda_vtable.CuTexObjectCreate != NULL);
517 return gst_cuda_vtable.CuTexObjectCreate (pTexObject, pResDesc, pTexDesc,
522 CuTexObjectDestroy (CUtexObject texObject)
524 g_assert (gst_cuda_vtable.CuTexObjectDestroy != NULL);
526 return gst_cuda_vtable.CuTexObjectDestroy (texObject);
530 CuLaunchKernel (CUfunction f, unsigned int gridDimX,
531 unsigned int gridDimY, unsigned int gridDimZ,
532 unsigned int blockDimX, unsigned int blockDimY, unsigned int blockDimZ,
533 unsigned int sharedMemBytes, CUstream hStream, void **kernelParams,
536 g_assert (gst_cuda_vtable.CuLaunchKernel != NULL);
538 return gst_cuda_vtable.CuLaunchKernel (f, gridDimX, gridDimY, gridDimZ,
539 blockDimX, blockDimY, blockDimZ, sharedMemBytes, hStream, kernelParams,
545 CuGraphicsGLRegisterImage (CUgraphicsResource * pCudaResource,
546 unsigned int image, unsigned int target, unsigned int Flags)
548 g_assert (gst_cuda_vtable.CuGraphicsGLRegisterImage != NULL);
550 return gst_cuda_vtable.CuGraphicsGLRegisterImage (pCudaResource, image,
555 CuGraphicsGLRegisterBuffer (CUgraphicsResource * pCudaResource,
556 unsigned int buffer, unsigned int Flags)
558 g_assert (gst_cuda_vtable.CuGraphicsGLRegisterBuffer != NULL);
560 return gst_cuda_vtable.CuGraphicsGLRegisterBuffer (pCudaResource, buffer,
565 CuGLGetDevices (unsigned int *pCudaDeviceCount, CUdevice * pCudaDevices,
566 unsigned int cudaDeviceCount, CUGLDeviceList deviceList)
568 g_assert (gst_cuda_vtable.CuGLGetDevices != NULL);
570 return gst_cuda_vtable.CuGLGetDevices (pCudaDeviceCount, pCudaDevices,
571 cudaDeviceCount, deviceList);
576 CuGraphicsD3D11RegisterResource (CUgraphicsResource * pCudaResource,
577 gpointer pD3DResource, unsigned int Flags)
579 g_assert (gst_cuda_vtable.CuGraphicsD3D11RegisterResource != NULL);
581 return gst_cuda_vtable.CuGraphicsD3D11RegisterResource (pCudaResource,
582 pD3DResource, Flags);
586 CuD3D11GetDevice (CUdevice * device, gpointer pAdapter)
588 g_assert (gst_cuda_vtable.CuD3D11GetDevice != NULL);
590 return gst_cuda_vtable.CuD3D11GetDevice (device, pAdapter);
594 CuD3D11GetDevices (unsigned int *pCudaDeviceCount,
595 CUdevice * pCudaDevices,
596 unsigned int cudaDeviceCount,
597 gpointer pD3D11Device, CUD3D11DeviceList deviceList)
599 g_assert (gst_cuda_vtable.CuD3D11GetDevices != NULL);
601 return gst_cuda_vtable.CuD3D11GetDevices (pCudaDeviceCount, pCudaDevices,
602 cudaDeviceCount, pD3D11Device, deviceList);