wfreerdp-server: modified and documented the display device check

This commit is contained in:
C-o-r-E 2012-08-14 11:57:25 -04:00
parent 07dccad079
commit 664596f5a5
2 changed files with 440 additions and 433 deletions

View File

@ -1,225 +1,232 @@
/**
* FreeRDP: A Remote Desktop Protocol Client
* FreeRDP Windows Server
*
* Copyright 2012 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <winpr/tchar.h>
#include <winpr/windows.h>
#include "wf_mirage.h"
#define DEVICE_KEY_PREFIX _T("\\Registry\\Machine\\")
int wf_mirage_step1(wfPeerContext* context)
{
BOOL result;
DWORD deviceNumber;
DISPLAY_DEVICE deviceInfo;
deviceNumber = 0;
deviceInfo.cb = sizeof(deviceInfo);
printf("Detecting display devices:\n");
while (result = EnumDisplayDevices(NULL, deviceNumber, &deviceInfo, 0))
{
_tprintf(_T("\t%s\n"), deviceInfo.DeviceString);
if (_tcscmp(deviceInfo.DeviceString, _T("Mirage Driver")) == 0)
{
int deviceKeyLength;
int deviceKeyPrefixLength;
_tprintf(_T("\n\nFound our target of interest!\n"));
deviceKeyPrefixLength = _tcslen(DEVICE_KEY_PREFIX);
if (_tcsncmp(deviceInfo.DeviceKey, DEVICE_KEY_PREFIX, deviceKeyPrefixLength) == 0)
{
deviceKeyLength = _tcslen(deviceInfo.DeviceKey) - deviceKeyPrefixLength;
context->deviceKey = (LPTSTR) malloc((deviceKeyLength + 1) * sizeof(TCHAR));
_tcsncpy_s(context->deviceKey, deviceKeyLength + 1,
&deviceInfo.DeviceKey[deviceKeyPrefixLength], deviceKeyLength);
_tprintf(_T("DeviceKey: %s\n"), context->deviceKey);
}
_tcsncpy_s(context->deviceName, 32, deviceInfo.DeviceName, _tcslen(deviceInfo.DeviceName));
}
deviceNumber++;
}
return 0;
}
int wf_mirage_step2(wfPeerContext* context)
{
LONG status;
DWORD rtype, rdata, rdata_size;
_tprintf(_T("\nOpening registry key %s\n"), context->deviceKey);
rtype = 0;
rdata = 0;
rdata_size = sizeof(rdata);
status = RegGetValue(HKEY_LOCAL_MACHINE, context->deviceKey,
_T("Attach.ToDesktop"), RRF_RT_REG_DWORD, &rtype, &rdata, &rdata_size);
if (status != ERROR_SUCCESS)
{
printf("Failed to read registry value.\n");
printf("operation returned %d\n", status);
return -1;
}
_tprintf(_T("type = %04X, data = %04X\n\nNow let's try attaching it...\n"), rtype, rdata);
if (rdata == 0)
{
rdata = 1;
status = RegSetKeyValue(HKEY_LOCAL_MACHINE, context->deviceKey,
_T("Attach.ToDesktop"), REG_DWORD, &rdata, rdata_size);
if (status != ERROR_SUCCESS)
{
_tprintf(_T("Failed to read registry value.\n"));
_tprintf(_T("operation returned %d\n"), status);
return -1;
}
_tprintf(_T("Attached to Desktop\n\n"));
}
else if (rdata == 1)
{
_tprintf(_T("Already attached to desktop!\n"));
}
else
{
_tprintf(_T("Something went wrong with attaching to desktop...\nrdata=%d\n"), rdata);
return -1;
}
return 0;
}
int wf_mirage_step3(wfPeerContext* context)
{
LONG status;
DWORD* extHdr;
WORD drvExtraSaved;
DEVMODE* deviceMode;
DWORD dmf_devmodewext_magic_sig = 0xDF20C0DE;
deviceMode = (DEVMODE*) malloc(sizeof(DEVMODE) + EXT_DEVMODE_SIZE_MAX);
deviceMode->dmDriverExtra = 2 * sizeof(DWORD);
extHdr = (DWORD*)((BYTE*) &deviceMode + sizeof(DEVMODE));
extHdr[0] = dmf_devmodewext_magic_sig;
extHdr[1] = 0;
drvExtraSaved = deviceMode->dmDriverExtra;
memset(deviceMode, 0, sizeof(DEVMODE) + EXT_DEVMODE_SIZE_MAX);
deviceMode->dmSize = sizeof(DEVMODE);
deviceMode->dmDriverExtra = drvExtraSaved;
deviceMode->dmPelsWidth = 640;
deviceMode->dmPelsHeight = 480;
deviceMode->dmBitsPerPel = 32;
deviceMode->dmPosition.x = 0;
deviceMode->dmPosition.y = 0;
deviceMode->dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT | DM_POSITION;
_tcsncpy_s(deviceMode->dmDeviceName, 32, context->deviceName, _tcslen(context->deviceName));
status = ChangeDisplaySettingsEx(context->deviceName, deviceMode, NULL, CDS_UPDATEREGISTRY, NULL);
switch (status)
{
case DISP_CHANGE_SUCCESSFUL:
printf("ChangeDisplaySettingsEx() was successfull\n");
break;
case DISP_CHANGE_BADDUALVIEW:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADDUALVIEW, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADFLAGS:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADFLAGS, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADMODE:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADMODE, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADPARAM:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADPARAM, code %d\n", status);
return -1;
break;
case DISP_CHANGE_FAILED:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_FAILED, code %d\n", status);
return -1;
break;
case DISP_CHANGE_NOTUPDATED:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_NOTUPDATED, code %d\n", status);
return -1;
break;
case DISP_CHANGE_RESTART:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_RESTART, code %d\n", status);
return -1;
break;
}
return 0;
}
int wf_mirage_step4(wfPeerContext* context)
{
int status;
printf("\n\nCreating a device context...\n");
context->driverDC = CreateDC(context->deviceName, NULL, NULL, NULL);
if (context->driverDC == NULL)
{
printf("Could not create device driver context!\n");
return -1;
}
context->changeBuffer = malloc(sizeof(GETCHANGESBUF));
printf("\n\nConnecting to driver...\n");
status = ExtEscape(context->driverDC, dmf_esc_usm_pipe_map, 0, 0, sizeof(GETCHANGESBUF), (LPSTR) context->changeBuffer);
if (status <= 0)
{
printf("Failed to map shared memory from the driver! Code %d\n", status);
}
return 0;
}
/**
* FreeRDP: A Remote Desktop Protocol Client
* FreeRDP Windows Server
*
* Copyright 2012 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <winpr/tchar.h>
#include <winpr/windows.h>
#include "wf_mirage.h"
#define DEVICE_KEY_PREFIX _T("\\Registry\\Machine\\")
/*
This function will iterate over the loaded display devices until it finds
the mirror device we want to load. If found, it will then copy the registry
key corresponding to the device to the context and returns true. Otherwise
the function returns false.
*/
BOOL wf_check_disp_devices(wfPeerContext* context)
{
BOOL result, devFound;
DWORD deviceNumber;
DISPLAY_DEVICE deviceInfo;
devFound = false;
deviceNumber = 0;
deviceInfo.cb = sizeof(deviceInfo);
printf("Detecting display devices:\n");
while (result = EnumDisplayDevices(NULL, deviceNumber, &deviceInfo, 0))
{
_tprintf(_T("\t%s\n"), deviceInfo.DeviceString);
if (_tcscmp(deviceInfo.DeviceString, _T("Mirage Driver")) == 0)
{
int deviceKeyLength;
int deviceKeyPrefixLength;
_tprintf(_T("\n\nFound our target of interest!\n"));
deviceKeyPrefixLength = _tcslen(DEVICE_KEY_PREFIX);
if (_tcsncmp(deviceInfo.DeviceKey, DEVICE_KEY_PREFIX, deviceKeyPrefixLength) == 0)
{
deviceKeyLength = _tcslen(deviceInfo.DeviceKey) - deviceKeyPrefixLength;
context->deviceKey = (LPTSTR) malloc((deviceKeyLength + 1) * sizeof(TCHAR));
_tcsncpy_s(context->deviceKey, deviceKeyLength + 1,
&deviceInfo.DeviceKey[deviceKeyPrefixLength], deviceKeyLength);
_tprintf(_T("DeviceKey: %s\n"), context->deviceKey);
}
_tcsncpy_s(context->deviceName, 32, deviceInfo.DeviceName, _tcslen(deviceInfo.DeviceName));
return true;
}
deviceNumber++;
}
return false;
}
int wf_mirage_step2(wfPeerContext* context)
{
LONG status;
DWORD rtype, rdata, rdata_size;
_tprintf(_T("\nOpening registry key %s\n"), context->deviceKey);
rtype = 0;
rdata = 0;
rdata_size = sizeof(rdata);
status = RegGetValue(HKEY_LOCAL_MACHINE, context->deviceKey,
_T("Attach.ToDesktop"), RRF_RT_REG_DWORD, &rtype, &rdata, &rdata_size);
if (status != ERROR_SUCCESS)
{
printf("Failed to read registry value.\n");
printf("operation returned %d\n", status);
return -1;
}
_tprintf(_T("type = %04X, data = %04X\n\nNow let's try attaching it...\n"), rtype, rdata);
if (rdata == 0)
{
rdata = 1;
status = RegSetKeyValue(HKEY_LOCAL_MACHINE, context->deviceKey,
_T("Attach.ToDesktop"), REG_DWORD, &rdata, rdata_size);
if (status != ERROR_SUCCESS)
{
_tprintf(_T("Failed to read registry value.\n"));
_tprintf(_T("operation returned %d\n"), status);
return -1;
}
_tprintf(_T("Attached to Desktop\n\n"));
}
else if (rdata == 1)
{
_tprintf(_T("Already attached to desktop!\n"));
}
else
{
_tprintf(_T("Something went wrong with attaching to desktop...\nrdata=%d\n"), rdata);
return -1;
}
return 0;
}
int wf_mirage_step3(wfPeerContext* context)
{
LONG status;
DWORD* extHdr;
WORD drvExtraSaved;
DEVMODE* deviceMode;
DWORD dmf_devmodewext_magic_sig = 0xDF20C0DE;
deviceMode = (DEVMODE*) malloc(sizeof(DEVMODE) + EXT_DEVMODE_SIZE_MAX);
deviceMode->dmDriverExtra = 2 * sizeof(DWORD);
extHdr = (DWORD*)((BYTE*) &deviceMode + sizeof(DEVMODE));
extHdr[0] = dmf_devmodewext_magic_sig;
extHdr[1] = 0;
drvExtraSaved = deviceMode->dmDriverExtra;
memset(deviceMode, 0, sizeof(DEVMODE) + EXT_DEVMODE_SIZE_MAX);
deviceMode->dmSize = sizeof(DEVMODE);
deviceMode->dmDriverExtra = drvExtraSaved;
deviceMode->dmPelsWidth = 640;
deviceMode->dmPelsHeight = 480;
deviceMode->dmBitsPerPel = 32;
deviceMode->dmPosition.x = 0;
deviceMode->dmPosition.y = 0;
deviceMode->dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT | DM_POSITION;
_tcsncpy_s(deviceMode->dmDeviceName, 32, context->deviceName, _tcslen(context->deviceName));
status = ChangeDisplaySettingsEx(context->deviceName, deviceMode, NULL, CDS_UPDATEREGISTRY, NULL);
switch (status)
{
case DISP_CHANGE_SUCCESSFUL:
printf("ChangeDisplaySettingsEx() was successfull\n");
break;
case DISP_CHANGE_BADDUALVIEW:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADDUALVIEW, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADFLAGS:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADFLAGS, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADMODE:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADMODE, code %d\n", status);
return -1;
break;
case DISP_CHANGE_BADPARAM:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_BADPARAM, code %d\n", status);
return -1;
break;
case DISP_CHANGE_FAILED:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_FAILED, code %d\n", status);
return -1;
break;
case DISP_CHANGE_NOTUPDATED:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_NOTUPDATED, code %d\n", status);
return -1;
break;
case DISP_CHANGE_RESTART:
printf("ChangeDisplaySettingsEx() failed with DISP_CHANGE_RESTART, code %d\n", status);
return -1;
break;
}
return 0;
}
int wf_mirage_step4(wfPeerContext* context)
{
int status;
printf("\n\nCreating a device context...\n");
context->driverDC = CreateDC(context->deviceName, NULL, NULL, NULL);
if (context->driverDC == NULL)
{
printf("Could not create device driver context!\n");
return -1;
}
context->changeBuffer = malloc(sizeof(GETCHANGESBUF));
printf("\n\nConnecting to driver...\n");
status = ExtEscape(context->driverDC, dmf_esc_usm_pipe_map, 0, 0, sizeof(GETCHANGESBUF), (LPSTR) context->changeBuffer);
if (status <= 0)
{
printf("Failed to map shared memory from the driver! Code %d\n", status);
}
return 0;
}

