| Index: cc/resources/resource_provider.cc
|
| diff --git a/cc/resources/resource_provider.cc b/cc/resources/resource_provider.cc
|
| index c0e8f1bd205ddd938390c8cbf10b0b46ce466904..89e619098f33d94eca7d2d0f99d0afb9fc1baa48 100644
|
| --- a/cc/resources/resource_provider.cc
|
| +++ b/cc/resources/resource_provider.cc
|
| @@ -75,6 +75,10 @@ GLenum TextureToStorageFormat(ResourceFormat format) {
|
| case ALPHA_8:
|
| case LUMINANCE_8:
|
| case RGB_565:
|
| + case ATC:
|
| + case ATC_IA:
|
| + case DXT1:
|
| + case DXT5:
|
| case ETC1:
|
| case RED_8:
|
| NOTREACHED();
|
| @@ -94,6 +98,10 @@ bool IsFormatSupportedForStorage(ResourceFormat format, bool use_bgra) {
|
| case ALPHA_8:
|
| case LUMINANCE_8:
|
| case RGB_565:
|
| + case ATC:
|
| + case ATC_IA:
|
| + case DXT1:
|
| + case DXT5:
|
| case ETC1:
|
| case RED_8:
|
| return false;
|
| @@ -122,12 +130,21 @@ gfx::GpuMemoryBuffer::Format ToGpuMemoryBufferFormat(ResourceFormat format) {
|
| return gfx::GpuMemoryBuffer::Format::RGBA_8888;
|
| case BGRA_8888:
|
| return gfx::GpuMemoryBuffer::Format::BGRA_8888;
|
| + case ATC:
|
| + return gfx::GpuMemoryBuffer::Format::ATC;
|
| + case ATC_IA:
|
| + return gfx::GpuMemoryBuffer::Format::ATCIA;
|
| + case DXT1:
|
| + return gfx::GpuMemoryBuffer::Format::DXT1;
|
| + case DXT5:
|
| + return gfx::GpuMemoryBuffer::Format::DXT5;
|
| + case ETC1:
|
| + return gfx::GpuMemoryBuffer::Format::ETC1;
|
| + case RED_8:
|
| case RGBA_4444:
|
| case ALPHA_8:
|
| case LUMINANCE_8:
|
| case RGB_565:
|
| - case ETC1:
|
| - case RED_8:
|
| break;
|
| }
|
| NOTREACHED();
|
| @@ -419,6 +436,25 @@ ResourceProvider::Resource::Resource(const SharedBitmapId& bitmap_id,
|
| DCHECK(wrap_mode == GL_CLAMP_TO_EDGE || wrap_mode == GL_REPEAT);
|
| }
|
|
|
| +bool ResourceProvider::Resource::IsCompressed() const {
|
| + return IsFormatCompressed(format);
|
| +}
|
| +
|
| +size_t ResourceProvider::Resource::CompressedSize() const {
|
| + switch (format) {
|
| + case ATC:
|
| + case DXT1:
|
| + case ETC1:
|
| + return size.width() * size.height() / 2;
|
| + case ATC_IA:
|
| + case DXT5:
|
| + return size.width() * size.height();
|
| + default:
|
| + NOTREACHED();
|
| + return 0;
|
| + }
|
| +}
|
| +
|
| ResourceProvider::Child::Child() : marked_for_deletion(false) {}
|
|
|
| ResourceProvider::Child::~Child() {}
|
| @@ -430,15 +466,13 @@ scoped_ptr<ResourceProvider> ResourceProvider::Create(
|
| BlockingTaskRunner* blocking_main_thread_task_runner,
|
| int highp_threshold_min,
|
| bool use_rgba_4444_texture_format,
|
| + bool use_texture_compression,
|
| size_t id_allocation_chunk_size) {
|
| - scoped_ptr<ResourceProvider> resource_provider(
|
| - new ResourceProvider(output_surface,
|
| - shared_bitmap_manager,
|
| - gpu_memory_buffer_manager,
|
| - blocking_main_thread_task_runner,
|
| - highp_threshold_min,
|
| - use_rgba_4444_texture_format,
|
| - id_allocation_chunk_size));
|
| + scoped_ptr<ResourceProvider> resource_provider(new ResourceProvider(
|
| + output_surface, shared_bitmap_manager, gpu_memory_buffer_manager,
|
| + blocking_main_thread_task_runner, highp_threshold_min,
|
| + use_rgba_4444_texture_format, use_texture_compression,
|
| + id_allocation_chunk_size));
|
|
|
| if (resource_provider->ContextGL())
|
| resource_provider->InitializeGL();
|
| @@ -458,6 +492,43 @@ ResourceProvider::~ResourceProvider() {
|
| CleanUpGLIfNeeded();
|
| }
|
|
|
| +ResourceFormat ResourceProvider::memory_efficient_texture_format(
|
| + ResourceFormatUsage usage) const {
|
| + if (use_texture_compression_ && usage != FORMAT_USAGE_NATIVE) {
|
| + // Try to select the prefered compression method.
|
| + switch (preferred_tile_compression_method_) {
|
| + case TILE_COMPRESSION_METHOD_ATC:
|
| + if (use_compressed_texture_atc_) {
|
| + return usage == FORMAT_USAGE_OPAQUE ? ATC : ATC_IA;
|
| + }
|
| + break;
|
| + case TILE_COMPRESSION_METHOD_DXT:
|
| + if (use_compressed_texture_dxt_) {
|
| + return usage == FORMAT_USAGE_OPAQUE ? DXT1 : DXT5;
|
| + }
|
| + break;
|
| + case TILE_COMPRESSION_METHOD_ETC:
|
| + if (use_compressed_texture_etc1_ && usage == FORMAT_USAGE_OPAQUE) {
|
| + return ETC1;
|
| + }
|
| + break;
|
| + default:
|
| + break;
|
| + }
|
| +
|
| + // Check the formats in preferred order, based on encoding speed and
|
| + // compression ratio.
|
| + if (use_compressed_texture_atc_) {
|
| + return usage == FORMAT_USAGE_OPAQUE ? ATC : ATC_IA;
|
| + }
|
| + if (use_compressed_texture_dxt_) {
|
| + return usage == FORMAT_USAGE_OPAQUE ? DXT1 : DXT5;
|
| + }
|
| + }
|
| +
|
| + return use_rgba_4444_texture_format_ ? RGBA_4444 : best_texture_format_;
|
| +}
|
| +
|
| bool ResourceProvider::InUseByConsumer(ResourceId id) {
|
| Resource* resource = GetResource(id);
|
| return resource->lock_for_read_count > 0 || resource->exported_count > 0 ||
|
| @@ -1205,6 +1276,7 @@ ResourceProvider::ResourceProvider(
|
| BlockingTaskRunner* blocking_main_thread_task_runner,
|
| int highp_threshold_min,
|
| bool use_rgba_4444_texture_format,
|
| + bool use_texture_compression,
|
| size_t id_allocation_chunk_size)
|
| : output_surface_(output_surface),
|
| shared_bitmap_manager_(shared_bitmap_manager),
|
| @@ -1218,11 +1290,14 @@ ResourceProvider::ResourceProvider(
|
| use_texture_storage_ext_(false),
|
| use_texture_format_bgra_(false),
|
| use_texture_usage_hint_(false),
|
| + use_compressed_texture_atc_(false),
|
| + use_compressed_texture_dxt_(false),
|
| use_compressed_texture_etc1_(false),
|
| yuv_resource_format_(LUMINANCE_8),
|
| max_texture_size_(0),
|
| best_texture_format_(RGBA_8888),
|
| use_rgba_4444_texture_format_(use_rgba_4444_texture_format),
|
| + use_texture_compression_(use_texture_compression),
|
| id_allocation_chunk_size_(id_allocation_chunk_size),
|
| use_sync_query_(false) {
|
| DCHECK(output_surface_->HasClient());
|
| @@ -1257,6 +1332,8 @@ void ResourceProvider::InitializeGL() {
|
| use_texture_storage_ext_ = caps.gpu.texture_storage;
|
| use_texture_format_bgra_ = caps.gpu.texture_format_bgra8888;
|
| use_texture_usage_hint_ = caps.gpu.texture_usage;
|
| + use_compressed_texture_atc_ = caps.gpu.texture_format_atc;
|
| + use_compressed_texture_dxt_ = caps.gpu.texture_format_dxt;
|
| use_compressed_texture_etc1_ = caps.gpu.texture_format_etc1;
|
| yuv_resource_format_ = caps.gpu.texture_rg ? RED_8 : LUMINANCE_8;
|
| use_sync_query_ = caps.gpu.sync_query;
|
| @@ -1732,7 +1809,6 @@ void ResourceProvider::AcquirePixelBuffer(ResourceId id) {
|
| DCHECK(resource->origin == Resource::Internal);
|
| DCHECK_EQ(resource->exported_count, 0);
|
| DCHECK(!resource->image_id);
|
| - DCHECK_NE(ETC1, resource->format);
|
|
|
| DCHECK_EQ(GLTexture, resource->type);
|
| GLES2Interface* gl = ContextGL();
|
| @@ -1741,11 +1817,11 @@ void ResourceProvider::AcquirePixelBuffer(ResourceId id) {
|
| resource->gl_pixel_buffer_id = buffer_id_allocator_->NextId();
|
| gl->BindBuffer(GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM,
|
| resource->gl_pixel_buffer_id);
|
| - unsigned bytes_per_pixel = BitsPerPixel(resource->format) / 8;
|
| - gl->BufferData(GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM,
|
| - resource->size.height() *
|
| - RoundUp(bytes_per_pixel * resource->size.width(), 4u),
|
| - NULL,
|
| + unsigned width_in_bytes =
|
| + BitsPerPixel(resource->format) * resource->size.width() / 8;
|
| + unsigned image_size = resource->size.height() * RoundUp(width_in_bytes, 4u);
|
| + DCHECK(image_size);
|
| + gl->BufferData(GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM, image_size, NULL,
|
| GL_DYNAMIC_DRAW);
|
| gl->BindBuffer(GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM, 0);
|
| }
|
| @@ -1882,26 +1958,33 @@ void ResourceProvider::BeginSetPixels(ResourceId id) {
|
| gl->GenQueriesEXT(1, &resource->gl_upload_query_id);
|
| gl->BeginQueryEXT(GL_ASYNC_PIXEL_UNPACK_COMPLETED_CHROMIUM,
|
| resource->gl_upload_query_id);
|
| - if (allocate) {
|
| - gl->AsyncTexImage2DCHROMIUM(GL_TEXTURE_2D,
|
| - 0, /* level */
|
| - GLInternalFormat(resource->format),
|
| - resource->size.width(),
|
| - resource->size.height(),
|
| - 0, /* border */
|
| - GLDataFormat(resource->format),
|
| - GLDataType(resource->format),
|
| - NULL);
|
| + if (resource->IsCompressed()) {
|
| + if (allocate) {
|
| + gl->AsyncCompressedTexImage2DCHROMIUM(
|
| + GL_TEXTURE_2D, 0 /* level */, GLInternalFormat(resource->format),
|
| + resource->size.width(), resource->size.height(), 0 /* border */,
|
| + resource->CompressedSize(), NULL);
|
| + } else {
|
| + gl->AsyncCompressedTexSubImage2DCHROMIUM(
|
| + GL_TEXTURE_2D, 0 /* level */, 0 /* x */, 0 /* y */,
|
| + resource->size.width(), resource->size.height(),
|
| + GLInternalFormat(resource->format), resource->CompressedSize(), NULL);
|
| + }
|
| } else {
|
| - gl->AsyncTexSubImage2DCHROMIUM(GL_TEXTURE_2D,
|
| - 0, /* level */
|
| - 0, /* x */
|
| - 0, /* y */
|
| - resource->size.width(),
|
| - resource->size.height(),
|
| - GLDataFormat(resource->format),
|
| - GLDataType(resource->format),
|
| - NULL);
|
| + if (allocate) {
|
| + gl->AsyncTexImage2DCHROMIUM(
|
| + GL_TEXTURE_2D, 0, /* level */
|
| + GLInternalFormat(resource->format), resource->size.width(),
|
| + resource->size.height(), 0, /* border */
|
| + GLDataFormat(resource->format), GLDataType(resource->format), NULL);
|
| + } else {
|
| + gl->AsyncTexSubImage2DCHROMIUM(
|
| + GL_TEXTURE_2D, 0, /* level */
|
| + 0, /* x */
|
| + 0, /* y */
|
| + resource->size.width(), resource->size.height(),
|
| + GLDataFormat(resource->format), GLDataType(resource->format), NULL);
|
| + }
|
| }
|
| gl->EndQueryEXT(GL_ASYNC_PIXEL_UNPACK_COMPLETED_CHROMIUM);
|
| gl->BindBuffer(GL_PIXEL_UNPACK_TRANSFER_BUFFER_CHROMIUM, 0);
|
| @@ -2035,8 +2118,8 @@ void ResourceProvider::LazyAllocate(Resource* resource) {
|
| gl->TexStorage2DEXT(
|
| GL_TEXTURE_2D, 1, storage_format, size.width(), size.height()));
|
| } else {
|
| - // ETC1 does not support preallocation.
|
| - if (format != ETC1) {
|
| + // Compressed formats does not support preallocation.
|
| + if (!IsFormatCompressed(format)) {
|
| GLC(gl,
|
| gl->TexImage2D(GL_TEXTURE_2D,
|
| 0,
|
| @@ -2101,12 +2184,17 @@ void ResourceProvider::CopyResource(ResourceId source_id, ResourceId dest_id) {
|
| }
|
| DCHECK(!dest_resource->image_id);
|
| dest_resource->allocated = true;
|
| - gl->CopyTextureCHROMIUM(dest_resource->target,
|
| - source_resource->gl_id,
|
| - dest_resource->gl_id,
|
| - 0,
|
| - GLInternalFormat(dest_resource->format),
|
| - GLDataType(dest_resource->format));
|
| + if (!source_resource->IsCompressed()) {
|
| + gl->CopyTextureCHROMIUM(dest_resource->target, source_resource->gl_id,
|
| + dest_resource->gl_id, 0,
|
| + GLInternalFormat(dest_resource->format),
|
| + GLDataType(dest_resource->format));
|
| + } else {
|
| + gl->CopyCompressedTextureCHROMIUM(
|
| + dest_resource->target, source_resource->gl_id, dest_resource->gl_id,
|
| + GLInternalFormat(dest_resource->format),
|
| + GLDataType(dest_resource->format));
|
| + }
|
| if (source_resource->gl_read_lock_query_id) {
|
| // End query and create a read lock fence that will prevent access to
|
| // source resource until CopyTextureCHROMIUM command has completed.
|
|
|