[virglrenderer-devel] [PATCH] virgl/vtest: add support to vtest for new cap getting.
Jakob Bornecrantz
jakob at collabora.com
Wed Jun 27 17:25:09 UTC 2018
On 2018-06-08 07:22, Dave Airlie wrote:
> From: Dave Airlie <airlied at redhat.com>
>
> The vtest protocol is pretty simple but also pretty dumb, and
> the v1 caps query was fixed size, with no nice way to expand it,
> however the server also ignores any command it doesn't understand.
>
> So we can query v2 caps by sending a v2 followed by a v1, if the
> v2 is ignored we know it's an old vtest server, and the we get
> a v2 answer then we can just read the v1 answer and discard it.
> ---
> .../winsys/virgl/vtest/virgl_vtest_socket.c | 30 +++++++++++++++++++---
> src/gallium/winsys/virgl/vtest/vtest_protocol.h | 2 ++
> 2 files changed, 28 insertions(+), 4 deletions(-)
>
> diff --git a/src/gallium/winsys/virgl/vtest/virgl_vtest_socket.c b/src/gallium/winsys/virgl/vtest/virgl_vtest_socket.c
> index adec26b66b8..d25f9a3bd9e 100644
> --- a/src/gallium/winsys/virgl/vtest/virgl_vtest_socket.c
> +++ b/src/gallium/winsys/virgl/vtest/virgl_vtest_socket.c
> @@ -129,12 +129,14 @@ int virgl_vtest_connect(struct virgl_vtest_winsys *vws)
> int virgl_vtest_send_get_caps(struct virgl_vtest_winsys *vws,
> struct virgl_drm_caps *caps)
> {
> - uint32_t get_caps_buf[VTEST_HDR_SIZE];
> + uint32_t get_caps_buf[VTEST_HDR_SIZE * 2];
> uint32_t resp_buf[VTEST_HDR_SIZE];
> -
> + uint32_t caps_size = sizeof(struct virgl_caps_v2);
> int ret;
> get_caps_buf[VTEST_CMD_LEN] = 0;
> - get_caps_buf[VTEST_CMD_ID] = VCMD_GET_CAPS;
> + get_caps_buf[VTEST_CMD_ID] = VCMD_GET_CAPS2;
> + get_caps_buf[VTEST_CMD_LEN + 2] = 0;
> + get_caps_buf[VTEST_CMD_ID + 2] = VCMD_GET_CAPS;
>
> virgl_block_write(vws->sock_fd, &get_caps_buf, sizeof(get_caps_buf));
>
> @@ -142,7 +144,27 @@ int virgl_vtest_send_get_caps(struct virgl_vtest_winsys *vws,
> if (ret <= 0)
> return 0;
>
> - ret = virgl_block_read(vws->sock_fd, &caps->caps, sizeof(struct virgl_caps_v1));
> + if (resp_buf[1] == 2) {
> + struct virgl_caps_v1 dummy;
> + uint32_t resp_size = resp_buf[0] - 1;
> + uint32_t dummy_size = 0;
> + if (resp_size > caps_size) {
> + dummy_size = resp_size - caps_size;
> + resp_size = caps_size;
> + }
> +
> + ret = virgl_block_read(vws->sock_fd, &caps->caps, resp_size);
> +
> + if (dummy_size)
> + ret = virgl_block_read(vws->sock_fd, &dummy, dummy_size);
Isn't there a risk that the "dummy_size" is larger then the struct
virgl_caps_v1 dummy and cause it to write over the stack? (I am assuming
you are using the dummy here as a place to put the extra caps the host
is exposing but the driver isn't supporting).
Wouldn't it be better if we had a virgl_block_skip function?
Cheers, Jakob.
> +
> + /* now read back the pointless caps v1 we requested */
> + ret = virgl_block_read(vws->sock_fd, resp_buf, sizeof(resp_buf));
> + if (ret <= 0)
> + return 0;
> + ret = virgl_block_read(vws->sock_fd, &dummy, sizeof(struct virgl_caps_v1));
> + } else
> + ret = virgl_block_read(vws->sock_fd, &caps->caps, sizeof(struct virgl_caps_v1));
>
> return 0;
> }
> diff --git a/src/gallium/winsys/virgl/vtest/vtest_protocol.h b/src/gallium/winsys/virgl/vtest/vtest_protocol.h
> index 86d197f006c..95bd8c1d0bd 100644
> --- a/src/gallium/winsys/virgl/vtest/vtest_protocol.h
> +++ b/src/gallium/winsys/virgl/vtest/vtest_protocol.h
> @@ -47,6 +47,8 @@
>
> /* pass the process cmd line for debugging */
> #define VCMD_CREATE_RENDERER 8
> +
> +#define VCMD_GET_CAPS2 9
> /* get caps */
> /* 0 length cmd */
> /* resp VCMD_GET_CAPS + caps */
>
More information about the virglrenderer-devel
mailing list