View File

@ -1,208 +1,208 @@
/**
* FreeRDP: A Remote Desktop Protocol Client
* FreeRDP Windows Server
*
* Copyright 2012 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef WF_MIRAGE_H
#define WF_MIRAGE_H
#include "wfreerdp.h"
enum
{
DMF_ESCAPE_BASE_1_VB = 1030,
DMF_ESCAPE_BASE_2_VB = 1026,
DMF_ESCAPE_BASE_3_VB = 24
};
#ifdef _WIN64
#define CLIENT_64BIT 0x8000
enum
{
DMF_ESCAPE_BASE_1 = CLIENT_64BIT | DMF_ESCAPE_BASE_1_VB,
DMF_ESCAPE_BASE_2 = CLIENT_64BIT | DMF_ESCAPE_BASE_2_VB,
DMF_ESCAPE_BASE_3 = CLIENT_64BIT | DMF_ESCAPE_BASE_3_VB,
};
#else
enum
{
DMF_ESCAPE_BASE_1 = DMF_ESCAPE_BASE_1_VB,
DMF_ESCAPE_BASE_2 = DMF_ESCAPE_BASE_2_VB,
DMF_ESCAPE_BASE_3 = DMF_ESCAPE_BASE_3_VB,
};
#endif
typedef enum
{
dmf_esc_qry_ver_info = DMF_ESCAPE_BASE_2 + 0,
dmf_esc_usm_pipe_map = DMF_ESCAPE_BASE_1 + 0,
dmf_esc_usm_pipe_unmap = DMF_ESCAPE_BASE_1 + 1,
dmf_esc_test = DMF_ESCAPE_BASE_1 + 20,
dmf_esc_usm_pipe_mapping_test = DMF_ESCAPE_BASE_1 + 21,
dmf_esc_pointer_shape_get = DMF_ESCAPE_BASE_3,
} dmf_escape;
#define CLIP_LIMIT 50
#define MAXCHANGES_BUF 20000
typedef enum
{
dmf_dfo_IGNORE = 0,
dmf_dfo_FROM_SCREEN = 1,
dmf_dfo_FROM_DIB = 2,
dmf_dfo_TO_SCREEN = 3,
dmf_dfo_SCREEN_SCREEN = 11,
dmf_dfo_BLIT = 12,
dmf_dfo_SOLIDFILL = 13,
dmf_dfo_BLEND = 14,
dmf_dfo_TRANS = 15,
dmf_dfo_PLG = 17,
dmf_dfo_TEXTOUT = 18,
dmf_dfo_Ptr_Shape = 19,
dmf_dfo_Ptr_Engage = 48,
dmf_dfo_Ptr_Avert = 49,
dmf_dfn_assert_on = 64,
dmf_dfn_assert_off = 65,
} dmf_UpdEvent;
#define NOCACHE 1
#define OLDCACHE 2
#define NEWCACHE 3
typedef struct
{
ULONG type;
RECT rect;
#ifndef DFMIRAGE_LEAN
RECT origrect;
POINT point;
ULONG color;
ULONG refcolor;
#endif
} CHANGES_RECORD;
typedef CHANGES_RECORD* PCHANGES_RECORD;
typedef struct
{
ULONG counter;
CHANGES_RECORD pointrect[MAXCHANGES_BUF];
} CHANGES_BUF;
#define EXT_DEVMODE_SIZE_MAX 3072
#define DMF_PIPE_SEC_SIZE_DEFAULT ALIGN64K(sizeof(CHANGES_BUF))
typedef struct
{
CHANGES_BUF* buffer;
PVOID Userbuffer;
} GETCHANGESBUF;
#define dmf_sprb_ERRORMASK 0x07FF
#define dmf_sprb_STRICTSESSION_AFF 0x1FFF
typedef enum
{
dmf_sprb_internal_error = 0x0001,
dmf_sprb_miniport_gen_error = 0x0004,
dmf_sprb_memory_alloc_failed = 0x0008,
dmf_sprb_pipe_buff_overflow = 0x0010,
dmf_sprb_pipe_buff_insufficient = 0x0020,
dmf_sprb_pipe_not_ready = 0x0040,
dmf_sprb_gdi_err = 0x0100,
dmf_sprb_owner_died = 0x0400,
dmf_sprb_tgtwnd_gone = 0x0800,
dmf_sprb_pdev_detached = 0x2000,
} dmf_session_prob_status;
#define DMF_ESC_RET_FAILF 0x80000000
#define DMF_ESC_RET_SSTMASK 0x0000FFFF
#define DMF_ESC_RET_IMMMASK 0x7FFF0000
typedef enum
{
dmf_escret_generic_ok = 0x00010000,
dmf_escret_bad_state = 0x00100000,
dmf_escret_access_denied = 0x00200000,
dmf_escret_bad_buffer_size = 0x00400000,
dmf_escret_internal_err = 0x00800000,
dmf_escret_out_of_memory = 0x02000000,
dmf_escret_already_connected = 0x04000000,
dmf_escret_oh_boy_too_late = 0x08000000,
dmf_escret_bad_window = 0x10000000,
dmf_escret_drv_ver_higher = 0x20000000,
dmf_escret_drv_ver_lower = 0x40000000,
} dmf_esc_retcode;
typedef struct
{
ULONG cbSize;
ULONG app_actual_version;
ULONG display_minreq_version;
ULONG connect_options;
} Esc_dmf_Qvi_IN;
enum
{
esc_qvi_prod_name_max = 16,
};
#define ESC_QVI_PROD_MIRAGE "MIRAGE"
#define ESC_QVI_PROD_QUASAR "QUASAR"
typedef struct
{
ULONG cbSize;
ULONG display_actual_version;
ULONG miniport_actual_version;
ULONG app_minreq_version;
ULONG display_buildno;
ULONG miniport_buildno;
char prod_name[esc_qvi_prod_name_max];
} Esc_dmf_Qvi_OUT;
typedef struct
{
ULONG cbSize;
char* pDstBmBuf;
ULONG nDstBmBufSize;
} Esc_dmf_pointer_shape_get_IN;
typedef struct
{
ULONG cbSize;
POINTL BmSize;
char* pMaskBm;
ULONG nMaskBmSize;
char* pColorBm;
ULONG nColorBmSize;
char* pColorBmPal;
ULONG nColorBmPalEntries;
} Esc_dmf_pointer_shape_get_OUT;
int wf_mirage_step1(wfPeerContext* context);
int wf_mirage_step2(wfPeerContext* context);
int wf_mirage_step3(wfPeerContext* context);
int wf_mirage_step4(wfPeerContext* context);
#endif /* WF_MIRAGE_H */
/**
* FreeRDP: A Remote Desktop Protocol Client
* FreeRDP Windows Server
*
* Copyright 2012 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef WF_MIRAGE_H
#define WF_MIRAGE_H
#include "wfreerdp.h"
enum
{
DMF_ESCAPE_BASE_1_VB = 1030,
DMF_ESCAPE_BASE_2_VB = 1026,
DMF_ESCAPE_BASE_3_VB = 24
};
#ifdef _WIN64
#define CLIENT_64BIT 0x8000
enum
{
DMF_ESCAPE_BASE_1 = CLIENT_64BIT | DMF_ESCAPE_BASE_1_VB,
DMF_ESCAPE_BASE_2 = CLIENT_64BIT | DMF_ESCAPE_BASE_2_VB,
DMF_ESCAPE_BASE_3 = CLIENT_64BIT | DMF_ESCAPE_BASE_3_VB,
};
#else
enum
{
DMF_ESCAPE_BASE_1 = DMF_ESCAPE_BASE_1_VB,
DMF_ESCAPE_BASE_2 = DMF_ESCAPE_BASE_2_VB,
DMF_ESCAPE_BASE_3 = DMF_ESCAPE_BASE_3_VB,
};
#endif
typedef enum
{
dmf_esc_qry_ver_info = DMF_ESCAPE_BASE_2 + 0,
dmf_esc_usm_pipe_map = DMF_ESCAPE_BASE_1 + 0,
dmf_esc_usm_pipe_unmap = DMF_ESCAPE_BASE_1 + 1,
dmf_esc_test = DMF_ESCAPE_BASE_1 + 20,
dmf_esc_usm_pipe_mapping_test = DMF_ESCAPE_BASE_1 + 21,
dmf_esc_pointer_shape_get = DMF_ESCAPE_BASE_3,
} dmf_escape;
#define CLIP_LIMIT 50
#define MAXCHANGES_BUF 20000
typedef enum
{
dmf_dfo_IGNORE = 0,
dmf_dfo_FROM_SCREEN = 1,
dmf_dfo_FROM_DIB = 2,
dmf_dfo_TO_SCREEN = 3,
dmf_dfo_SCREEN_SCREEN = 11,
dmf_dfo_BLIT = 12,
dmf_dfo_SOLIDFILL = 13,
dmf_dfo_BLEND = 14,
dmf_dfo_TRANS = 15,
dmf_dfo_PLG = 17,
dmf_dfo_TEXTOUT = 18,
dmf_dfo_Ptr_Shape = 19,
dmf_dfo_Ptr_Engage = 48,
dmf_dfo_Ptr_Avert = 49,
dmf_dfn_assert_on = 64,
dmf_dfn_assert_off = 65,
} dmf_UpdEvent;
#define NOCACHE 1
#define OLDCACHE 2
#define NEWCACHE 3
typedef struct
{
ULONG type;
RECT rect;
#ifndef DFMIRAGE_LEAN
RECT origrect;
POINT point;
ULONG color;
ULONG refcolor;
#endif
} CHANGES_RECORD;
typedef CHANGES_RECORD* PCHANGES_RECORD;
typedef struct
{
ULONG counter;
CHANGES_RECORD pointrect[MAXCHANGES_BUF];
} CHANGES_BUF;
#define EXT_DEVMODE_SIZE_MAX 3072
#define DMF_PIPE_SEC_SIZE_DEFAULT ALIGN64K(sizeof(CHANGES_BUF))
typedef struct
{
CHANGES_BUF* buffer;
PVOID Userbuffer;
} GETCHANGESBUF;
#define dmf_sprb_ERRORMASK 0x07FF
#define dmf_sprb_STRICTSESSION_AFF 0x1FFF
typedef enum
{
dmf_sprb_internal_error = 0x0001,
dmf_sprb_miniport_gen_error = 0x0004,
dmf_sprb_memory_alloc_failed = 0x0008,
dmf_sprb_pipe_buff_overflow = 0x0010,
dmf_sprb_pipe_buff_insufficient = 0x0020,
dmf_sprb_pipe_not_ready = 0x0040,
dmf_sprb_gdi_err = 0x0100,
dmf_sprb_owner_died = 0x0400,
dmf_sprb_tgtwnd_gone = 0x0800,
dmf_sprb_pdev_detached = 0x2000,
} dmf_session_prob_status;
#define DMF_ESC_RET_FAILF 0x80000000
#define DMF_ESC_RET_SSTMASK 0x0000FFFF
#define DMF_ESC_RET_IMMMASK 0x7FFF0000
typedef enum
{
dmf_escret_generic_ok = 0x00010000,
dmf_escret_bad_state = 0x00100000,
dmf_escret_access_denied = 0x00200000,
dmf_escret_bad_buffer_size = 0x00400000,
dmf_escret_internal_err = 0x00800000,
dmf_escret_out_of_memory = 0x02000000,
dmf_escret_already_connected = 0x04000000,
dmf_escret_oh_boy_too_late = 0x08000000,
dmf_escret_bad_window = 0x10000000,
dmf_escret_drv_ver_higher = 0x20000000,
dmf_escret_drv_ver_lower = 0x40000000,
} dmf_esc_retcode;
typedef struct
{
ULONG cbSize;
ULONG app_actual_version;
ULONG display_minreq_version;
ULONG connect_options;
} Esc_dmf_Qvi_IN;
enum
{
esc_qvi_prod_name_max = 16,
};
#define ESC_QVI_PROD_MIRAGE "MIRAGE"
#define ESC_QVI_PROD_QUASAR "QUASAR"
typedef struct
{
ULONG cbSize;
ULONG display_actual_version;
ULONG miniport_actual_version;
ULONG app_minreq_version;
ULONG display_buildno;
ULONG miniport_buildno;
char prod_name[esc_qvi_prod_name_max];
} Esc_dmf_Qvi_OUT;
typedef struct
{
ULONG cbSize;
char* pDstBmBuf;
ULONG nDstBmBufSize;
} Esc_dmf_pointer_shape_get_IN;
typedef struct
{
ULONG cbSize;
POINTL BmSize;
char* pMaskBm;
ULONG nMaskBmSize;
char* pColorBm;
ULONG nColorBmSize;
char* pColorBmPal;
ULONG nColorBmPalEntries;
} Esc_dmf_pointer_shape_get_OUT;
int wf_check_disp_devices(wfPeerContext* context);
int wf_mirage_step2(wfPeerContext* context);
int wf_mirage_step3(wfPeerContext* context);
int wf_mirage_step4(wfPeerContext* context);
#endif /* WF_MIRAGE_H */