[Spice-devel] [win32-qxl]Do not allow duplicate IDs in video mode info buffer.
Uri Lublin
uril at redhat.com
Thu Sep 17 08:06:21 PDT 2015
On 09/17/2015 02:40 PM, Christophe Fergeau wrote:
> On Wed, Sep 16, 2015 at 03:27:49PM -0400, Sandy Stutsman wrote:
>>
>> Modes are returned in a buffer from qemu with IDs in increasing but not
>> necessarily consecutive order. (Some modes may be omitted if they don't fit
>> into the framebuffer.) Two custom modes are appended to the local buffer to
>> support arbitrary resolutions. The first custom id must be set to +1 of the
>> last id in the mode buffer, not to the last index +1 of the buffer.
>>
>> E.G. these are the last entries in the mode buffer returned from QEMU:
>> Index Mode id (unfortunately named ModeIndex in the struct)
>> ...
>> 124 128
>> 125 130
>> 126 132
>> 127 134 (last mode returned from QEMU)
>>
>> Custom Modes:
>> 128 135 (Not 128!)
>> 129 136
>>
>> If the first custom mode id is set to 128 (the number of modes returned
>> from QEMU), it will duplicate the id for the mode at index 124. That could
>> cause the FindMode function which searches the mode list by mode id
>> to return the wrong mode information.
>>
>> The custom mode id's are now set to be greater than the last mode id
>> returned from QEMU.
>> ---
>> xddm/miniport/qxl.c | 15 +++++++++++----
>> 1 file changed, 11 insertions(+), 4 deletions(-)
>>
>> diff --git a/xddm/miniport/qxl.c b/xddm/miniport/qxl.c
>> index e0fb87f..22537e2 100644
>> --- a/xddm/miniport/qxl.c
>> +++ b/xddm/miniport/qxl.c
>> @@ -596,6 +596,7 @@ VP_STATUS InitModes(QXLExtension *dev)
>> ULONG n_modes;
>> ULONG i;
>> VP_STATUS error;
>> + ULONG custom_mode_id = 0;
>>
>> PAGED_CODE();
>> DEBUG_PRINT((dev, 0, "%s\n", __FUNCTION__));
>> @@ -632,6 +633,11 @@ VP_STATUS InitModes(QXLExtension *dev)
>> return error;
>> }
>> }
>> + /* Mode ids are increasing in the buffer but may not be consecutive,
>> + * so set the first custom id to be 1 larger than the last id in the buffer.
>> + * (ModeIndex isn't really an index, it is an ID).
>> + */
>> + custom_mode_id = modes->modes[modes->n_modes-1].id + 1;
>>
>> /* 2 dummy modes for custom display resolution */
>> /* This is necessary to bypass Windows mode index check, that
>> @@ -640,7 +646,7 @@ VP_STATUS InitModes(QXLExtension *dev)
>>
>> for (i = dev->custom_mode; i <= dev->custom_mode + 1; ++i) {
>> memcpy(&modes_info[i], &modes_info[0], sizeof(VIDEO_MODE_INFORMATION));
>> - modes_info[i].ModeIndex = i;
>> + modes_info[i].ModeIndex = custom_mode_id++;
>> }
>>
>> dev->n_modes = n_modes;
>> @@ -1002,6 +1008,7 @@ static VP_STATUS SetCustomDisplay(QXLExtension *dev_ext, QXLEscapeSetCustomDispl
>> uint32_t xres = custom_display->xres;
>> uint32_t yres = custom_display->yres;
>> uint32_t bpp = custom_display->bpp;
>> + PVIDEO_MODE_INFORMATION pMode;
>>
>> /* alternate custom mode index */
>> if (dev_ext->custom_mode == (dev_ext->n_modes - 1))
>> @@ -1014,11 +1021,11 @@ static VP_STATUS SetCustomDisplay(QXLExtension *dev_ext, QXLEscapeSetCustomDispl
>> __FUNCTION__, xres, yres, bpp, dev_ext->rom->surface0_area_size));
>> return ERROR_NOT_ENOUGH_MEMORY;
>> }
>> -
>> - ret = FillVidModeInfo(&dev_ext->modes[dev_ext->custom_mode],
>> + pMode = &dev_ext->modes[dev_ext->custom_mode];
>> + ret = FillVidModeInfo(pMode,
>> custom_display->xres, custom_display->yres,
>> custom_display->bpp,
>> - dev_ext->custom_mode);
>> + pMode->ModeIndex);
>
> This looks good to me, ACK.
> I'd add a commit on top of that getting rid of
> the last argument to FillVidModeInfo as all that function does with this
> argument is set pMode->ModeIndex to be equal to its value.
This patch is good, but I wonder if the problem is not with qemu.
If we change in qemu/hw/display/qxl.c:
- modes->modes[n].id = cpu_to_le32(i);
+ modes->modes[n].id = cpu_to_le32(n);
Does that solves the problem ?
Thanks,
Uri.
More information about the Spice-devel
mailing list