render/gles2: check buffer stride when uploading texture
If the stride is too small, the driver could end up segfaulting (e.g. radeonsi segfaults in __memmove_sse2_unaligned_erms).
This commit is contained in:
parent
f3758d1d0a
commit
6ca59519c9
|
@ -30,6 +30,21 @@ static bool gles2_texture_is_opaque(struct wlr_texture *wlr_texture) {
|
||||||
return !texture->has_alpha;
|
return !texture->has_alpha;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool check_stride(const struct wlr_gles2_pixel_format *fmt,
|
||||||
|
uint32_t stride, uint32_t width) {
|
||||||
|
if (stride % (fmt->bpp / 8) != 0) {
|
||||||
|
wlr_log(WLR_ERROR, "Invalid stride %d (incompatible with %d "
|
||||||
|
"bytes-per-pixel)", stride, fmt->bpp / 8);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (stride < width * (fmt->bpp / 8)) {
|
||||||
|
wlr_log(WLR_ERROR, "Invalid stride %d (too small for %d "
|
||||||
|
"bytes-per-pixel and width %d)", stride, fmt->bpp / 8, width);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
static bool gles2_texture_write_pixels(struct wlr_texture *wlr_texture,
|
static bool gles2_texture_write_pixels(struct wlr_texture *wlr_texture,
|
||||||
uint32_t stride, uint32_t width, uint32_t height,
|
uint32_t stride, uint32_t width, uint32_t height,
|
||||||
uint32_t src_x, uint32_t src_y, uint32_t dst_x, uint32_t dst_y,
|
uint32_t src_x, uint32_t src_y, uint32_t dst_x, uint32_t dst_y,
|
||||||
|
@ -45,6 +60,10 @@ static bool gles2_texture_write_pixels(struct wlr_texture *wlr_texture,
|
||||||
get_gles2_format_from_wl(texture->wl_format);
|
get_gles2_format_from_wl(texture->wl_format);
|
||||||
assert(fmt);
|
assert(fmt);
|
||||||
|
|
||||||
|
if (!check_stride(fmt, stride, width)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
struct wlr_egl_context prev_ctx;
|
struct wlr_egl_context prev_ctx;
|
||||||
wlr_egl_save_context(&prev_ctx);
|
wlr_egl_save_context(&prev_ctx);
|
||||||
wlr_egl_make_current(texture->renderer->egl);
|
wlr_egl_make_current(texture->renderer->egl);
|
||||||
|
@ -142,6 +161,10 @@ struct wlr_texture *gles2_texture_from_pixels(struct wlr_renderer *wlr_renderer,
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!check_stride(fmt, stride, width)) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
struct wlr_gles2_texture *texture =
|
struct wlr_gles2_texture *texture =
|
||||||
calloc(1, sizeof(struct wlr_gles2_texture));
|
calloc(1, sizeof(struct wlr_gles2_texture));
|
||||||
if (texture == NULL) {
|
if (texture == NULL) {
|
||||||
|
|
Loading…
Reference in New Issue