Я, похоже, наткнулся на проблему, связанную с программированием DirectX 12.0, и никакие исследования пока не дали понимания проблемы. Поэтому мне оставлено, чтобы найти проблему самостоятельно, за исключением того, что пока не представляется ощутимым решением.GetCPUDescriptorHandleForHeapStart повреждение стека
Чтобы сообщить вам, я программирование с использованием C (не C++) и, как видно, заголовочные файлы DirectX 12 при условии, сделать поддержки C, наряду с C++, хотя проблема, которую я столкнулся странно, что он, кажется, плохо спроектированный для C, вероятно, из-за того, что не многие люди больше программируют сложные (особенно объектно-ориентированные) приложения на этом языке.
Это моя проблема: у меня есть здесь, в моей процедуре D3D12 устройства инициализации следующий блок кода:
/* Get a handle to the memory location in the render target
view heap to identify where the render target views will be
located for the two back buffers */
hRTV = pThis->pRTVHeap->lpVtbl->GetCPUDescriptorHandleForHeapStart(pThis->pRTVHeap);
Где hRTV означает ' Ручка для Render Target View' (D3D12_CPU_DESCRIPTOR_HANDLE) и pRTVHeap означает ' Pointer в Render Target Просмотр Heap' (ID3D12DescriptorHeap).
Здесь C++ эквивалент - это работает отлично:
/* Get a handle to the memory location in the render target
view heap to identify where the render target views will be
located for the two back buffers */
hRTV = this->pRTVHeap->GetCPUDescriptorHandleForHeapStart();
Там нет ошибки времени компиляции присутствует, но во время выполнения вызова этого метода (GetCPUDescriptorHandleForHeapStart) в C вызывает искажение стека (ESP перекос по 4 байта).
Осмотрел разборку для метода и сделал к сведению RET (возврат) инструкция:
50290030 mov edi,edi
50290032 push ebp
50290033 mov ebp,esp
50290035 mov ecx,dword ptr [ebp+8]
50290038 mov eax,dword ptr [ecx+2Ch]
5029003B cmp dword ptr [eax],2
5029003E jne 5029004A
50290040 mov eax,dword ptr [ebp+0Ch]
50290043 mov ecx,dword ptr [ecx+28h]
50290046 mov dword ptr [eax],ecx
50290048 jmp 50290055
5029004A push dword ptr [ebp+0Ch]
5029004D call 5029005E
50290052 mov eax,dword ptr [ebp+0Ch]
50290055 pop ebp
50290056 ret 8
Для тех, кто знаком с собранием, или в противном случае __stdcall вызова условность COM (Component Object Model) объекты , этот «указатель», переданный в стек, является первым параметром (и в этом случае является также единственным параметром) метода, так что COM-объект может получить доступ к своим собственным данным.
Следующий фрагмент кода (также показан в конце фрагмента кода выше) вызывает мое замешательство, и это справедливо, когда среда выполнения выдает «откалибрована ESP» ошибка:
ret 8
только один параметр является в этом случае, который является «этим» указателем. Размер указателя (в 32-битной системе - моя целевая архитектура на данный момент - x86) - 4 байта (32 бита), так почему вызывающая сторона очищает 8 байтов в стеке?
Могу ли я назвать это ошибкой? Необходимо ли информировать Microsoft об этой проблеме? Я ошибаюсь? Это глупая ошибка с моей стороны?
Спасибо за ваше время, и я надеюсь, что кто-нибудь, у кого больше знаний, чем я, может рассказать мне об этом, но, пожалуйста, не предлагайте, чтобы решение заключалось в написании на C++ вместо C. Я уже рассмотрел это и сделал вывод что это не обязательно, и лично я чувствую, в моем случае, что это был бы ленивый подход к решению, особенно когда я нахожу, что C позволяет более программному управлению и (в моем случае здесь) повысить эффективность.
Выполняется то же самое, например. 'GetResourceAllocationInfo' и другие методы преобразования структуры? В любом случае, вы должны сделать свое редактирование ответом и принять его (возможно, даже получить значок [self-learner] (http://stackoverflow.com/help/badges/14/self-learner)), чтобы помочь увеличить видимость для [людей из будущего] (https://xkcd.com/979/). – MooseBoys
Я буду исследовать. Я не ожидал ответа - извините мой поздний ответ. Сообщив о проблеме Microsoft, я получил подтверждение. Я понятия не имею, что-то делается, или рассматривается ли моя проблема. Это должно быть легко исправить, потому что, в конце концов, это только файл заголовка, который нуждается в модификации, а не сам API. Но я буду исследовать и возвращаться с моими открытиями. Я ничего не могу гарантировать, но я все еще новичок в DirectX-12. –