2016-08-11 5 views

답변

3

NVIDIA는 OpenGL에서 VkImage을 렌더링 할 수있는 NV_draw_vulkan_image라는 OpenGL 확장을 만들었습니다. Vulkan 세마포어 등과 상호 작용하기위한 메커니즘도 있습니다.

그러나 모든 Vulkan 레이어를 우회해야합니다. 레이어가 디스 패칭 할 수없는 핸들을 수정할 수 있고 OpenGL 확장이 수정에 대해 알지 못하기 때문입니다. 그렇게하기 위해 권장되는 방법은 모든 Vulkan 기능에 glGetVkProcAddrNV을 사용하는 것입니다.

또한 Vulkan 레이어를 사용하는 모든 디버깅에 액세스 할 수 없음을 의미합니다.

+0

물론 CPU쪽에 복사 한 다음 다른 API로 업로드하는 사기성있는 방법은 제외됩니다. – krOoze

+0

이 답변은 오래되었습니다. nVidia는 OpenGL interop 확장을 발표했습니다. 그들은 Vulkan Semaphor를 기다리거나 신호를 보내고, Vulkan fence 신호를 보내고, 현재 바운드 된 draw framebuffer에 Vulkan 이미지를 그릴 수 있습니다. 여기에 예제 앱을 만들었습니다. https://github.com/jherico/Vulkan/blob/cpp/examples/windows/glinterop.cpp – Jherico

+0

@Jherico : [This] (https://www.khronos.org/) registry/vulkan /)은 공식 Vulkan 확장 레지스트리입니다. [This] (https://www.opengl.org/registry/)는 공식 OpenGL 확장 레지스트리입니다. 그 중 하나가 당신이 토론하고있는 연장을 가질 때까지, 나는 내 진술에 편안함을 느낀다. –

0

SIGGRAPH 2016에서 더 최근의 정보 slide deck이 있습니다. 슬라이드 63-65는 Vulkan 이미지를 OpenGL 백 버퍼에 블릿하는 방법을 설명합니다. 제 견해로 Vulkan 드라이버가 libGL.so (Linux)에 포함되어 있기 때문에 NVIDIA가이를 지원하는 것이 꽤 쉽습니다. 따라서 Vulkan 이미지 핸들을 운전자의 GL쪽에 제공하는 것이 그리 힘들지 않았을 수도 있고 유용 할 수도 있습니다.

또 다른 대답은 공식 등록 된 다중 공급 업체 interop 확장이 아직 없음을 지적했습니다. 이 접근 방식은 NVIDIA에서 작동합니다.

+0

NV_draw_vulkan_image가 등록되지 않은 확장 프로그램 * 인 것 같습니다. 독점적 인 확장 기능과 OpenGL 레지스트리에 제대로 등록되지 않은 확장 기능의 차이점이 있습니다. 후자는 모든 확장 기능이 필요합니다. 그것은 모든 OpenGL 함수의 gl.xml 레지스트리에도 없으므로 OpenGL 로더를 사용하여 함수 포인터를로드 할 수 없습니다. 이것은 NVIDIA의 더러운 수영장처럼 보입니다. –

1

예, 이면이면 Vulkan 구현과 OpenGL 구현에 둘 다 적절한 확장명을 사용할 수 있습니다. VULKAN의 초기 릴리스 작업에서 OpenGL과 외부 VULKAN에 대한 Memory/Fence/Sempahore 확장에 대한 External Objects 확장의 결과로,이 거기 해본 적이 있기 때문에

.

확장의 Vulkan 쪽에서는 결과 개체를 내보낼 수 있도록 표시하면서 메모리를 할당하고, 세마포 또는 펜스를 만들 수 있습니다. 해당 GL 확장을 사용하면 개체를 가져 와서 울타리를 기다리고 신호를 보내고 세마포어를 기다리거나 OpenGL 텍스처를 복원하기 위해 Vulkan 할당 메모리를 사용할 수있는 새로운 GL 명령을 사용하여 개체를 조작 할 수 있습니다. OpenGL 프레임 버퍼에서 이러한 텍스처를 사용하면 원하는대로 렌더링하고 Vulkan에서 렌더링 된 결과를 사용할 수 있습니다.

당신은 당신이 할 수있는 이미지에 대한 메모리를 할당 할 때 내가는 VULKAN 측면에서, 몇 가지 예제 코드 예를 들어 here

의 개발에 노력했습니다 ...

vk::Image image; 
... // create the image as normal 
vk::MemoryRequirements memReqs = device.getImageMemoryRequirements(image); 
vk::MemoryAllocateInfo memAllocInfo; 
vk::ExportMemoryAllocateInfo exportAllocInfo{ 
    vk::ExternalMemoryHandleTypeFlagBits::eOpaqueWin32 
}; 
memAllocInfo.pNext = &exportAllocInfo; 
memAllocInfo.allocationSize = memReqs.size; 
memAllocInfo.memoryTypeIndex = context.getMemoryType(
    memReqs.memoryTypeBits, vk::MemoryPropertyFlagBits::eDeviceLocal); 
vk::DeviceMemory memory; 
memory = device.allocateMemory(memAllocInfo); 
device.bindImageMemory(image, memory, 0); 
HANDLE sharedMemoryHandle = device.getMemoryWin32HandleKHR({ 
    texture.memory, vk::ExternalMemoryHandleTypeFlagBits::eOpaqueWin32 
}); 

이것은 C++ 인터페이스를 사용하며 확장 기능의 Win32 변형을 사용하고 있습니다. Posix 플랫폼의 경우 WIN32 핸들 대신 파일 설명자를 가져 오는 대체 방법이 있습니다.

sharedMemoryHandle은 실제 할당 크기와 함께 OpenGL에 전달해야하는 값입니다. GL 측에서 다음 작업을 수행 할 수 있습니다.

// These values should be populated by the vulkan code 
HANDLE sharedMemoryHandle; 
GLuint64 sharedMemorySize; 

// Create a 'memory object' in OpenGL, and associate it with the memory 
// allocated in vulkan 
GLuint mem; 
glCreateMemoryObjectsEXT(1, mem); 
glImportMemoryWin32HandleEXT(mem, sharedMemorySize, 
    GL_HANDLE_TYPE_OPAQUE_WIN32_EXT, sharedMemoryHandle); 

// Having created the memory object we can now create a texture and use 
// the memory object for backing it 
glCreateTextures(GL_TEXTURE_2D, 1, &color); 
// The internalFormat here should correspond to the format of 
// the Vulkan image. Similarly, the w & h values should correspond to 
// the extent of the Vulkan image 
glTextureStorageMem2DEXT(color, 1, GL_RGBA8, w, h, mem, 0); 
관련 문제