Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(448)

Unified Diff: gpu/command_buffer/client/gles2_implementation.cc

Issue 434063: Merged in recent changes to command buffer code. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: Created 11 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: gpu/command_buffer/client/gles2_implementation.cc
===================================================================
--- gpu/command_buffer/client/gles2_implementation.cc (revision 33021)
+++ gpu/command_buffer/client/gles2_implementation.cc (working copy)
@@ -14,13 +14,21 @@
GLES2Implementation::GLES2Implementation(
GLES2CmdHelper* helper,
+ size_t transfer_buffer_size,
void* transfer_buffer,
- int transfer_buffer_id)
+ int32 transfer_buffer_id)
: util_(0), // TODO(gman): Get real number of compressed texture formats.
helper_(helper),
- shared_memory_(transfer_buffer, transfer_buffer_id),
+ transfer_buffer_(transfer_buffer_size, helper, transfer_buffer),
+ transfer_buffer_id_(transfer_buffer_id),
pack_alignment_(4),
unpack_alignment_(4) {
+ // Eat 1 id so we start at 1 instead of 0.
+ GLuint eat;
+ MakeIds(1, &eat);
+ // Allocate space for simple GL results.
+ result_buffer_ = transfer_buffer_.Alloc(kMaxSizeOfSimpleResult);
+ result_shm_offset_ = transfer_buffer_.GetOffset(result_buffer_);
}
void GLES2Implementation::MakeIds(GLsizei n, GLuint* ids) {
@@ -35,11 +43,47 @@
}
}
+void GLES2Implementation::WaitForCmd() {
+ int32 token = helper_->InsertToken();
+ helper_->WaitForToken(token);
+}
+
void GLES2Implementation::DrawElements(
GLenum mode, GLsizei count, GLenum type, const void* indices) {
helper_->DrawElements(mode, count, type, reinterpret_cast<GLuint>(indices));
}
+GLint GLES2Implementation::GetAttribLocation(
+ GLuint program, const char* name) {
+ helper_->GetAttribLocationImmediate(
+ program, name, result_shm_id(), result_shm_offset());
+ WaitForCmd();
+ return GetResultAs<GLint>();
+}
+
+GLint GLES2Implementation::GetUniformLocation(
+ GLuint program, const char* name) {
+ helper_->GetUniformLocationImmediate(
+ program, name, result_shm_id(), result_shm_offset());
+ WaitForCmd();
+ return GetResultAs<GLint>();
+}
+
+void GLES2Implementation::PixelStorei(GLenum pname, GLint param) {
+ switch (pname) {
+ case GL_PACK_ALIGNMENT:
+ pack_alignment_ = param;
+ break;
+ case GL_UNPACK_ALIGNMENT:
+ unpack_alignment_ = param;
+ break;
+ default:
+ break;
+ }
+ helper_->PixelStorei(pname, param);
+}
+
+
void GLES2Implementation::VertexAttribPointer(
GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride,
const void* ptr) {
@@ -48,103 +92,158 @@
}
void GLES2Implementation::ShaderSource(
- GLuint shader, GLsizei count, const char** string, const GLint* length) {
+ GLuint shader, GLsizei count, const char** source, const GLint* length) {
// TODO(gman): change to use buckets and check that there is enough room.
- uint32* offsets = shared_memory_.GetAddressAs<uint32*>(0);
- char* strings = reinterpret_cast<char*>(offsets + count);
+ // Compute the total size.
+ uint32 total_size = count * sizeof(total_size);
+ for (GLsizei ii = 0; ii < count; ++ii) {
+ total_size += length ? length[ii] : strlen(source[ii]);
+ }
+
+ // Create string table in transfer buffer.
+ char* strings = transfer_buffer_.AllocTyped<char>(total_size);
+ uint32* offsets = reinterpret_cast<uint32*>(strings);
uint32 offset = count * sizeof(*offsets);
for (GLsizei ii = 0; ii < count; ++ii) {
- uint32 len = length ? length[ii] : strlen(string[ii]);
- memcpy(strings + offset, string[ii], len);
+ uint32 len = length ? length[ii] : strlen(source[ii]);
+ memcpy(strings + offset, source[ii], len);
offset += len;
offsets[ii] = offset;
}
- helper_->ShaderSource(shader, count, shared_memory_.GetId(), 0, offset);
- // TODO(gman): Should insert token but not wait until we need shared memory
- // again. Really, I should implement a shared memory manager that puts
- // things in the next unused part of shared memory and only blocks
- // when it needs more memory.
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ helper_->ShaderSource(shader, count,
+ transfer_buffer_id_,
+ transfer_buffer_.GetOffset(strings), offset);
+ transfer_buffer_.FreePendingToken(strings, helper_->InsertToken());
}
void GLES2Implementation::BufferData(
GLenum target, GLsizeiptr size, const void* data, GLenum usage) {
- // TODO(gman): Switch to use buckets alwayst or at least if no room in shared
- // memory.
- memcpy(shared_memory_.GetAddress(0), data, size);
- helper_->BufferData(target, size, shared_memory_.GetId(), 0, usage);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ // NOTE: Should this be optimized for the case where we can call BufferData
+ // with the actual data in the case of our transfer buffer being big
+ // enough?
+ helper_->BufferData(target, size, 0, 0, usage);
+ if (data != NULL) {
+ BufferSubData(target, 0, size, data);
+ }
}
void GLES2Implementation::BufferSubData(
GLenum target, GLintptr offset, GLsizeiptr size, const void* data) {
- // TODO(gman): Switch to use buckets alwayst or at least if no room in shared
- // memory.
- memcpy(shared_memory_.GetAddress(0), data, size);
- helper_->BufferSubData(target, offset, size, shared_memory_.GetId(), 0);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ const int8* source = static_cast<const int8*>(data);
+ GLsizeiptr max_size = transfer_buffer_.GetLargestFreeOrPendingSize();
+ while (size) {
+ GLsizeiptr part_size = std::min(size, max_size);
+ void* buffer = transfer_buffer_.Alloc(part_size);
+ memcpy(buffer, source, part_size);
+ helper_->BufferSubData(target, offset, part_size,
+ transfer_buffer_id_,
+ transfer_buffer_.GetOffset(buffer));
+ transfer_buffer_.FreePendingToken(buffer, helper_->InsertToken());
+ offset += part_size;
+ source += part_size;
+ size -= part_size;
+ }
}
void GLES2Implementation::CompressedTexImage2D(
GLenum target, GLint level, GLenum internalformat, GLsizei width,
- GLsizei height, GLint border, GLsizei imageSize, const void* data) {
+ GLsizei height, GLint border, GLsizei image_size, const void* data) {
// TODO(gman): Switch to use buckets alwayst or at least if no room in shared
// memory.
- memcpy(shared_memory_.GetAddress(0), data, imageSize);
+ DCHECK_LE(image_size,
+ static_cast<GLsizei>(
+ transfer_buffer_.GetLargestFreeOrPendingSize()));
+ void* buffer = transfer_buffer_.Alloc(image_size);
+ memcpy(buffer, data, image_size);
helper_->CompressedTexImage2D(
- target, level, internalformat, width, height, border, imageSize,
- shared_memory_.GetId(), 0);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ target, level, internalformat, width, height, border, image_size,
+ transfer_buffer_id_, transfer_buffer_.GetOffset(buffer));
+ transfer_buffer_.FreePendingToken(buffer, helper_->InsertToken());
}
void GLES2Implementation::CompressedTexSubImage2D(
GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width,
- GLsizei height, GLenum format, GLsizei imageSize, const void* data) {
+ GLsizei height, GLenum format, GLsizei image_size, const void* data) {
// TODO(gman): Switch to use buckets alwayst or at least if no room in shared
// memory.
- memcpy(shared_memory_.GetAddress(0), data, imageSize);
+ DCHECK_LE(image_size,
+ static_cast<GLsizei>(
+ transfer_buffer_.GetLargestFreeOrPendingSize()));
+ void* buffer = transfer_buffer_.Alloc(image_size);
+ memcpy(buffer, data, image_size);
helper_->CompressedTexSubImage2D(
- target, level, xoffset, yoffset, width, height, format, imageSize,
- shared_memory_.GetId(), 0);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ target, level, xoffset, yoffset, width, height, format, image_size,
+ transfer_buffer_id_, transfer_buffer_.GetOffset(buffer));
+ transfer_buffer_.FreePendingToken(buffer, helper_->InsertToken());
}
void GLES2Implementation::TexImage2D(
GLenum target, GLint level, GLint internalformat, GLsizei width,
GLsizei height, GLint border, GLenum format, GLenum type,
const void* pixels) {
- // TODO(gman): Switch to use buckets alwayst or at least if no room in shared
- // memory.
- uint32 pixels_size = GLES2Util::ComputeImageDataSize(
- width, height, format, type, unpack_alignment_);
- memcpy(shared_memory_.GetAddress(0), pixels, pixels_size);
helper_->TexImage2D(
- target, level, internalformat, width, height, border, format, type,
- shared_memory_.GetId(), 0);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ target, level, internalformat, width, height, border, format, type, 0, 0);
+ if (pixels) {
+ TexSubImage2D(target, level, 0, 0, width, height, format, type, pixels);
+ }
}
void GLES2Implementation::TexSubImage2D(
GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width,
GLsizei height, GLenum format, GLenum type, const void* pixels) {
- // TODO(gman): Switch to use buckets alwayst or at least if no room in shared
- // memory.
- uint32 pixels_size = GLES2Util::ComputeImageDataSize(
- width, height, format, type, unpack_alignment_);
- memcpy(shared_memory_.GetAddress(0), pixels, pixels_size);
- helper_->TexSubImage2D(
- target, level, xoffset, yoffset, width, height, format, type,
- shared_memory_.GetId(), 0);
- int32 token = helper_->InsertToken();
- helper_->WaitForToken(token);
+ const int8* source = static_cast<const int8*>(pixels);
+ GLsizeiptr max_size = transfer_buffer_.GetLargestFreeOrPendingSize();
+
+ GLsizeiptr unpadded_row_size = GLES2Util::ComputeImageDataSize(
+ width, 1, format, type, unpack_alignment_);
+ GLsizeiptr padded_row_size = GLES2Util::ComputeImageDataSize(
+ width, 2, format, type, unpack_alignment_) - unpadded_row_size;
+
+ if (padded_row_size <= max_size) {
+ // Transfer by rows.
+ GLint max_rows = max_size / padded_row_size;
+ while (height) {
+ GLint num_rows = std::min(height, max_rows);
+ GLsizeiptr part_size = num_rows * padded_row_size;
+ void* buffer = transfer_buffer_.Alloc(part_size);
+ memcpy(buffer, source, part_size);
+ helper_->TexSubImage2D(
+ target, level, xoffset, yoffset, width, num_rows, format, type,
+ transfer_buffer_id_, transfer_buffer_.GetOffset(buffer));
+ transfer_buffer_.FreePendingToken(buffer, helper_->InsertToken());
+ yoffset += num_rows;
+ source += part_size;
+ height -= num_rows;
+ }
+ } else {
+ // Transfer by sub rows. Beacuse GL has no maximum texture dimensions.
+ GLsizeiptr element_size = GLES2Util::ComputeImageDataSize(
+ 1, 1, format, type, unpack_alignment_);
+ max_size -= max_size % element_size;
+ GLint max_sub_row_pixels = max_size / element_size;
+ for (; height; --height) {
+ GLint temp_width = width;
+ GLint temp_xoffset = xoffset;
+ const int8* row_source = source;
+ while (temp_width) {
+ GLint num_pixels = std::min(width, max_sub_row_pixels);
+ GLsizeiptr part_size = num_pixels * element_size;
+ void* buffer = transfer_buffer_.Alloc(part_size);
+ memcpy(buffer, row_source, part_size);
+ helper_->TexSubImage2D(
+ target, level, temp_xoffset, yoffset, temp_width, 1, format, type,
+ transfer_buffer_id_, transfer_buffer_.GetOffset(buffer));
+ transfer_buffer_.FreePendingToken(buffer, helper_->InsertToken());
+ row_source += part_size;
+ temp_xoffset += num_pixels;
+ temp_width -= num_pixels;
+ }
+ ++yoffset;
+ source += padded_row_size;
+ }
+ }
}
« no previous file with comments | « gpu/command_buffer/client/gles2_implementation.h ('k') | gpu/command_buffer/client/gles2_implementation_autogen.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698