diff options
| author | bunnei <bunneidev@gmail.com> | 2018-09-01 02:42:43 -0400 | 
|---|---|---|
| committer | bunnei <bunneidev@gmail.com> | 2018-09-08 02:53:37 -0400 | 
| commit | 030676b95d8f0c0cd6c288f59daf94bbda6c7133 (patch) | |
| tree | c49f4fc4b5d797b7af730c8292555a748250ab41 | |
| parent | a439f7b6e1ecbaebdba5396fea1c7b171fcd17e8 (diff) | |
gl_rasterizer_cache: Keep track of texture type per surface.
| -rw-r--r-- | src/video_core/renderer_opengl/gl_rasterizer.cpp | 1 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_rasterizer_cache.cpp | 80 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_rasterizer_cache.h | 35 | 
3 files changed, 84 insertions, 32 deletions
diff --git a/src/video_core/renderer_opengl/gl_rasterizer.cpp b/src/video_core/renderer_opengl/gl_rasterizer.cpp index d5bbfbd1c..5deee20dd 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer.cpp +++ b/src/video_core/renderer_opengl/gl_rasterizer.cpp @@ -700,6 +700,7 @@ u32 RasterizerOpenGL::SetupTextures(Maxwell::ShaderStage stage, Shader& shader,          Surface surface = res_cache.GetTextureSurface(texture);          if (surface != nullptr) {              state.texture_units[current_bindpoint].texture = surface->Texture().handle; +            state.texture_units[current_bindpoint].target = surface->Target();              state.texture_units[current_bindpoint].swizzle.r =                  MaxwellToGL::SwizzleSource(texture.tic.x_source);              state.texture_units[current_bindpoint].swizzle.g = diff --git a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp index 0df1bbf6b..4d6fd8b8b 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp +++ b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp @@ -55,6 +55,7 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {      params.size_in_bytes = params.SizeInBytes();      params.cache_width = Common::AlignUp(params.width, 16);      params.cache_height = Common::AlignUp(params.height, 16); +    params.target = SurfaceTargetFromTextureType(config.tic.texture_type);      return params;  } @@ -73,6 +74,7 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {      params.size_in_bytes = params.SizeInBytes();      params.cache_width = Common::AlignUp(params.width, 16);      params.cache_height = Common::AlignUp(params.height, 16); +    params.target = SurfaceTarget::Texture2D;      return params;  } @@ -93,6 +95,7 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {      params.size_in_bytes = params.SizeInBytes();      params.cache_width = Common::AlignUp(params.width, 16);      params.cache_height = Common::AlignUp(params.height, 16); +    params.target = SurfaceTarget::Texture2D;      return params;  } @@ -166,6 +169,26 @@ static constexpr std::array<FormatTuple, SurfaceParams::MaxPixelFormat> tex_form       ComponentType::Float, false}, // Z32FS8  }}; +static GLenum SurfaceTargetToGL(SurfaceParams::SurfaceTarget target) { +    switch (target) { +    case SurfaceParams::SurfaceTarget::Texture1D: +        return GL_TEXTURE_1D; +    case SurfaceParams::SurfaceTarget::Texture2D: +        return GL_TEXTURE_2D; +    case SurfaceParams::SurfaceTarget::Texture3D: +        return GL_TEXTURE_3D; +    case SurfaceParams::SurfaceTarget::Texture1DArray: +        return GL_TEXTURE_1D_ARRAY; +    case SurfaceParams::SurfaceTarget::Texture2DArray: +        return GL_TEXTURE_2D_ARRAY; +    case SurfaceParams::SurfaceTarget::TextureCubemap: +        return GL_TEXTURE_CUBE_MAP; +    } +    LOG_CRITICAL(Render_OpenGL, "Unimplemented texture target={}", static_cast<u32>(target)); +    UNREACHABLE(); +    return {}; +} +  static const FormatTuple& GetFormatTuple(PixelFormat pixel_format, ComponentType component_type) {      ASSERT(static_cast<size_t>(pixel_format) < tex_format_tuples.size());      auto& format = tex_format_tuples[static_cast<unsigned int>(pixel_format)]; @@ -357,33 +380,6 @@ static constexpr std::array<void (*)(u32, u32, u32, std::vector<u8>&, VAddr),          // clang-format on  }; -// Allocate an uninitialized texture of appropriate size and format for the surface -static void AllocateSurfaceTexture(GLuint texture, const FormatTuple& format_tuple, u32 width, -                                   u32 height) { -    OpenGLState cur_state = OpenGLState::GetCurState(); - -    // Keep track of previous texture bindings -    GLuint old_tex = cur_state.texture_units[0].texture; -    cur_state.texture_units[0].texture = texture; -    cur_state.Apply(); -    glActiveTexture(GL_TEXTURE0); - -    if (!format_tuple.compressed) { -        // Only pre-create the texture for non-compressed textures. -        glTexImage2D(GL_TEXTURE_2D, 0, format_tuple.internal_format, width, height, 0, -                     format_tuple.format, format_tuple.type, nullptr); -    } - -    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); -    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); -    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); -    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - -    // Restore previous texture bindings -    cur_state.texture_units[0].texture = old_tex; -    cur_state.Apply(); -} -  static bool BlitTextures(GLuint src_tex, const MathUtil::Rectangle<u32>& src_rect, GLuint dst_tex,                           const MathUtil::Rectangle<u32>& dst_rect, SurfaceType type,                           GLuint read_fb_handle, GLuint draw_fb_handle) { @@ -438,12 +434,34 @@ static bool BlitTextures(GLuint src_tex, const MathUtil::Rectangle<u32>& src_rec      return true;  } -CachedSurface::CachedSurface(const SurfaceParams& params) : params(params) { +CachedSurface::CachedSurface(const SurfaceParams& params) +    : params(params), gl_target(SurfaceTargetToGL(params.target)) {      texture.Create();      const auto& rect{params.GetRect()}; -    AllocateSurfaceTexture(texture.handle, -                           GetFormatTuple(params.pixel_format, params.component_type), -                           rect.GetWidth(), rect.GetHeight()); + +    OpenGLState cur_state = OpenGLState::GetCurState(); + +    // Keep track of previous texture bindings +    GLuint old_tex = cur_state.texture_units[0].texture; +    cur_state.texture_units[0].texture = texture.handle; +    cur_state.Apply(); +    glActiveTexture(GL_TEXTURE0); + +    const auto& format_tuple = GetFormatTuple(params.pixel_format, params.component_type); +    if (!format_tuple.compressed) { +        // Only pre-create the texture for non-compressed textures. +        glTexImage2D(GL_TEXTURE_2D, 0, format_tuple.internal_format, rect.GetWidth(), +                     rect.GetHeight(), 0, format_tuple.format, format_tuple.type, nullptr); +    } + +    glTexParameteri(SurfaceTargetToGL(params.target), GL_TEXTURE_MAX_LEVEL, 0); +    glTexParameteri(SurfaceTargetToGL(params.target), GL_TEXTURE_MIN_FILTER, GL_LINEAR); +    glTexParameteri(SurfaceTargetToGL(params.target), GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); +    glTexParameteri(SurfaceTargetToGL(params.target), GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + +    // Restore previous texture bindings +    cur_state.texture_units[0].texture = old_tex; +    cur_state.Apply();  }  static void ConvertS8Z24ToZ24S8(std::vector<u8>& data, u32 width, u32 height) { diff --git a/src/video_core/renderer_opengl/gl_rasterizer_cache.h b/src/video_core/renderer_opengl/gl_rasterizer_cache.h index b17867f64..6693b5cda 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer_cache.h +++ b/src/video_core/renderer_opengl/gl_rasterizer_cache.h @@ -109,6 +109,33 @@ struct SurfaceParams {          Invalid = 4,      }; +    enum class SurfaceTarget { +        Texture1D, +        Texture2D, +        Texture3D, +        Texture1DArray, +        Texture2DArray, +        TextureCubemap, +    }; + +    static SurfaceTarget SurfaceTargetFromTextureType(Tegra::Texture::TextureType texture_type) { +        switch (texture_type) { +        case Tegra::Texture::TextureType::Texture1D: +            return SurfaceTarget::Texture1D; +        case Tegra::Texture::TextureType::Texture2D: +        case Tegra::Texture::TextureType::Texture2DNoMipmap: +            return SurfaceTarget::Texture2D; +        case Tegra::Texture::TextureType::Texture1DArray: +            return SurfaceTarget::Texture1DArray; +        case Tegra::Texture::TextureType::Texture2DArray: +            return SurfaceTarget::Texture2DArray; +        default: +            LOG_CRITICAL(HW_GPU, "Unimplemented texture_type={}", static_cast<u32>(texture_type)); +            UNREACHABLE(); +            return SurfaceTarget::Texture2D; +        } +    } +      /**       * Gets the compression factor for the specified PixelFormat. This applies to just the       * "compressed width" and "compressed height", not the overall compression factor of a @@ -666,6 +693,7 @@ struct SurfaceParams {      u32 height;      u32 unaligned_height;      size_t size_in_bytes; +    SurfaceTarget target;      // Parameters used for caching only      u32 cache_width; @@ -709,6 +737,10 @@ public:          return texture;      } +    GLenum Target() const { +        return gl_target; +    } +      static constexpr unsigned int GetGLBytesPerPixel(SurfaceParams::PixelFormat format) {          if (format == SurfaceParams::PixelFormat::Invalid)              return 0; @@ -724,13 +756,14 @@ public:      void LoadGLBuffer();      void FlushGLBuffer(); -    // Upload/Download data in gl_buffer in/to this surface's texture +    // Upload data in gl_buffer to this surface's texture      void UploadGLTexture(GLuint read_fb_handle, GLuint draw_fb_handle);  private:      OGLTexture texture;      std::vector<u8> gl_buffer;      SurfaceParams params; +    GLenum gl_target;  };  class RasterizerCacheOpenGL final : public RasterizerCache<Surface> {  | 
