Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

422 lines
16 KiB

/****************************************************************************/
// cm.h
//
// Cursor manager header.
//
// Copyright (C) 1997-2000 Microsoft Corp.
/****************************************************************************/
#ifndef _H_CM
#define _H_CM
extern "C" {
#include <adcgdata.h>
}
#include "autil.h"
#include "wui.h"
#include "uh.h"
#include "objs.h"
#include "cd.h"
#define TRC_GROUP TRC_GROUP_CORE
#define TRC_FILE "cm"
#define TSC_HR_FILEID TSC_HR_CM_H
/****************************************************************************/
/* Cursor size constants. These are t.128 specifications. */
/****************************************************************************/
#define CM_CURSOR_WIDTH 32
#define CM_CURSOR_HEIGHT 32
#define CM_NUM_CURSOR_BITMAP_BYTES ((CM_CURSOR_WIDTH * CM_CURSOR_HEIGHT) / 8)
/****************************************************************************/
/* Pointer cache sizes. */
/* */
/* Note: For 'old' style support, the cache includes one entry (never */
/* used!) for the last mono cursor */
/****************************************************************************/
#define CM_COLOR_CACHE_SIZE 20
#define CM_MONO_CACHE_SIZE 1
#define CM_MONO_CACHE_INDEX CM_COLOR_CACHE_SIZE
#define CM_CURSOR_CACHE_SIZE (CM_COLOR_CACHE_SIZE + CM_MONO_CACHE_SIZE)
/**STRUCT+*******************************************************************/
/* Structure: CM_GLOBAL_DATA */
/* */
/* Description: */
/****************************************************************************/
typedef struct tagCM_GLOBAL_DATA
{
HCURSOR cursorCache[CM_CURSOR_CACHE_SIZE];
} CM_GLOBAL_DATA, DCPTR PCM_GLOBAL_DATA;
/**STRUCT-*******************************************************************/
#define CM_DEFAULT_ARROW_CURSOR_HANDLE LoadCursor(NULL, IDC_ARROW)
class CCM
{
public:
CCM(CObjs* objs);
~CCM();
//
// API
//
/****************************************************************************/
// Functions
/****************************************************************************/
DCVOID DCAPI CM_Init(DCVOID);
DCVOID DCAPI CM_Enable(ULONG_PTR unused);
EXPOSE_CD_SIMPLE_NOTIFICATION_FN(CCM, CM_Enable);
DCVOID DCAPI CM_Disable(ULONG_PTR unused);
EXPOSE_CD_SIMPLE_NOTIFICATION_FN(CCM, CM_Disable);
void DCAPI CM_NullSystemPointerPDU(void);
void DCAPI CM_DefaultSystemPointerPDU(void);
HRESULT DCAPI CM_MonoPointerPDU(TS_MONOPOINTERATTRIBUTE UNALIGNED FAR *, DCUINT);
void DCAPI CM_PositionPDU(TS_POINT16 UNALIGNED FAR *);
HRESULT DCAPI CM_ColorPointerPDU(TS_COLORPOINTERATTRIBUTE UNALIGNED FAR *, DCUINT);
void DCAPI CM_CachedPointerPDU(unsigned);
HRESULT DCAPI CM_PointerPDU(TS_POINTERATTRIBUTE UNALIGNED FAR *, DCUINT);
/****************************************************************************/
/* Name: CM_Term */
/* */
/* Purpose: Cursor Manager termination */
/****************************************************************************/
inline void DCAPI CM_Term(void)
{
} /* CM_Term */
/****************************************************************************/
// CM_SlowPathPDU
//
// Handles non-fast-path translation to handler function calls.
/****************************************************************************/
// SECURITY - the size of the packet has been checked only to be sure there is
// enough data to read the TS_POINTER_PDU_DATA.messageType field
inline HRESULT DCAPI CM_SlowPathPDU(
TS_POINTER_PDU_DATA UNALIGNED FAR *pPointerPDU,
DCUINT dataLen )
{
DC_BEGIN_FN("CM_SlowPathPDU");
HRESULT hr = S_OK;
switch (pPointerPDU->messageType) {
case TS_PTRMSGTYPE_POSITION:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TS_POINT16), hr, (TB, _T("Bad TS_PTRMSGTYPE_POSITION")));
CM_PositionPDU(&pPointerPDU->pointerData.pointerPosition);
break;
case TS_PTRMSGTYPE_SYSTEM:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TSUINT32), hr, (TB, _T("Bad TS_PTRMSGTYPE_SYSTEM")));
switch (pPointerPDU->pointerData.systemPointerType) {
case TS_SYSPTR_NULL:
CM_NullSystemPointerPDU();
break;
case TS_SYSPTR_DEFAULT:
CM_DefaultSystemPointerPDU();
break;
default:
TRC_ERR((TB, _T("Invalid system pointer type")));
break;
}
break;
case TS_PTRMSGTYPE_MONO:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TS_MONOPOINTERATTRIBUTE), hr, (TB, _T("Bad TS_PTRMSGTYPE_MONO")));
hr = CM_MonoPointerPDU(&pPointerPDU->pointerData.
monoPointerAttribute, dataLen - FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData));
break;
case TS_PTRMSGTYPE_COLOR:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TS_COLORPOINTERATTRIBUTE), hr, (TB, _T("Bad TS_PTRMSGTYPE_COLOR")));
hr = CM_ColorPointerPDU(&pPointerPDU->pointerData.
colorPointerAttribute, dataLen - FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData));
break;
case TS_PTRMSGTYPE_POINTER:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TS_POINTERATTRIBUTE), hr, (TB, _T("Bad TS_PTRMSGTYPE_POINTER")));
hr = CM_PointerPDU(&pPointerPDU->pointerData.pointerAttribute,
dataLen - FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData));
break;
case TS_PTRMSGTYPE_CACHED:
CHECK_READ_N_BYTES(pPointerPDU, (PBYTE)pPointerPDU + dataLen,
FIELDOFFSET(TS_POINTER_PDU_DATA,pointerData) +
sizeof(TSUINT16), hr, (TB, _T("Bad TS_PTRMSGTYPE_CACHED")));
CM_CachedPointerPDU(pPointerPDU->pointerData.cachedPointerIndex);
break;
default:
TRC_ERR((TB, _T("Unknown PointerPDU type %#x"),
pPointerPDU->messageType));
hr = E_UNEXPECTED;
break;
}
DC_EXIT_POINT:
DC_END_FN();
return hr;
}
public:
//
// Public data members
//
CM_GLOBAL_DATA _CM;
private:
//
// Internal functions
//
/****************************************************************************/
/* Functions */
/****************************************************************************/
HRESULT DCINTERNAL CMCreateColorCursor(unsigned,
TS_COLORPOINTERATTRIBUTE UNALIGNED FAR *, DCUINT, HCURSOR *);
HRESULT DCINTERNAL CMCreateMonoCursor(
TS_MONOPOINTERATTRIBUTE UNALIGNED FAR *, DCUINT, HCURSOR *);
inline HRESULT DCINTERNAL CMCreateNewCursor(
TS_POINTERATTRIBUTE UNALIGNED FAR *pAttr,
DCUINT dataLen,
HCURSOR FAR *pNewHandle,
HCURSOR * pOldHandle)
{
HRESULT hr = S_OK;
HCURSOR oldHandle = NULL;
HCURSOR newHandle;
unsigned cacheIndex;
unsigned xorLen;
DC_BEGIN_FN("CMCreateNewCursor");
TRC_DATA_DBG("Rx cursor data", pAttr, sizeof(TS_POINTERATTRIBUTE) );
cacheIndex = pAttr->colorPtrAttr.cacheIndex;
// SECURITY: 555587 cursor values must be validated
if (cacheIndex >= CM_CURSOR_CACHE_SIZE) {
TRC_ERR(( TB, _T("Invalid cache index %d"), cacheIndex));
hr = E_TSC_CORE_CACHEVALUE;
DC_QUIT;
}
TRC_DBG((TB, _T("Cached index %d"), cacheIndex));
oldHandle = _CM.cursorCache[cacheIndex];
// SECURITY 555587: CMCreate<XXX>Cursor must validate input
if (FIELDOFFSET(TS_COLORPOINTERATTRIBUTE, colorPointerData) +
pAttr->colorPtrAttr.lengthXORMask + pAttr->colorPtrAttr.lengthANDMask > dataLen) {
TRC_ERR(( TB, _T("Bad CreateNewCursor; dataLen %u"), dataLen));
hr = E_TSC_CORE_LENGTH;
DC_QUIT;
}
// Create the new cursor according to the color depth
if (pAttr->XORBpp == 1) {
TRC_NRM((TB, _T("Create mono cursor")));
// Data contains XOR followed by AND mask.
xorLen = pAttr->colorPtrAttr.lengthXORMask;
TRC_DATA_DBG("AND mask",
pAttr->colorPtrAttr.colorPointerData + xorLen,
xorLen);
TRC_DATA_DBG("XOR bitmap",
pAttr->colorPtrAttr.colorPointerData,
xorLen);
#ifndef OS_WINCE
newHandle = CreateCursor(_pUi->UI_GetInstanceHandle(),
pAttr->colorPtrAttr.hotSpot.x,
pAttr->colorPtrAttr.hotSpot.y,
pAttr->colorPtrAttr.width,
pAttr->colorPtrAttr.height,
pAttr->colorPtrAttr.colorPointerData + xorLen,
pAttr->colorPtrAttr.colorPointerData);
#else
/******************************************************************/
/* In Windows CE environments, we're not guaranteed that */
/* CreateCursor is part of the OS, so we do a GetProcAddress on */
/* it so we can be sure. If it's not there, this usually means */
/* we're on a touch screen device where these cursor doesn't */
/* matter anyway. */
/******************************************************************/
if (g_pCreateCursor)
{
newHandle = g_pCreateCursor(_pUi->UI_GetInstanceHandle(),
pAttr->colorPtrAttr.hotSpot.x,
pAttr->colorPtrAttr.hotSpot.y,
pAttr->colorPtrAttr.width,
pAttr->colorPtrAttr.height,
pAttr->colorPtrAttr.colorPointerData + xorLen,
pAttr->colorPtrAttr.colorPointerData);
}
else
{
newHandle = NULL;
}
#endif // OS_WINCE
}
else {
TRC_NRM((TB, _T("Create %d bpp cursor"), pAttr->XORBpp));
hr = CMCreateColorCursor(pAttr->XORBpp, &(pAttr->colorPtrAttr),
dataLen - FIELDSIZE(TS_POINTERATTRIBUTE, XORBpp), &newHandle);
DC_QUIT_ON_FAIL(hr);
}
_CM.cursorCache[cacheIndex] = newHandle;
if (newHandle != NULL) {
// New cursor created OK.
*pNewHandle = newHandle;
}
else {
// Failed to create the new color cursor - use default
TRC_ALT((TB, _T("Failed to create cursor")));
*pNewHandle = CM_DEFAULT_ARROW_CURSOR_HANDLE;
}
*pOldHandle = oldHandle;
DC_EXIT_POINT:
DC_END_FN();
return hr;
}
inline HRESULT DCINTERNAL CMCreateNewColorCursor(
unsigned cacheIndex,
TS_COLORPOINTERATTRIBUTE UNALIGNED FAR *pAttr,
DCUINT dataLen,
HCURSOR FAR *pNewHandle,
HCURSOR * pOldHandle)
{
HRESULT hr = S_OK;
HCURSOR oldHandle = NULL;
HCURSOR newHandle;
DC_BEGIN_FN("CMCreateNewColorCursor");
// SECURITY: 555587 cursor values must be validated
if (cacheIndex >= CM_CURSOR_CACHE_SIZE) {
TRC_ERR(( TB, _T("Invalid cache index %d"), cacheIndex));
hr = E_TSC_CORE_CACHEVALUE;
DC_QUIT;
}
TRC_DBG((TB, _T("Cached index %d"), cacheIndex));
oldHandle = _CM.cursorCache[cacheIndex];
// Create the new color cursor. Save in the cache.
// This is for the 'old' cursor protocol so we hard coded the color
// depth as 24 bpp.
// SECURITY 559307: CMCreate<XXX>Cursor need size of PDU passed in
hr = CMCreateColorCursor(24, pAttr, dataLen, &newHandle);
DC_QUIT_ON_FAIL(hr);
_CM.cursorCache[cacheIndex] = newHandle;
if (newHandle != NULL) {
// New cursor created OK.
*pNewHandle = newHandle;
}
else {
// Failed to create the new color cursor - use default
TRC_ALT((TB, _T("Failed to create color cursor")));
*pNewHandle = CM_DEFAULT_ARROW_CURSOR_HANDLE;
}
*pOldHandle = oldHandle;
DC_EXIT_POINT:
DC_END_FN();
return hr;
}
inline HCURSOR DCINTERNAL CMGetCachedCursor(unsigned cacheIndex)
{
DC_BEGIN_FN("CMGetCachedCursor");
TRC_NRM((TB, _T("Cached color pointer - index %d"), cacheIndex));
TRC_ASSERT((cacheIndex < CM_CURSOR_CACHE_SIZE),
(TB, _T("Invalid cache index %d"), cacheIndex));
/************************************************************************/
/* Assume NULL means we failed to create the cursor, so use the */
/* default. If the server has not sent this definition, that is not our */
/* fault. */
/************************************************************************/
// SECURITY 550811: Cache index must be verified
if (cacheIndex < CM_CURSOR_CACHE_SIZE &&
_CM.cursorCache[cacheIndex] != NULL) {
DC_END_FN();
return _CM.cursorCache[cacheIndex];
}
else {
TRC_ALT((TB, _T("No cached cursor - use default")));
DC_END_FN();
return CM_DEFAULT_ARROW_CURSOR_HANDLE;
}
}
// Platform specific prototypes.
HBITMAP CMCreateXORBitmap(LPBITMAPINFO,
TS_COLORPOINTERATTRIBUTE UNALIGNED FAR *);
HCURSOR CMCreatePlatformCursor(TS_COLORPOINTERATTRIBUTE UNALIGNED FAR *,
HBITMAP, HBITMAP);
#ifdef OS_WINCE
DCVOID DCINTERNAL CMMakeMonoDIB(HDC, LPBITMAPINFO, PDCUINT8, PDCUINT8);
#endif // OS_WINCE
private:
CUT* _pUt;
CUH* _pUh;
CCD* _pCd;
CIH* _pIh;
CUI* _pUi;
private:
CObjs* _pClientObjects;
};
#undef TRC_FILE
#undef TRC_GROUP
#undef TSC_HR_FILEID
#endif // _H_CM