cudaGraphicsGLRegisterBuffer returns cudaErrorOperatingSystem when called from a DLL

I’m trying to make a DLL using cuda and openGL to create on screen rendering DLL. I have been using the simpleGL sample. the sample is working completely fine but when I’m trying to implement it inside my DLL I get cudaErrorOperatingSystem from cudaGraphicsGLRegisterBuffer function which is being called in kernal.cu. I am using visual studio 2022 on a windows 11 operating system and cuda 12.0.

CR.cpp

#define GLEW_STATIC
#include "GL/glew.h"
#include "GLFW/glfw3.h"


#include "CR.h"
#include "pch.h"
#include "Kernal.h"

#include <string>



CR::CR(){}
CR::~CR(){}

CR_ERROR CR::createWindow(unsigned int x, unsigned int y, const char* title){
    maxX = x; maxY = y;

    if (glfwInit() != GLFW_TRUE)
        return CR_WINDOW_INIT_FAILED;

    glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
    glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
    glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);

    wnd = (void*)glfwCreateWindow(x, y, title, nullptr, nullptr);
    if ((GLFWwindow*)wnd == NULL)
        return CR_WINDOW_INIT_FAILED;

    glfwMakeContextCurrent((GLFWwindow*)wnd);

    if (glewInit() != GLEW_OK)
        return CR_WINDOW_INIT_FAILED;
    
    glClearColor(1,1,1,1);

    glGenVertexArrays(1,&vao);
    glBindVertexArray(vao);

    glGenBuffers(1, &vbo);
    glBindBuffer(GL_ARRAY_BUFFER, vbo);

    size_t size = x * y * 4 * sizeof(float);
    glBufferData(GL_ARRAY_BUFFER, size, 0, GL_DYNAMIC_DRAW);
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
    glEnableVertexAttribArray(0);
    k = (void*)new Kernal(&vbo);
    return CR_OK;
}

void CR::display() {
    while (!glfwWindowShouldClose((GLFWwindow*)wnd))
    {
        /* Render here */
        glClear(GL_COLOR_BUFFER_BIT);
        ((Kernal*)k)->runCuda(maxX,maxY);
        /* Swap front and back buffers */
        glfwSwapBuffers((GLFWwindow*)wnd);

        /* Poll for and process events */
        glfwPollEvents();
    }
}

CR.h:

#pragma once

#ifdef CR_EXPORT
#define CR_API __declspec(dllexport)
#else
#define CR_API __declspec(dllimport)

#endif 

enum CR_ERROR {
    CR_OK,
    CR_WINDOW_INIT_FAILED,
};

class CR_API CR {
public:
    CR();
    ~CR();

    CR_ERROR createWindow(unsigned int x, unsigned int y, const char* title);
    void display();
private:
    unsigned int maxX, maxY;
    unsigned int vbo, vao;
    void* wnd;
    void* k;
};




kernal.cu:

#include "kernal.h"

#include <string>

#define checkError(err) checkForCudaErrors(err,__LINE__)

void checkForCudaErrors(cudaError_t err,int line) {
    if (err != cudaSuccess) {
        std::string error = cudaGetErrorString(err);
        error += " on line: ";
        error += std::to_string(line);
        MessageBoxExA(NULL,error.c_str(), NULL, MB_OK | MB_ICONERROR, MAKELANGID(LANG_NEUTRAL, SUBLANG_NEUTRAL));
    }
}

__global__ void drawCircle(float3* pos, size_t size, int x, int y, int r, int maxX, int maxY) {
    for (int i = blockDim.x * blockIdx.x + threadIdx.x; i < maxX; i += blockDim.x * gridDim.x) {
        for (int j = blockDim.y * blockIdx.y + threadIdx.y; j < maxY; j += blockDim.y * gridDim.y) {
            if (x * x + y * y < r * r)
                pos[maxX * y + x] = make_float3(1, 0, 0);
        }
    }
}

void Kernal::drawCircleCaller(unsigned int x, unsigned int y, unsigned int r, unsigned int maxX, unsigned int maxY) {
    dim3 threads(16, 16);
    dim3 blocks(maxX / 16 + 1, maxY / 16 + 1);
    drawCircle << < blocks, threads >> > (pos,size, x, y, r, maxX, maxY);
    checkError(cudaDeviceSynchronize());
    checkError(cudaGetLastError());

}

Kernal::Kernal(unsigned int* vbo) : vbo{ vbo } {
    checkError(cudaGraphicsGLRegisterBuffer(&vboResource, *vbo, cudaGraphicsRegisterFlagsNone));
}

void Kernal::runCuda(unsigned int maxX, unsigned int maxY){
    checkError(cudaGraphicsMapResources(1, &vboResource, 0));
    checkError(cudaGraphicsResourceGetMappedPointer((void**)&pos, &size, vboResource));
    drawCircleCaller(100, 100, 50, maxX, maxY);
    cudaGraphicsUnmapResources(1, &vboResource, 0);
}

I tried using cuda 11.7 which I have installed but the error still occurs.

Hi @nivrazon, welcome to the NVIDIA developer forums!

I think to figure out the best way to correctly build and link a CUDA app into a DLL, th eCUDA programming forums will be more helpful to you.

I hope you don’t mind me moving your post over.

Thanks!

1 Like