<div dir="ltr">Looks ok for me. Couple questions:<div><br></div><div>1. Is there any reason to have "<span style="font-size:small;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">glEnable(GL_FRAMEBUFFER_SRGB);" inside loop?</span></div><div><span style="font-size:small;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">2. Would it be better to restore old <span style="text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">GL_FRAMEBUFFER_SRGB state instead of disabling it?</span></span></div></div><br><div class="gmail_quote"><div dir="ltr">On Thu, Jul 19, 2018 at 5:03 AM Gert Wollny <<a href="mailto:gert.wollny@collabora.com">gert.wollny@collabora.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">On an GL host set the sRGB framebuffer state explicitly to make virgl<br>
behave like on a GLES host.<br>
<br>
This does not correct the handing of sRGB completely, because the state<br>
GL_FRAMEBUFFER_SRGB is not properly transmitted to the host. As a result<br>
the piglits "blit texture linear_to_srgb * * *" flip.<br>
Tests thatset "enable" failed before and pass now, and tests that set "disable"<br>
now fail.<br>
<br>
Fixes on GL host:<br>
dEQP-GLES3.functional.fbo.blit.conversion.rgb8_to_srgb8_alpha8<br>
dEQP-GLES3.functional.fbo.blit.default_framebuffer.srgb8_alpha8<br>
<br>
Signed-off-by: Gert Wollny <<a href="mailto:gert.wollny@collabora.com" target="_blank">gert.wollny@collabora.com</a>><br>
---<br>
<br>
Since this doesn't correct the piglits, only flips some of them, I thought I <br>
might add a comment about the problems fixing this, I'm actually not sure<br>
whether handling GL_FRAMEBUFFER_SRGB can really be fixed in a reliable way <br>
considering the approach how framebuffers and blits are implemented: On one <br>
hand, the state GL_FRAMEBUFFER_SRGB is currently not transmitted to the host,<br>
but even if it would be, one still would have to guess to which framebuffer it<br>
refers, because the guest never sends information about which framebuffers are<br>
currently bound: This is handled within the mesa code, and Gallium isn't<br>
notified about changes in binding.<br>
<br>
On the other hand, if GL_FRAMEBUFFER_SRGB is disabled, but an sRGB surface is <br>
bound to the framebuffer then the framebuffer's state is updated by attaching <br>
a non-sRGB surface that is also created on the host as a texture view. Then the<br>
changed state is then send to the host via VIRGL_CCMD_SET_FRAMEBUFFER_STATE, <br>
but the command doesn't have any information about *which* framebuffer's state <br>
must be set, since Gallium doesn't know this and virglrenderer always sets the<br>
state of the current sub-context's default fb.<br>
<br>
Now, when virglrenderer enters vrend_renderer_blit_int it references the <br>
original textures with there original formats, and when GL_FRAMEBUFFER_SRGB is <br>
disabled things go wrong. <br>
<br>
The only approach for guessing the right state I could think of is, to change <br>
Gallium to send the changed GL_FRAMEBUFFER_SRGB state, and when a blit comes up, <br>
to check whether the target texture is sRGB has a texture view that has the <br>
corresponding linear format and has otherwise the same parameters. <br>
<br>
Thanks for any comments and for reviewing the patch, <br>
Gert<br>
<br>
src/vrend_blitter.c | 19 ++++++++++++++++++-<br>
src/vrend_renderer.c | 9 ++++++++-<br>
src/vrend_renderer.h | 3 ++-<br>
3 files changed, 28 insertions(+), 3 deletions(-)<br>
<br>
diff --git a/src/vrend_blitter.c b/src/vrend_blitter.c<br>
index 68b5bab..1439c9b 100644<br>
--- a/src/vrend_blitter.c<br>
+++ b/src/vrend_blitter.c<br>
@@ -686,7 +686,8 @@ static void calc_dst_deltas_from_src(const struct pipe_blit_info *info,<br>
void vrend_renderer_blit_gl(UNUSED struct vrend_context *ctx,<br>
struct vrend_resource *src_res,<br>
struct vrend_resource *dst_res,<br>
- const struct pipe_blit_info *info)<br>
+ const struct pipe_blit_info *info,<br>
+ bool use_gles)<br>
{<br>
struct vrend_blitter_ctx *blit_ctx = &vrend_blit_ctx;<br>
GLuint buffers;<br>
@@ -787,6 +788,8 @@ void vrend_renderer_blit_gl(UNUSED struct vrend_context *ctx,<br>
to_gl_swizzle(src_entry->swizzle[3]));<br>
}<br>
<br>
+ if (!use_gles && util_format_is_srgb(src_res->base.format))<br>
+ glTexParameteri(src_res->target, GL_TEXTURE_SRGB_DECODE_EXT, GL_DECODE_EXT);<br>
<br>
glTexParameteri(src_res->target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);<br>
glTexParameteri(src_res->target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);<br>
@@ -820,6 +823,13 @@ void vrend_renderer_blit_gl(UNUSED struct vrend_context *ctx,<br>
glBindFramebuffer(GL_FRAMEBUFFER_EXT, blit_ctx->fb_id);<br>
vrend_fb_bind_texture(dst_res, 0, info->dst.level, layer);<br>
<br>
+ if (!use_gles) {<br>
+ if (util_format_is_srgb(dst_res->base.format))<br>
+ glEnable(GL_FRAMEBUFFER_SRGB);<br>
+ else<br>
+ glDisable(GL_FRAMEBUFFER_SRGB);<br>
+ }<br>
+<br>
buffers = GL_COLOR_ATTACHMENT0_EXT;<br>
glDrawBuffers(1, &buffers);<br>
blitter_set_texcoords(blit_ctx, src_res, info->src.level,<br>
@@ -829,4 +839,11 @@ void vrend_renderer_blit_gl(UNUSED struct vrend_context *ctx,<br>
glBufferData(GL_ARRAY_BUFFER, sizeof(blit_ctx->vertices), blit_ctx->vertices, GL_STATIC_DRAW);<br>
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);<br>
}<br>
+ if (!use_gles) {<br>
+ if (util_format_is_srgb(dst_res->base.format))<br>
+ glDisable(GL_FRAMEBUFFER_SRGB);<br>
+<br>
+ if (util_format_is_srgb(src_res->base.format))<br>
+ glTexParameteri(src_res->target, GL_TEXTURE_SRGB_DECODE_EXT, GL_DECODE_EXT);<br>
+ }<br>
}<br>
diff --git a/src/vrend_renderer.c b/src/vrend_renderer.c<br>
index e357bae..8b3e513 100644<br>
--- a/src/vrend_renderer.c<br>
+++ b/src/vrend_renderer.c<br>
@@ -6571,7 +6571,7 @@ static void vrend_renderer_blit_int(struct vrend_context *ctx,<br>
use_gl = !vrend_formats_can_blit(tex_conv_table, src_res->base.format, dst_res->base.format);<br>
<br>
if (use_gl) {<br>
- vrend_renderer_blit_gl(ctx, src_res, dst_res, info);<br>
+ vrend_renderer_blit_gl(ctx, src_res, dst_res, info, vrend_state.use_gles);<br>
vrend_clicbs->make_current(0, ctx->sub->gl_context);<br>
return;<br>
}<br>
@@ -6690,6 +6690,13 @@ static void vrend_renderer_blit_int(struct vrend_context *ctx,<br>
vrend_fb_bind_texture(dst_res, 0, info->dst.level, info->dst.box.z + i);<br>
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, ctx->sub->blit_fb_ids[1]);<br>
<br>
+ if (!vrend_state.use_gles) {<br>
+ if (util_format_is_srgb(dst_res->base.format))<br>
+ glEnable(GL_FRAMEBUFFER_SRGB);<br>
+ else<br>
+ glDisable(GL_FRAMEBUFFER_SRGB);<br>
+ }<br>
+<br>
glBindFramebuffer(GL_READ_FRAMEBUFFER, intermediate_fbo);<br>
<br>
glBlitFramebuffer(info->src.box.x,<br>
diff --git a/src/vrend_renderer.h b/src/vrend_renderer.h<br>
index 28e2819..c873c8c 100644<br>
--- a/src/vrend_renderer.h<br>
+++ b/src/vrend_renderer.h<br>
@@ -388,7 +388,8 @@ bool vrend_formats_can_blit(struct vrend_format_table *table, enum virgl_formats<br>
void vrend_renderer_blit_gl(struct vrend_context *ctx,<br>
struct vrend_resource *src_res,<br>
struct vrend_resource *dst_res,<br>
- const struct pipe_blit_info *info);<br>
+ const struct pipe_blit_info *info,<br>
+ bool use_gles);<br>
<br>
void vrend_renderer_reset(void);<br>
int vrend_renderer_get_poll_fd(void);<br>
-- <br>
2.17.1<br>
<br>
_______________________________________________<br>
virglrenderer-devel mailing list<br>
<a href="mailto:virglrenderer-devel@lists.freedesktop.org" target="_blank">virglrenderer-devel@lists.freedesktop.org</a><br>
<a href="https://lists.freedesktop.org/mailman/listinfo/virglrenderer-devel" rel="noreferrer" target="_blank">https://lists.freedesktop.org/mailman/listinfo/virglrenderer-devel</a><br>
</blockquote></div>