The OpenGL reference mentions about the GL_OUT_OF_MEMORY
error
The state of the GL is undefined, except for the state of the error flags,
What do you do if malloc
returns NULL or new
throws an exception? Do you have a recovery path for that possibility?
Most applications don't. Most applications happily assume that malloc
will never return NULL and/or that new
will never throw. And if those operations fail, they will happily crash.
The same would generally go for OpenGL. You presumably asked for that particular memory size for a good reason; because you needed it. And if you can't get it, for whatever reason, there usually isn't a solution for that.
While there are cases where you could recover from not being able to allocate memory, OpenGL confounds you in another way.
See, the reason that the entire state of OpenGL is undefined on an OUT_OF_MEMORY error is this: OOM can happen from anywhere. No function's documentation claims that it can issue an OOM error because every function can issue such an error.
Memory is not (necessarily) allocated when you call an allocating function. The driver can (and almost certainly will) defer allocation until later. So you get an OOM error from whatever OpenGL function you call after the driver detects the OOM condition.
So if buffer allocation fails, long after the call to glBufferData
that provoked the failure, what can the OpenGL specification say about the current state? From the OOM error alone, there is no way to track down exactly what caused it.
So if you get this error, recovery is not really possible. Your only real recourse is to terminate the application or rebuild it.
Note that lower-level APIs like Vulkan or D3D12 will OOM immediately when you try to allocate memory and cannot.
Also:
But on the other hand the API doesn't seem to provide any way to check if sending data of particular size would succeed.
That would solve nothing. Why?
Because your application doesn't own the GPU; your OS does. Multiple programs can allocate memory on the GPU at the same time. The OS can poke about with memory too, paging things into and outof memory as it sees fit.
So if you ask if an allocation would succeed, and OpenGL returned yes, by the time you actually perform that allocation, the answer may have changed.
This is also why Vulkan and similar APIs do not have a function to test if an allocation will succeed (nor does it have a function to test how much memory is left unallocated). You just allocate memory; either it works and you get your memory, or it fails and you don't.