Implemented depth(stencil) textures reading/writing

Implemented swizzled textures reading
Minor fixes
This commit is contained in:
DHrpcs3 2016-03-08 16:45:06 +03:00
parent 8e57cf8da8
commit 220d48a980
9 changed files with 280 additions and 72 deletions

View File

@ -31,21 +31,69 @@ namespace
throw EXCEPTION("Unknow depth format");
}
u32 to_gl_internal_type(rsx::vertex_base_type type, u8 size)
gl::texture::sized_internal_format to_gl_internal_type(rsx::vertex_base_type type, u8 size)
{
/**
* The buffer texture spec only allows fetches aligned to 8, 16, 32, etc...
* This rules out most 3-component formats, except for the 32-wide RGB32F, RGB32I, RGB32UI
*/
const u32 vec1_types[] = { GL_R16, GL_R32F, GL_R16F, GL_R8, GL_R16I, GL_R16, GL_R8UI };
const u32 vec2_types[] = { GL_RG16, GL_RG32F, GL_RG16F, GL_RG8, GL_RG16I, GL_RG16, GL_RG8UI };
const u32 vec3_types[] = { GL_RGBA16, GL_RGB32F, GL_RGBA16F, GL_RGBA8, GL_RGBA16I, GL_RGBA16, GL_RGBA8UI }; //VEC3 COMPONENTS NOT SUPPORTED!
const u32 vec4_types[] = { GL_RGBA16, GL_RGBA32F, GL_RGBA16F, GL_RGBA8, GL_RGBA16I, GL_RGBA16, GL_RGBA8UI };
static const gl::texture::sized_internal_format vec1_types[]
{
gl::texture::sized_internal_format::r16,
gl::texture::sized_internal_format::r32f,
gl::texture::sized_internal_format::r16f,
gl::texture::sized_internal_format::r8,
gl::texture::sized_internal_format::r16i,
gl::texture::sized_internal_format::r16,
gl::texture::sized_internal_format::r8ui
};
const u32* vec_selectors[] = { 0, vec1_types, vec2_types, vec3_types, vec4_types };
static const gl::texture::sized_internal_format vec2_types[]
{
gl::texture::sized_internal_format::rg16,
gl::texture::sized_internal_format::rg32f,
gl::texture::sized_internal_format::rg16f,
gl::texture::sized_internal_format::rg8,
gl::texture::sized_internal_format::rg16i,
gl::texture::sized_internal_format::rg16,
gl::texture::sized_internal_format::rg8ui
};
static const gl::texture::sized_internal_format vec3_types[] //VEC3 COMPONENTS NOT SUPPORTED!
{
gl::texture::sized_internal_format::rgba16,
gl::texture::sized_internal_format::rgb32f,
gl::texture::sized_internal_format::rgba16f,
gl::texture::sized_internal_format::rgba8,
gl::texture::sized_internal_format::rgba16i,
gl::texture::sized_internal_format::rgba16,
gl::texture::sized_internal_format::rgba8ui
};
static const gl::texture::sized_internal_format vec4_types[]
{
gl::texture::sized_internal_format::rgba16,
gl::texture::sized_internal_format::rgba32f,
gl::texture::sized_internal_format::rgba16f,
gl::texture::sized_internal_format::rgba8,
gl::texture::sized_internal_format::rgba16i,
gl::texture::sized_internal_format::rgba16,
gl::texture::sized_internal_format::rgba8ui
};
static const gl::texture::sized_internal_format* vec_selectors[]
{
nullptr,
vec1_types,
vec2_types,
vec3_types,
vec4_types
};
if (type > rsx::vertex_base_type::ub256)
{
throw EXCEPTION("OpenGL error: unknown vertex base type 0x%X.", (u32)type);
}
return vec_selectors[size][(int)type];
}
@ -189,9 +237,9 @@ void GLGSRender::begin()
if (u32 blend_mrt = rsx::method_registers[NV4097_SET_BLEND_ENABLE_MRT])
{
__glcheck enable(blend_mrt & 2, GL_BLEND, GL_COLOR_ATTACHMENT1);
__glcheck enable(blend_mrt & 4, GL_BLEND, GL_COLOR_ATTACHMENT2);
__glcheck enable(blend_mrt & 8, GL_BLEND, GL_COLOR_ATTACHMENT3);
__glcheck enable(blend_mrt & 2, GL_BLEND, 1);
__glcheck enable(blend_mrt & 4, GL_BLEND, 2);
__glcheck enable(blend_mrt & 8, GL_BLEND, 3);
}
if (__glcheck enable(rsx::method_registers[NV4097_SET_LOGIC_OP_ENABLE], GL_LOGIC_OP))
@ -347,7 +395,7 @@ namespace
case rsx::vertex_base_type::ub: return gl::buffer_pointer::type::u8;
case rsx::vertex_base_type::s32k: return gl::buffer_pointer::type::s32;
case rsx::vertex_base_type::cmp: return gl::buffer_pointer::type::s16; // Needs conversion
case rsx::vertex_base_type::ub256: gl::buffer_pointer::type::u8;
case rsx::vertex_base_type::ub256: return gl::buffer_pointer::type::u8;
}
throw EXCEPTION("unknow vertex type");
}
@ -389,7 +437,7 @@ void GLGSRender::end()
int location;
if (m_program->uniforms.has_location("tex" + std::to_string(i), &location))
{
__glcheck rsx::gl_texture::bind(m_texture_cache, i, textures[i]);
__glcheck rsx::gl_texture::bind(m_texture_cache, textures[i]);
__glcheck glProgramUniform1i(m_program->id(), location, i);
}
}
@ -472,7 +520,7 @@ void GLGSRender::end()
const u32 element_size = rsx::get_vertex_type_size_on_host(vertex_info.type, vertex_info.size);
u32 data_size = element_size * vertex_draw_count;
u32 gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
gl::texture::sized_internal_format gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
auto &buffer = m_gl_attrib_buffers[index].buffer;
auto &texture = m_gl_attrib_buffers[index].texture;
@ -530,7 +578,7 @@ void GLGSRender::end()
if (!enabled)
{
glActiveTexture(GL_TEXTURE0 + index + rsx::limits::textures_count);
glBindTexture(GL_TEXTURE_BUFFER, NULL);
glBindTexture(GL_TEXTURE_BUFFER, 0);
glProgramUniform1i(m_program->id(), location, index + rsx::limits::textures_count);
continue;
}
@ -573,16 +621,11 @@ void GLGSRender::end()
vertex_arrays_offsets[index] = gsl::narrow<u32>(position);
vertex_arrays_data.resize(position + size);
u32 gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
u32 data_size = element_size * vertex_draw_count;
gl::texture::sized_internal_format gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
auto& attrib_pair = m_gl_attrib_buffers[index];
__glcheck 0;
attrib_pair.buffer.data(data_size, vertex_array.data());
__glcheck 0;
attrib_pair.buffer.data(vertex_array.size(), vertex_array.data());
//Attach buffer to texture
attrib_pair.texture.copy_from(attrib_pair.buffer, gl_type);
@ -601,12 +644,11 @@ void GLGSRender::end()
case rsx::vertex_base_type::f:
{
const u32 element_size = rsx::get_vertex_type_size_on_host(vertex_info.type, vertex_info.size);
const u32 gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
const size_t data_size = vertex_data.size();
gl::texture::sized_internal_format gl_type = to_gl_internal_type(vertex_info.type, vertex_info.size);
auto& attrib_pair = m_gl_attrib_buffers[index];
attrib_pair.buffer.data(data_size, vertex_data.data());
attrib_pair.buffer.data(vertex_data.size(), vertex_data.data());
//Attach buffer to texture
attrib_pair.texture.copy_from(attrib_pair.buffer, gl_type);
@ -623,7 +665,7 @@ void GLGSRender::end()
else
{
glActiveTexture(GL_TEXTURE0 + index + rsx::limits::textures_count);
glBindTexture(GL_TEXTURE_BUFFER, NULL);
glBindTexture(GL_TEXTURE_BUFFER, 0);
glProgramUniform1i(m_program->id(), location, index + rsx::limits::textures_count);
continue;
}
@ -1080,7 +1122,7 @@ u32 surface_format_to_texture_format(rsx::surface_color_format format)
gl::texture_info surface_info(rsx::surface_color_format format, u32 offset, u32 location, u32 width, u32 height, u32 pitch)
{
gl::texture_info info;
gl::texture_info info{};
info.width = width;
info.height = height;
@ -1089,6 +1131,8 @@ gl::texture_info surface_info(rsx::surface_color_format format, u32 offset, u32
info.compressed_size = 0;
info.target = gl::texture::target::texture2D;
info.dimension = 2;
//TODO
info.swizzled = false;
info.start_address = rsx::get_address(offset, location);
info.format = gl::get_texture_format(surface_format_to_texture_format(format));
@ -1144,7 +1188,7 @@ void GLGSRender::init_buffers(bool skip_reading)
u32 location = rsx::method_registers[mr_color_dma[index]];
u32 pitch = rsx::method_registers[mr_color_pitch[index]];
if (!location)
if (pitch <= 64)
{
cached_color_buffers[index] = nullptr;
draw_fbo.color[index] = null_texture;
@ -1162,14 +1206,14 @@ void GLGSRender::init_buffers(bool skip_reading)
u32 location = rsx::method_registers[NV4097_SET_CONTEXT_DMA_ZETA];
u32 pitch = rsx::method_registers[NV4097_SET_SURFACE_PITCH_Z];
if (!location)
if (pitch <= 64)
{
cached_depth_buffer = nullptr;
draw_fbo.depth_stencil = null_texture;
}
else
{
gl::texture_info info;
gl::texture_info info{};
info.width = m_surface.width;
info.height = m_surface.height;
@ -1179,6 +1223,8 @@ void GLGSRender::init_buffers(bool skip_reading)
info.compressed_size = 0;
info.start_address = rsx::get_address(offset, location);
info.target = gl::texture::target::texture2D;
//TODO
info.swizzled = false;
switch (m_surface.depth_format)
{
@ -1203,24 +1249,24 @@ void GLGSRender::init_buffers(bool skip_reading)
}
info.format.remap = { GL_ZERO, GL_ZERO, GL_ZERO, GL_ZERO };
cached_depth_buffer = &m_texture_cache.entry(info, skip_reading ? gl::cache_buffers::none : gl::cache_buffers::local);
__glcheck 0;
__glcheck cached_depth_buffer = &m_texture_cache.entry(info, skip_reading ? gl::cache_buffers::none : gl::cache_buffers::local);
switch (m_surface.depth_format)
{
case rsx::surface_depth_format::z16:
draw_fbo.depth = cached_depth_buffer->view();
__glcheck draw_fbo.depth = cached_depth_buffer->view();
break;
case rsx::surface_depth_format::z24s8:
draw_fbo.depth_stencil = cached_depth_buffer->view();
__glcheck draw_fbo.depth_stencil = cached_depth_buffer->view();
break;
}
}
}
draw_fbo.bind();
__glcheck draw_fbo.bind();
{
auto info = rsx::get_active_color_surfaces();
@ -1233,7 +1279,7 @@ void GLGSRender::init_buffers(bool skip_reading)
GL_COLOR_ATTACHMENT3
};
glDrawBuffers(info.second, color_buffers + info.first);
__glcheck glDrawBuffers(info.second, color_buffers + info.first);
}
set_viewport();
@ -1323,7 +1369,7 @@ bool GLGSRender::on_access_violation(u32 address, bool is_writing)
{
if (auto region = m_texture_cache.find_region(address))
{
std::lock_guard<gl::protected_region> lock(*region);
//std::lock_guard<gl::protected_region> lock(*region);
if (is_writing)
{

View File

@ -173,6 +173,10 @@ OPENGL_PROC(PFNGLTEXTUREBUFFERRANGEEXTPROC, TextureBufferRangeEXT);
OPENGL_PROC(PFNGLTEXSTORAGE1DPROC, TexStorage1D);
OPENGL_PROC(PFNGLTEXSTORAGE2DPROC, TexStorage2D);
OPENGL_PROC(PFNGLTEXSTORAGE3DPROC, TexStorage3D);
OPENGL_PROC(PFNGLCOMPRESSEDTEXSUBIMAGE1DPROC, CompressedTexSubImage1D);
OPENGL_PROC(PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC, CompressedTexSubImage2D);
OPENGL_PROC(PFNGLCOMPRESSEDTEXSUBIMAGE3DPROC, CompressedTexSubImage3D);
OPENGL_PROC(PFNGLCLEARTEXIMAGEPROC, ClearTexImage);
//ARB_Copy_Image
OPENGL_PROC(PFNGLCOPYIMAGESUBDATAPROC, CopyImageSubData);

View File

@ -810,6 +810,7 @@ namespace gl
r32f = GL_R32F,
r8ui = GL_R8UI,
r8i = GL_R8I,
r16 = GL_R16,
r16ui = GL_R16UI,
r16i = GL_R16I,
r32ui = GL_R32UI,
@ -820,6 +821,7 @@ namespace gl
rg32f = GL_RG32F,
rg8ui = GL_RG8UI,
rg8i = GL_RG8I,
rg16 = GL_RG16,
rg16ui = GL_RG16UI,
rg16i = GL_RG16I,
rg32ui = GL_RG32UI,
@ -830,6 +832,7 @@ namespace gl
rgb8_snorm = GL_RGB8_SNORM,
r11f_g11f_b10f = GL_R11F_G11F_B10F,
rgb9_e5 = GL_RGB9_E5,
rgb16 = GL_RGB16,
rgb16f = GL_RGB16F,
rgb32f = GL_RGB32F,
rgb8ui = GL_RGB8UI,
@ -849,6 +852,7 @@ namespace gl
rgba8ui = GL_RGBA8UI,
rgba8i = GL_RGBA8I,
rgb10_a2ui = GL_RGB10_A2UI,
rgba16 = GL_RGBA16,
rgba16ui = GL_RGBA16UI,
rgba16i = GL_RGBA16I,
rgba32i = GL_RGBA32I,
@ -1203,27 +1207,27 @@ namespace gl
__glcheck glTexSubImage2D((GLenum)get_target(), level(), 0, 0, width(), height(), (GLenum)format, (GLenum)type, src);
}
void copy_from(buffer &buf, u32 gl_format_type, u32 offset, u32 length)
void copy_from(const buffer &buf, gl::texture::sized_internal_format format, u32 offset, u32 length)
{
if (get_target() != target::texture_buffer)
throw EXCEPTION("OpenGL error: texture cannot copy from buffer");
if (!offset)
{
copy_from(buf, gl_format_type);
copy_from(buf, format);
return;
}
if (glTextureBufferRangeEXT == nullptr)
throw EXCEPTION("OpenGL error: partial buffer access for textures is unsupported on your system");
__glcheck glTextureBufferRangeEXT(id(), (GLenum)target::texture_buffer, gl_format_type, buf.id(), offset, length);
__glcheck glTextureBufferRangeEXT(id(), (GLenum)target::texture_buffer, (GLenum)format, buf.id(), offset, length);
}
void copy_from(buffer &buf, u32 gl_format_type)
void copy_from(const buffer &buf, gl::texture::sized_internal_format format)
{
save_binding_state save(*this);
__glcheck glTexBuffer((GLenum)target::texture_buffer, gl_format_type, buf.id());
__glcheck glTexBuffer((GLenum)target::texture_buffer, (GLenum)format, buf.id());
}
void copy_from(const buffer& buf, texture::format format, texture::type type, class pixel_unpack_settings pixel_settings)

View File

@ -3,6 +3,7 @@
#include "gl_texture_cache.h"
#include "GLGSRender.h"
#include "../Common/TextureUtils.h"
#include "../rsx_utils.h"
#include <exception>
#include <string>
@ -40,9 +41,7 @@ namespace gl
if (found_texture)
{
//read from local
LOG_WARNING(RSX, "cached_texture at 0x%x reading from local buffer", info->start_address);
glCopyImageSubData(
__glcheck glCopyImageSubData(
found_texture->gl_name, (GLenum)found_texture->info->target, 0, 0, 0, 0,
gl_name, (GLenum)info->target, 0, 0, 0, 0,
info->width, info->height, info->depth);
@ -60,23 +59,92 @@ namespace gl
if (info->format.format == gl::texture::format::depth || info->format.format == gl::texture::format::depth_stencil)
{
LOG_ERROR(RSX, "cached_texture at 0x%x: unimplemented reading depth(stencil) from host buffer", info->start_address);
gl::buffer pbo_depth;
//TODO
__glcheck pbo_depth.create(info->pitch * info->height);
__glcheck pbo_depth.map([&](GLubyte* pixels)
{
switch (info->format.bpp)
{
case 2:
{
u16 *dst = (u16*)pixels;
const be_t<u16>* src = (const be_t<u16>*)vm::base_priv(info->start_address);
for (u32 i = 0, end = info->pitch / info->format.bpp * info->height; i < end; ++i)
{
dst[i] = src[i];
}
}
break;
case 4:
{
u32 *dst = (u32*)pixels;
const be_t<u32>* src = (const be_t<u32>*)vm::base_priv(info->start_address);
for (u32 i = 0, end = info->pitch / info->format.bpp * info->height; i < end; ++i)
{
dst[i] = src[i];
}
}
break;
default:
throw EXCEPTION("");
}
}, gl::buffer::access::write);
gl::pixel_unpack_settings{}
.row_length(info->pitch / info->format.bpp)
.aligment(1)
.swap_bytes((info->format.flags & gl::texture_flags::swap_bytes) != gl::texture_flags::none)
.apply();
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, pbo_depth.id());
__glcheck 0;
__glcheck glTexSubImage2D((GLenum)info->target, 0, 0, 0, info->width, info->height,
(GLenum)info->format.format, (GLenum)info->format.type, nullptr);
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, 0);
}
else if (info->compressed_size)
{
LOG_WARNING(RSX, "cached_texture at 0x%x: reading compressed texture from host buffer", info->start_address);
__glcheck glCompressedTexImage2D((GLenum)info->target, 0,
__glcheck glCompressedTexSubImage2D((GLenum)info->target, 0,
0, 0, info->width, info->height,
(GLenum)info->format.internal_format,
info->width, info->height,
0,
info->compressed_size, vm::base_priv(info->start_address));
}
else
{
LOG_WARNING(RSX, "cached_texture at 0x%x reading from host buffer", info->start_address);
void *pixels = vm::base_priv(info->start_address);
std::unique_ptr<u8[]> linear_pixels;
if (info->swizzled && (info->format.flags & texture_flags::allow_swizzle) != texture_flags::none)
{
linear_pixels.reset(new u8[info->size()]);
switch (info->format.bpp)
{
case 1:
rsx::convert_linear_swizzle<u8>(pixels, linear_pixels.get(), info->width, info->height, true);
break;
case 2:
rsx::convert_linear_swizzle<u16>(pixels, linear_pixels.get(), info->width, info->height, true);
break;
case 4:
rsx::convert_linear_swizzle<u32>(pixels, linear_pixels.get(), info->width, info->height, true);
break;
case 8:
rsx::convert_linear_swizzle<u64>(pixels, linear_pixels.get(), info->width, info->height, true);
break;
default:
throw EXCEPTION("");
}
pixels = linear_pixels.get();
}
gl::pixel_unpack_settings{}
.row_length(info->pitch / info->format.bpp)
@ -85,7 +153,7 @@ namespace gl
.apply();
__glcheck glTexSubImage2D((GLenum)info->target, 0, 0, 0, info->width, info->height,
(GLenum)info->format.format, (GLenum)info->format.type, vm::base_priv(info->start_address));
(GLenum)info->format.format, (GLenum)info->format.type, pixels);
}
}
@ -94,15 +162,55 @@ namespace gl
void cached_texture::write()
{
LOG_WARNING(RSX, "cached_texture at 0x%x writing to host buffer", info->start_address);
bind();
if (info->format.format == gl::texture::format::depth || info->format.format == gl::texture::format::depth_stencil)
{
LOG_ERROR(RSX, "cached_texture at 0x%x: unimplemented writing depth(stencil) to host buffer", info->start_address);
gl::buffer pbo_depth;
//TODO
pbo_depth.create(info->pitch * info->height);
gl::pixel_pack_settings{}
.row_length(info->pitch / info->format.bpp)
.aligment(1)
.swap_bytes((info->format.flags & gl::texture_flags::swap_bytes) != gl::texture_flags::none)
.apply();
glBindBuffer(GL_PIXEL_PACK_BUFFER, pbo_depth.id());
__glcheck glGetTexImage((GLenum)info->target, 0, (GLenum)info->format.format, (GLenum)info->format.type, nullptr);
glBindBuffer(GL_PIXEL_PACK_BUFFER, 0);
__glcheck pbo_depth.map([&](GLubyte* pixels)
{
switch (info->format.bpp)
{
case 2:
{
const u16 *src = (const u16*)pixels;
be_t<u16>* dst = (be_t<u16>*)vm::base_priv(info->start_address);
for (u32 i = 0, end = info->pitch / info->format.bpp * info->height; i < end; ++i)
{
dst[i] = src[i];
}
}
break;
case 4:
{
const u32 *src = (const u32*)pixels;
be_t<u32>* dst = (be_t<u32>*)vm::base_priv(info->start_address);
for (u32 i = 0, end = info->pitch / info->format.bpp * info->height; i < end; ++i)
{
dst[i] = src[i];
}
}
break;
default:
throw EXCEPTION("");
}
}, gl::buffer::access::read);
}
else if (info->compressed_size)
{
@ -110,13 +218,19 @@ namespace gl
}
else
{
if (info->swizzled && (info->format.flags & texture_flags::allow_swizzle) != texture_flags::none)
{
//TODO
LOG_ERROR(RSX, "writing swizzled texture[0x%x] to host buffer", info->start_address);
}
gl::pixel_pack_settings{}
.row_length(info->pitch / info->format.bpp)
.aligment(1)
.swap_bytes((info->format.flags & gl::texture_flags::swap_bytes) != gl::texture_flags::none)
.apply();
glGetTexImage((GLenum)info->target, 0, (GLenum)info->format.format, (GLenum)info->format.type, vm::base_priv(info->start_address));
__glcheck glGetTexImage((GLenum)info->target, 0, (GLenum)info->format.format, (GLenum)info->format.type, vm::base_priv(info->start_address));
}
ignore(gl::cache_buffers::all);
@ -126,7 +240,7 @@ namespace gl
{
if (!created())
{
create();
__glcheck create();
}
switch (m_state)
@ -135,7 +249,7 @@ namespace gl
case cache_entry_state::host_synchronized:
if ((buffers & cache_buffers::local) != cache_buffers::none)
{
read();
__glcheck read();
return true;
}
break;
@ -254,11 +368,9 @@ namespace gl
glGenTextures(1, &gl_name);
if (!info->compressed_size)
{
bind();
__glcheck glTexStorage2D((GLenum)info->target, 1, (GLenum)info->format.internal_format, info->width, info->height);
}
bind();
__glcheck glTexStorage2D((GLenum)info->target, 1, (GLenum)info->format.internal_format, info->width, info->height);
//__glcheck glClearTexImage(gl_name, 0, (GLenum)info->format.format, (GLenum)info->format.type, nullptr);
}
void cached_texture::remove()
@ -331,7 +443,7 @@ namespace gl
if (m_current_protection != flags)
{
LOG_WARNING(RSX, "protection region [0x%x, 0x%x)", start_address, start_address + size());
LOG_WARNING(RSX, "protected region [0x%x, 0x%x)", start_address, start_address + size());
vm::page_protect(start_address, size(), 0, m_current_protection & ~flags, flags);
m_current_protection = flags;
}
@ -449,8 +561,31 @@ namespace gl
cached_texture &texture_cache::entry(const texture_info &info, cache_buffers sync)
{
u32 aligned_address = info.start_address & ~(vm::page_size - 1);
u32 aligned_size = align(info.size(), vm::page_size);
//u32 aligned_address = info.start_address & ~(vm::page_size - 1);
u32 aligned_address;
u32 aligned_size;
const bool accurate_cache = false;
if (accurate_cache)
{
aligned_address = info.start_address & ~(vm::page_size - 1);
aligned_size = align(info.start_address - aligned_address + info.size(), vm::page_size);
}
else
{
aligned_size = info.size() & ~(vm::page_size - 1);
if (!aligned_size)
{
aligned_address = info.start_address & ~(vm::page_size - 1);
aligned_size = align(info.size() + info.start_address - aligned_address, vm::page_size);
}
else
{
aligned_address = align(info.start_address, vm::page_size);
}
}
std::vector<protected_region*> regions = find_regions(aligned_address, aligned_size);
protected_region *region;

View File

@ -2,6 +2,7 @@
#include <vector>
#include "Utilities/types.h"
#include "gl_helpers.h"
#include <array>
namespace gl
{
@ -63,6 +64,7 @@ namespace gl
texture::target target;
texture_format format;
bool swizzled;
u32 start_address;

View File

@ -136,7 +136,7 @@ int wrap(int wrap)
}
void rsx::gl_texture::bind(gl::texture_cache& cache, int index, rsx::texture& tex)
void rsx::gl_texture::bind(gl::texture_cache& cache, rsx::texture& tex)
{
u32 full_format = tex.format();
u32 format = full_format & ~(CELL_GCM_TEXTURE_LN | CELL_GCM_TEXTURE_UN);
@ -145,7 +145,7 @@ void rsx::gl_texture::bind(gl::texture_cache& cache, int index, rsx::texture& te
gl::texture::target target = is_normalized ? gl::texture::target::texture2D : gl::texture::target::texture_rectangle;
glActiveTexture(GL_TEXTURE0 + index);
glActiveTexture(GL_TEXTURE0 + tex.index());
gl::texture_view(target, 0).bind();
if (!tex.enabled())
@ -166,6 +166,7 @@ void rsx::gl_texture::bind(gl::texture_cache& cache, int index, rsx::texture& te
info.dimension = tex.dimension();
info.start_address = rsx::get_address(tex.offset(), tex.location());
info.target = target;
info.swizzled = is_swizzled;
if (is_compressed)
{
@ -218,7 +219,7 @@ void rsx::gl_texture::bind(gl::texture_cache& cache, int index, rsx::texture& te
remap = info.format.remap.data();
}
__glcheck cache.entry(info, gl::cache_buffers::local).bind(index);
__glcheck cache.entry(info, gl::cache_buffers::local).bind(tex.index());
__glcheck glTexParameteri((GLenum)target, GL_TEXTURE_MAX_LEVEL, tex.mipmap() - 1);
__glcheck glTexParameteri((GLenum)target, GL_GENERATE_MIPMAP, tex.mipmap() > 1);

View File

@ -18,7 +18,7 @@ namespace rsx
namespace gl_texture
{
void bind(gl::texture_cache& cache, int index, rsx::texture& tex);
void bind(gl::texture_cache& cache, rsx::texture& tex);
}
}

View File

@ -210,6 +210,11 @@ namespace rsx
return method_registers[NV4097_SET_TEXTURE_CONTROL3 + m_index] & 0xfffff;
}
u8 texture::index() const
{
return m_index;
}
void vertex_texture::init(u8 index)
{
m_index = index;
@ -393,4 +398,9 @@ namespace rsx
{
return method_registers[NV4097_SET_VERTEX_TEXTURE_CONTROL3 + (m_index * 8)] & 0xfffff;
}
u8 vertex_texture::index() const
{
return m_index;
}
}

View File

@ -561,7 +561,10 @@ namespace rsx
else
{
++m_internal_task_waiters;
add_internal_task(callback).wait();
while (add_internal_task(callback).wait_for(1s) == std::future_status::timeout)
{
CHECK_EMU_STATUS;
}
--m_internal_task_waiters;
}
}
@ -737,6 +740,9 @@ namespace rsx
method_registers[NV4097_SET_BLEND_COLOR2] = 0;
method_registers[NV4097_SET_BLEND_EQUATION] = (CELL_GCM_FUNC_ADD << 16) | CELL_GCM_FUNC_ADD;
method_registers[NV4097_SET_STENCIL_TEST_ENABLE] = false;
method_registers[NV4097_SET_DEPTH_TEST_ENABLE] = false;
method_registers[NV4097_SET_STENCIL_MASK] = 0xff;
method_registers[NV4097_SET_STENCIL_FUNC] = CELL_GCM_ALWAYS;
method_registers[NV4097_SET_STENCIL_FUNC_REF] = 0x00;