From: Edward O'Callaghan Date: Mon, 5 Dec 2016 23:43:17 +0000 (+1100) Subject: virgl: Fix a strict-aliasing violation in the encoder X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=5e6b2b05a5d6c09f103db59e7dcda10ccfeceae5;p=mesa.git virgl: Fix a strict-aliasing violation in the encoder As per the C spec, it is illegal to alias pointers to different types. This results in undefined behaviour after optimization passes, resulting in very subtle bugs that happen only on a full moon.. Use a memcpy() as a well defined coercion between the double to uint64_t interpretations of the memory. V.2: Use static_assert() instead of assert(). V.3: Use C99 compat STATIC_ASSERT() over C11 static_assert(). Signed-off-by: Edward O'Callaghan Acked-by: Dave Airlie --- diff --git a/src/gallium/drivers/virgl/virgl_encode.c b/src/gallium/drivers/virgl/virgl_encode.c index be72f707fa1..85843b70094 100644 --- a/src/gallium/drivers/virgl/virgl_encode.c +++ b/src/gallium/drivers/virgl/virgl_encode.c @@ -21,6 +21,8 @@ * USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include +#include +#include #include "util/u_format.h" #include "util/u_memory.h" @@ -315,12 +317,16 @@ int virgl_encode_clear(struct virgl_context *ctx, double depth, unsigned stencil) { int i; + uint64_t qword; + + STATIC_ASSERT(sizeof(qword) == sizeof(depth)); + memcpy(&qword, &depth, sizeof(qword)); virgl_encoder_write_cmd_dword(ctx, VIRGL_CMD0(VIRGL_CCMD_CLEAR, 0, VIRGL_OBJ_CLEAR_SIZE)); virgl_encoder_write_dword(ctx->cbuf, buffers); for (i = 0; i < 4; i++) virgl_encoder_write_dword(ctx->cbuf, color->ui[i]); - virgl_encoder_write_qword(ctx->cbuf, *(uint64_t *)&depth); + virgl_encoder_write_qword(ctx->cbuf, qword); virgl_encoder_write_dword(ctx->cbuf, stencil); return 0; }