Chromium Code Reviews| Index: gpu/command_buffer/service/texture_manager.h |
| diff --git a/gpu/command_buffer/service/texture_manager.h b/gpu/command_buffer/service/texture_manager.h |
| index 7293f272e14209a21cd68fdb8a6f3d681e2d027a..4a64fbd5b08d8441c8f443fb50a4f6e1099384cb 100644 |
| --- a/gpu/command_buffer/service/texture_manager.h |
| +++ b/gpu/command_buffer/service/texture_manager.h |
| @@ -6,6 +6,7 @@ |
| #define GPU_COMMAND_BUFFER_SERVICE_TEXTURE_MANAGER_H_ |
| #include <list> |
| +#include <set> |
| #include <string> |
| #include <vector> |
| #include "base/basictypes.h" |
| @@ -25,13 +26,17 @@ class GLES2Decoder; |
| class Display; |
| class ErrorState; |
| class FeatureInfo; |
| +class FramebufferManager; |
| class TextureDefinition; |
| class TextureManager; |
| +class TextureRef; |
| // Info about Textures currently in the system. |
| -class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| +// This class wraps a real GL texture, keeping track of its meta-data. It is |
| +// jointly owned by possibly multiple TextureRef. |
| +class GPU_EXPORT Texture { |
| public: |
| - Texture(TextureManager* manager, GLuint service_id); |
| + explicit Texture(GLuint service_id); |
| GLenum min_filter() const { |
| return min_filter_; |
| @@ -102,10 +107,6 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| // does not exist. |
| gfx::GLImage* GetLevelImage(GLint target, GLint level) const; |
| - bool IsDeleted() const { |
| - return deleted_; |
| - } |
|
piman
2013/05/14 01:34:50
Note: I removed this because it didn't seem to be
|
| - |
| // Returns true of the given dimensions are inside the dimensions of the |
| // level and if the format and type match the level. |
| bool ValidForTexture( |
| @@ -119,7 +120,7 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| GLenum type) const; |
| bool IsValid() const { |
| - return target() && !IsDeleted(); |
| + return !!target(); |
| } |
| void SetNotOwned() { |
| @@ -147,15 +148,13 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| return stream_texture_; |
| } |
| - gpu::AsyncPixelTransferState* GetAsyncTransferState() const { |
| - return async_transfer_state_.get(); |
| - } |
| - void SetAsyncTransferState(scoped_ptr<gpu::AsyncPixelTransferState> state) { |
| - async_transfer_state_ = state.Pass(); |
| - } |
| + // Gets the async transfer state for this texture. Note: the transfer state is |
| + // owned by a single TextureRef. |
| + AsyncPixelTransferState* GetAsyncTransferState() const; |
| + |
| bool AsyncTransferIsInProgress() { |
| - return async_transfer_state_ && |
| - async_transfer_state_->TransferIsInProgress(); |
| + AsyncPixelTransferState* state = GetAsyncTransferState(); |
| + return state && state->TransferIsInProgress(); |
| } |
| void SetImmutable(bool immutable) { |
| @@ -176,10 +175,25 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| private: |
| friend class TextureManager; |
| + friend class TextureRef; |
| friend class TextureTestHelper; |
| - friend class base::RefCounted<Texture>; |
| ~Texture(); |
| + void AddTextureRef(TextureRef* ref); |
| + void RemoveTextureRef(TextureRef* ref, bool have_context); |
| + MemoryTypeTracker* GetMemTracker(); |
| + |
| + // Condition on which this texture is renderable. Can be ONLY_IF_NPOT if it |
| + // depends on context support for non-power-of-two textures (i.e. will be |
| + // renderable if NPOT support is in the context, otherwise not, e.g. texture |
| + // with a NPOT level). ALWAYS means it doesn't depend on context features |
| + // (e.g. complete POT), NEVER means it's not renderable regardless (e.g. |
| + // incomplete). |
| + enum CanRenderCondition { |
| + CAN_RENDER_ALWAYS, |
| + CAN_RENDER_NEVER, |
| + CAN_RENDER_ONLY_IF_NPOT |
| + }; |
| struct LevelInfo { |
| LevelInfo(); |
| @@ -255,10 +269,6 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| // Makes each of the mip levels as though they were generated. |
| bool MarkMipmapsGenerated(const FeatureInfo* feature_info); |
| - void MarkAsDeleted() { |
| - deleted_ = true; |
| - } |
| - |
| bool NeedsMips() const { |
| return min_filter_ != GL_NEAREST && min_filter_ != GL_LINEAR; |
| } |
| @@ -292,18 +302,39 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| const FeatureInfo* feature_info, |
| GLenum target, GLint level, std::string* signature) const; |
| + // Updates the unsafe textures count in all the managers referencing this |
| + // texture. |
| + void UpdateSafeToRenderFrom(bool cleared); |
| + |
| + // Updates the uncleared mip count in all the managers referencing this |
| + // texture. |
| + void UpdateMipCleared(LevelInfo* info, bool cleared); |
| + |
| + // Computes the CanRenderCondition flag. |
| + CanRenderCondition GetCanRenderCondition() const; |
| + |
| + // Updates the unrenderable texture count in all the managers referencing this |
| + // texture. |
| + void UpdateCanRenderCondition(); |
| + |
| + // Increment the framebuffer state change count in all the managers |
| + // referencing this texture. |
| + void IncAllFramebufferStateChangeCount(); |
| + |
| // Info about each face and level of texture. |
| std::vector<std::vector<LevelInfo> > level_infos_; |
| - // The texture manager that manages this Texture. |
| - TextureManager* manager_; |
| + // The texture refs that point to this Texture. |
| + typedef std::set<TextureRef*> RefSet; |
| + RefSet refs_; |
| + |
| + // The single TextureRef that accounts for memory for this texture. Must be |
| + // one of refs_. |
| + TextureRef* memory_tracking_ref_; |
| // The id of the texure |
| GLuint service_id_; |
| - // Whether this texture has been deleted. |
| - bool deleted_; |
| - |
| // Whether all renderable mips of this texture have been cleared. |
| bool cleared_; |
| @@ -345,9 +376,6 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| // Whether this is a special streaming texture. |
| bool stream_texture_; |
| - // State to facilitate async transfers on this texture. |
| - scoped_ptr<gpu::AsyncPixelTransferState> async_transfer_state_; |
| - |
| // Whether the texture is immutable and no further changes to the format |
| // or dimensions of the texture object can be made. |
| bool immutable_; |
| @@ -355,9 +383,55 @@ class GPU_EXPORT Texture : public base::RefCounted<Texture> { |
| // Size in bytes this texture is assumed to take in memory. |
| uint32 estimated_size_; |
| + // Cache of the computed CanRenderCondition flag. |
| + CanRenderCondition can_render_condition_; |
| + |
| DISALLOW_COPY_AND_ASSIGN(Texture); |
| }; |
| +// This class represents a texture in a client context group. It's mostly 1:1 |
| +// with a client id, though it can outlive the client id if it's still bound to |
| +// a FBO or another context when destroyed. |
| +// Multiple TextureRef can point to the same texture with cross-context sharing. |
| +class GPU_EXPORT TextureRef : public base::RefCounted<TextureRef> { |
| + public: |
| + TextureRef(TextureManager* manager, Texture* texture); |
| + static scoped_refptr<TextureRef> Create(TextureManager* manager, |
| + GLuint service_id); |
| + const Texture* texture() const { return texture_; } |
| + Texture* texture() { return texture_; } |
| + GLuint service_id() const { return texture_->service_id(); } |
| + |
| + // Sets the async transfer state for this texture. Only a single TextureRef |
| + // can set this on a given texture at any time. |
| + // NOTE: this should be per-context rather than per-texture. crbug.com/240504 |
| + void SetAsyncTransferState( |
| + scoped_ptr<AsyncPixelTransferState> state) { |
| + DCHECK(!state || !texture_->GetAsyncTransferState()); |
| + async_transfer_state_ = state.Pass(); |
| + } |
| + |
| + private: |
| + friend class base::RefCounted<TextureRef>; |
| + friend class Texture; |
| + friend class TextureManager; |
| + |
| + ~TextureRef(); |
| + const TextureManager* manager() const { return manager_; } |
| + TextureManager* manager() { return manager_; } |
| + AsyncPixelTransferState* async_transfer_state() const { |
| + return async_transfer_state_.get(); |
| + } |
| + |
| + TextureManager* manager_; |
| + Texture* texture_; |
| + |
| + // State to facilitate async transfers on this texture. |
| + scoped_ptr<AsyncPixelTransferState> async_transfer_state_; |
| + |
| + DISALLOW_COPY_AND_ASSIGN(TextureRef); |
| +}; |
| + |
| // This class keeps track of the textures and their sizes so we can do NPOT and |
| // texture complete checking. |
| // |
| @@ -379,6 +453,10 @@ class GPU_EXPORT TextureManager { |
| GLsizei max_cube_map_texture_size); |
| ~TextureManager(); |
| + void set_framebuffer_manager(FramebufferManager* manager) { |
| + framebuffer_manager_ = manager; |
| + } |
| + |
| // Init the texture manager. |
| bool Initialize(); |
| @@ -419,13 +497,13 @@ class GPU_EXPORT TextureManager { |
| // True if this texture meets all the GLES2 criteria for rendering. |
| // See section 3.8.2 of the GLES2 spec. |
| - bool CanRender(const Texture* texture) const { |
| - return texture->CanRender(feature_info_); |
| + bool CanRender(const TextureRef* ref) const { |
| + return ref->texture()->CanRender(feature_info_); |
| } |
| // Returns true if mipmaps can be generated by GL. |
| - bool CanGenerateMipmaps(const Texture* texture) const { |
| - return texture->CanGenerateMipmaps(feature_info_); |
| + bool CanGenerateMipmaps(const TextureRef* ref) const { |
| + return ref->texture()->CanGenerateMipmaps(feature_info_); |
| } |
| // Sets the Texture's target |
| @@ -433,12 +511,12 @@ class GPU_EXPORT TextureManager { |
| // target: GL_TEXTURE_2D or GL_TEXTURE_CUBE_MAP |
| // max_levels: The maximum levels this type of target can have. |
| void SetTarget( |
| - Texture* texture, |
| + TextureRef* ref, |
| GLenum target); |
| // Set the info for a particular level in a TexureInfo. |
| void SetLevelInfo( |
| - Texture* texture, |
| + TextureRef* ref, |
| GLenum target, |
| GLint level, |
| GLenum internal_format, |
| @@ -451,27 +529,27 @@ class GPU_EXPORT TextureManager { |
| bool cleared); |
| // Adapter to call above function. |
| - void SetLevelInfoFromParams(Texture* texture, |
| + void SetLevelInfoFromParams(TextureRef* ref, |
| const gpu::AsyncTexImage2DParams& params) { |
| SetLevelInfo( |
| - texture, params.target, params.level, params.internal_format, |
| + ref, params.target, params.level, params.internal_format, |
| params.width, params.height, 1 /* depth */, |
| params.border, params.format, |
| params.type, true /* cleared */ ); |
| } |
| // Save the texture definition and leave it undefined. |
| - TextureDefinition* Save(Texture* texture); |
| + TextureDefinition* Save(TextureRef* ref); |
| // Redefine all the levels from the texture definition. |
| bool Restore( |
| const char* function_name, |
| GLES2Decoder* decoder, |
| - Texture* texture, |
| + TextureRef* ref, |
| TextureDefinition* definition); |
| // Sets a mip as cleared. |
| - void SetLevelCleared(Texture* texture, GLenum target, |
| + void SetLevelCleared(TextureRef* ref, GLenum target, |
| GLint level, bool cleared); |
| // Sets a texture parameter of a Texture |
| @@ -479,24 +557,24 @@ class GPU_EXPORT TextureManager { |
| // TODO(gman): Expand to SetParameteri,f,iv,fv |
| void SetParameter( |
| const char* function_name, ErrorState* error_state, |
| - Texture* texture, GLenum pname, GLint param); |
| + TextureRef* ref, GLenum pname, GLint param); |
| // Makes each of the mip levels as though they were generated. |
| // Returns false if that's not allowed for the given texture. |
| - bool MarkMipmapsGenerated(Texture* texture); |
| + bool MarkMipmapsGenerated(TextureRef* ref); |
| // Clears any uncleared renderable levels. |
| - bool ClearRenderableLevels(GLES2Decoder* decoder, Texture* texture); |
| + bool ClearRenderableLevels(GLES2Decoder* decoder, TextureRef* ref); |
| // Clear a specific level. |
| bool ClearTextureLevel( |
| - GLES2Decoder* decoder,Texture* texture, GLenum target, GLint level); |
| + GLES2Decoder* decoder, TextureRef* ref, GLenum target, GLint level); |
| // Creates a new texture info. |
| - Texture* CreateTexture(GLuint client_id, GLuint service_id); |
| + TextureRef* CreateTexture(GLuint client_id, GLuint service_id); |
| // Gets the texture info for the given texture. |
| - Texture* GetTexture(GLuint client_id) const; |
| + TextureRef* GetTexture(GLuint client_id) const; |
| // Removes a texture info. |
| void RemoveTexture(GLuint client_id); |
| @@ -504,7 +582,7 @@ class GPU_EXPORT TextureManager { |
| // Gets a client id for a given service id. |
| bool GetClientId(GLuint service_id, GLuint* client_id) const; |
| - Texture* GetDefaultTextureInfo(GLenum target) { |
| + TextureRef* GetDefaultTextureInfo(GLenum target) { |
| switch (target) { |
| case GL_TEXTURE_2D: |
| return default_textures_[kTexture2D]; |
| @@ -555,27 +633,34 @@ class GPU_EXPORT TextureManager { |
| } |
| void SetLevelImage( |
| - Texture* texture, |
| + TextureRef* ref, |
| GLenum target, |
| GLint level, |
| gfx::GLImage* image); |
| void AddToSignature( |
| - Texture* texture, |
| + TextureRef* ref, |
| GLenum target, |
| GLint level, |
| std::string* signature) const; |
| private: |
| friend class Texture; |
| + friend class TextureRef; |
| // Helper for Initialize(). |
| - scoped_refptr<Texture> CreateDefaultAndBlackTextures( |
| + scoped_refptr<TextureRef> CreateDefaultAndBlackTextures( |
| GLenum target, |
| GLuint* black_texture); |
| - void StartTracking(Texture* texture); |
| - void StopTracking(Texture* texture); |
| + void StartTracking(TextureRef* texture); |
| + void StopTracking(TextureRef* texture); |
| + |
| + void UpdateSafeToRenderFrom(int delta); |
| + void UpdateUnclearedMips(int delta); |
| + void UpdateCanRenderCondition(Texture::CanRenderCondition old_condition, |
| + Texture::CanRenderCondition new_condition); |
| + void IncFramebufferStateChangeCount(); |
| MemoryTypeTracker* GetMemTracker(GLenum texture_pool); |
| scoped_ptr<MemoryTypeTracker> memory_tracker_managed_; |
| @@ -583,8 +668,10 @@ class GPU_EXPORT TextureManager { |
| scoped_refptr<FeatureInfo> feature_info_; |
| + FramebufferManager* framebuffer_manager_; |
| + |
| // Info for each texture in the system. |
| - typedef base::hash_map<GLuint, scoped_refptr<Texture> > TextureMap; |
| + typedef base::hash_map<GLuint, scoped_refptr<TextureRef> > TextureMap; |
| TextureMap textures_; |
| GLsizei max_texture_size_; |
| @@ -608,7 +695,7 @@ class GPU_EXPORT TextureManager { |
| GLuint black_texture_ids_[kNumDefaultTextures]; |
| // The default textures for each target (texture name = 0) |
| - scoped_refptr<Texture> default_textures_[kNumDefaultTextures]; |
| + scoped_refptr<TextureRef> default_textures_[kNumDefaultTextures]; |
| DISALLOW_COPY_AND_ASSIGN(TextureManager); |
| }; |