Большинство форматов файлов изображений либо сжаты, либо сильно закодированы.Поэтому, по крайней мере, некоторые их части должны сначала проходить через обычную системную память.Однако нет необходимости выделять буфер для всего изображения в system RAM, если вы используете объект буфера OpenGL.Однако он, вероятно, в конечном итоге выделит буферный объект в VRAM, , поэтому у вас есть данные там дважды, по крайней мере, в течение некоторого времени .
В скале указано, как его использовать:
size_t buffer_size = ...;
GLuint buffer_id;
glGenBuffers(1, &buffer_id);
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, buffer_id);
glBufferData(GL_PIXEL_UNPACK_BUFFER, buffer_size, NULL, GL_STATIC_DRAW);
void *buffer_ptr = glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_WRITE_ONLY);
size_t offset_into_buffer = ...;
read_image_pixels_into_buffer((char*)buffer_ptr + offset_into_buffer);
glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER);
glTexImage2D(..., (void*)((uintptr_t)offset_into_buffer));
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, 0);
glDeleteBuffers(1, &buffer_id);
Обратите внимание, что производительность и эффективность могут пострадать, если объекты буфера используются наивно, как в коде выше.Обычно буферные объекты используются в качестве пулов памяти, из которых фрагменты обрезаются по мере необходимости, а буферы не создаются постоянно и удаляются.Однако существует также потоковая передача через буферизацию, которая фактически создает заново буферы: https://www.khronos.org/opengl/wiki/Buffer_Object_Streaming
Обновление, касающееся комментария @ BDL
С OpenGL вы действительно не имеете никакого контроля над тем, как обстоят дела произойдет , но вы можете подтолкнуть выбранный путь кода в определенном направлении.Всегда нужно помнить одну вещь: у OpenGL вообще нет модели памяти.Все просто должно работать ... как-то.
Побочным эффектом этого является то, что для выполнения требований реализация OpenGL на основе графического процессора может в любой момент быть вынуждена отправить некоторые данные в память графического процессора.где-нибудь еще.… Скорее всего, системная оперативная память, но, может быть, даже место под диск.Поскольку современные операционные системы имеют тенденцию перегружать память, вполне вероятно, что реализация OpenGL просто сохранит тот же объем фактически поврежденной памяти страницы, который требуется для всех выделенных объектов OpenGL.А для непотоковых данных имеет смысл иметь постоянную копию данных в системной памяти (или подкачке), потому что это превращает выселение в очистку некоторой записи выделения памяти VRAM.
Теперьв случае объектов буфера тот самый путь кода, который я обрисовал выше, может фактически избежать одной дополнительной копии путем переименования области буфера, то есть при загрузке данных в текстуру данные фактически не копируются, а только дескриптор текстуры, установленный в точкув этой конкретной области в объекте буфера ... пока эта область в буфере не будет перезаписана, что затем инициирует создание копии.Однако удаление объекта буфера (имени) сразу после загрузки его в текстуру может фактически перевести всю память буфера в объект текстуры._Это, однако, всего лишь потенциальная оптимизация, реализация OpenGL может реализовать, но не обязана .__
Вся спецификация OpenGL чрезвычайно расплывчата, что делает разработку высокопроизводительного OpenGLреализация мина boggingly тяжелая работа.