Files
UnrealEngine/Engine/Source/Runtime/OpenGLDrv/Private/OpenGL4.cpp
2025-05-18 13:04:45 +08:00

115 lines
3.7 KiB
C++

// Copyright Epic Games, Inc. All Rights Reserved.
/*=============================================================================
OpenGL4.cpp: OpenGL 4.3 implementation.
=============================================================================*/
#include "OpenGL4.h"
#if UGL_PLATFORM_SUPPORTS_GL4
#include "OpenGLDrvPrivate.h"
GLint FOpenGL4::MaxComputeUniformComponents = -1;
GLint FOpenGL4::MaxCombinedUAVUnits = 0;
GLint FOpenGL4::MaxComputeUAVUnits = -1;
GLint FOpenGL4::MaxPixelUAVUnits = -1;
bool FOpenGL4::bSupportsGPUMemoryInfo = false;
void FOpenGL4::ProcessQueryGLInt()
{
GET_GL_INT(GL_MAX_COMBINED_IMAGE_UNIFORMS, 0, MaxCombinedUAVUnits);
GET_GL_INT(GL_MAX_FRAGMENT_IMAGE_UNIFORMS, 0, MaxPixelUAVUnits);
GET_GL_INT(GL_TEXTURE_BUFFER_OFFSET_ALIGNMENT, 0, TextureBufferAlignment);
GET_GL_INT(GL_MAX_COMPUTE_UNIFORM_COMPONENTS, 0, MaxComputeUniformComponents);
GET_GL_INT(GL_MAX_COMPUTE_IMAGE_UNIFORMS, 0, MaxComputeUAVUnits);
GLint MaxCombinedSSBOUnits = 0;
GET_GL_INT(GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS, 0, MaxCombinedSSBOUnits);
// UAVs slots in UE are shared between Images and SSBO, so this should be max(GL_MAX_COMBINED_IMAGE_UNIFORMS, GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS)
MaxCombinedUAVUnits = FMath::Max(MaxCombinedUAVUnits, MaxCombinedSSBOUnits);
// clamp UAV units to a sensible limit
MaxCombinedUAVUnits = FMath::Min(MaxCombinedUAVUnits, 16);
MaxComputeUAVUnits = FMath::Min(MaxComputeUAVUnits, 16);
// this is split between VS and PS, 4 to each stage
MaxPixelUAVUnits = FMath::Min(MaxPixelUAVUnits, 4);
}
void FOpenGL4::ProcessExtensions( const FString& ExtensionsString )
{
int32 MajorVersion =0;
int32 MinorVersion =0;
FString Version = ANSI_TO_TCHAR((const ANSICHAR*)glGetString(GL_VERSION));
FString MajorString, MinorString;
if (Version.Split(TEXT("."), &MajorString, &MinorString))
{
MajorVersion = FCString::Atoi(*MajorString);
MinorVersion = FCString::Atoi(*MinorString);
}
check(MajorVersion!=0);
bSupportsGPUMemoryInfo = ExtensionsString.Contains(TEXT("GL_NVX_gpu_memory_info"));
//Process Queries after extensions to avoid queries that use functionality that might not be present
ProcessQueryGLInt();
FOpenGL3::ProcessExtensions(ExtensionsString);
}
#ifndef GL_NVX_gpu_memory_info
#define GL_NVX_gpu_memory_info 1
#define GL_GPU_MEMORY_INFO_DEDICATED_VIDMEM_NVX 0x9047
#define GL_GPU_MEMORY_INFO_TOTAL_AVAILABLE_MEMORY_NVX 0x9048
#define GL_GPU_MEMORY_INFO_CURRENT_AVAILABLE_VIDMEM_NVX 0x9049
#define GL_GPU_MEMORY_INFO_EVICTION_COUNT_NVX 0x904A
#define GL_GPU_MEMORY_INFO_EVICTED_MEMORY_NVX 0x904B
#endif
uint64 FOpenGL4::GetVideoMemorySize()
{
uint64 VideoMemorySize = 0;
if (bSupportsGPUMemoryInfo)
{
GLint VMSizeKB = 0;
glGetIntegerv( GL_GPU_MEMORY_INFO_DEDICATED_VIDMEM_NVX, &VMSizeKB);
VideoMemorySize = VMSizeKB * 1024ll;
}
return VideoMemorySize;
}
static FORCEINLINE void BindVertexBuffer(GLuint BindingIndex, GLuint Buffer, GLintptr Offset, GLsizei Stride)
{
glBindVertexBuffer(BindingIndex, Buffer, Offset, Stride);
}
static FORCEINLINE void VertexAttribFormat(GLuint AttribIndex, GLint Size, GLenum Type, GLboolean Normalized, GLuint RelativeOffset)
{
glVertexAttribFormat(AttribIndex, Size, Type, Normalized, RelativeOffset);
}
static FORCEINLINE void VertexAttribIFormat(GLuint AttribIndex, GLint Size, GLenum Type, GLuint RelativeOffset)
{
glVertexAttribIFormat(AttribIndex, Size, Type, RelativeOffset);
}
static FORCEINLINE void VertexAttribBinding(GLuint AttribIndex, GLuint BindingIndex)
{
glVertexAttribBinding(AttribIndex, BindingIndex);
}
static FORCEINLINE void VertexBindingDivisor(GLuint BindingIndex, GLuint Divisor)
{
glVertexBindingDivisor(BindingIndex, Divisor);
}
#endif