Vulkan specification 을 보다가 보면 "opaque" 라는 표현이 자주 나옵니다.


Command pools are opaque objects that command buffer memory is allocated from, and which allow the implementation to amortize the cost of resource creation across multiple command buffers.


- 출처 : 5.2. Command Pools, Vulkan 1.1.83 Specification.


이게 무슨 의미인지 궁금해서 찾아 보니 Wikipedia 에 "opaque data type" 이라는 개념이 있었습니다.


컴퓨터 과학에서 opaque data type 은 인터페이스에서 그것의 concrete data structure 가 정의되지 않은 data type 입니다. 이는 정보 은닉( information hiding )을 강화하는데, 그것의 값들이, 그 알 수 없는 정보에 대한 접근을 허용하는, 서브루틴을 호출함으로써만 조작될 수 있기 때문입니다.


- 출처 : Opaque data type, Wikipedia.


"Opaque" 가 "불투명한" 혹은 "이해하기 힘든" 라는 뜻을 가지고 있기 때문에 말이 되는 표현인 것 같습니다. "concrete data structure" 라는 것은 "abstract data structure" 와 대칭되는 개념인 것 같더군요.


C/C++ 을 사용한지 15 년도 넘었는데 이런 기본적인 개념도 제대로 이해하고 있지 않다니 자괴감이 드네요. 어쨌든 C++ 로 치면 "abstract data type" 이라는 것은 interface( abstract class ) 이고 "concrete data type" 은 실제 class 라고 생각하시면 됩니다.


Vulkan 에서 특정 object 들에 대한 정의를 찾아 가면 다음과 같은 매크로들을 볼 수 있습니다. VK_DEFINE_HANDLE 은 dispatchable object 를 의미하고 VK_DEFINE_NON_DISPATCHABLE_HANDLE 은 non-dispatchable object 를 의미합니다. 여기에 대한 설명은 이 문서의 주제를 벗어나므로 여기에서 구체적인 언급은 하지 않겠습니다. 나중에 따로 다루도록 하겠습니다.



어쨌든 이 매크로의 정의를 보면 다음과 같습니다.



해당 type 에 대한 구체적인 정의는 없고 단순히 pointer 를 선언하고 있을 뿐입니다. 실제 내용은 라이브러리를 구현하는 측에서 채우게 되는 것이죠. 처음에는 이 선언이 매우 당황스러웠는데 opaque object 를 구현하기 위한 선언이라고 생각하니 이해가 가는군요.


같은 이름만 가지고 있다면 구현측에서 내부에 어떤 내용을 채워도 상관이 없다는 것입니다. Vulkan 에서는 object 생성시에 vkCreateXXX() 메서드를 호출하고 필요한 정보를 VkXXXCreateInfo 라는 구조체를 통해서 전달하게 하고 있습니다. 위에서 설명하듯이 구조체 내부 구현은 알 수 없지만 특정 메서드를 통해서 접근할 수 있도록 하고 있는 것입니다.


보시면 알겠지만 전부 pointer 형으로 선언되어 있습니다. 그래서 가끔 이러한 type 을 선언할 때 기본이 type 이 pointer 형이라는 것을 까먹는 경우가 많은데, Vulkan 을 사용할 때 주의해야 할 점 중에 하나입니다.

+ Recent posts