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.
636 lines
17 KiB
636 lines
17 KiB
/*============================================================================
|
|
*
|
|
* _ITABLE.H
|
|
*
|
|
* Internal header file for MAPI 1.0 In-memory MAPI Table DLL
|
|
*
|
|
* Copyright (C) 1993 and 1994 Microsoft Corporation
|
|
*
|
|
*
|
|
* Hungarian shorthand:
|
|
* To avoid excessively long identifier names, the following
|
|
* shorthand expressions are used:
|
|
*
|
|
* LPSPropTagArray lppta
|
|
* LPSRestriction lpres
|
|
* LPSPropValue lpprop
|
|
* LPSRow lprow
|
|
* LPSRowSet lprows
|
|
* LPSSortOrder lpso
|
|
* LPSSortOrderSet lpsos
|
|
*/
|
|
|
|
// $MAC - Fix up some naming conflicts
|
|
|
|
#ifdef MAC
|
|
#define FFindColumn ITABLE_FFindColumn
|
|
#endif
|
|
|
|
typedef struct _TAD FAR * LPTAD;
|
|
typedef struct _VUE FAR * LPVUE;
|
|
|
|
// Global Constants
|
|
#define ROW_CHUNK_SIZE 50
|
|
#define COLUMN_CHUNK_SIZE 15
|
|
|
|
// Max number of notifications to send in a batch
|
|
//
|
|
// Raid: Horsefly/Exchange/36281
|
|
// This was changed from 8 to 1 because code in itable.c which fills in
|
|
// the batch cannot guarantee the correct order of the notifications in
|
|
// it. If this is ever changed, that bug will have to be revisited.
|
|
//
|
|
#define MAX_BATCHED_NOTIFS 1
|
|
|
|
// For use in aligning data in buffers
|
|
#if defined (_AMD64_) || defined (_IA64_)
|
|
#define ALIGNTYPE LARGE_INTEGER
|
|
#else
|
|
#define ALIGNTYPE DWORD
|
|
#endif
|
|
#define ALIGN ((ULONG) (sizeof(ALIGNTYPE) - 1))
|
|
#define LcbAlignLcb(lcb) (((lcb) + ALIGN) & ~ALIGN)
|
|
#define PbAlignPb(pb) ((LPBYTE) ((((DWORD) (pb)) + ALIGN) & ~ALIGN))
|
|
|
|
// This structure is used to keep track of a private memory buffer which is
|
|
// used with the private AllocateMore function ScBufAllocateMore(). This
|
|
// allows for one MAPI memory allocation when the size of a property is known
|
|
// and the author wishes to use PropCopyMore. See ITABLE.C ScCopyTadRow()
|
|
// for an example.
|
|
typedef struct _CMB
|
|
{
|
|
ULONG ulcb;
|
|
LPVOID lpv;
|
|
} CMB, * LPCMB;
|
|
|
|
|
|
#if !defined(NO_VALIDATION)
|
|
|
|
#define VALIDATE_OBJ(lpobj,objtype,fn,lpVtbl) \
|
|
if ( BAD_STANDARD_OBJ(lpobj,objtype,fn,lpVtbl)) \
|
|
{ \
|
|
DebugTrace( TEXT("%s::%s() - Invalid parameter passed as %s object\n"), \
|
|
#objtype, \
|
|
#fn, \
|
|
#objtype ); \
|
|
return ResultFromScode( MAPI_E_INVALID_PARAMETER ); \
|
|
}
|
|
|
|
#endif
|
|
|
|
#ifndef BEGIN_INTERFACE
|
|
#define BEGIN_INTERFACE
|
|
#endif
|
|
|
|
// $MAC - Supprt for WLM 4.0
|
|
#ifndef VTABLE_FILL
|
|
#define VTABLE_FILL
|
|
#endif
|
|
|
|
|
|
|
|
#define HrSetLastErrorIds(lpobj,sc,ids) \
|
|
UNKOBJ_HrSetLastError((LPUNKOBJ)(lpobj), \
|
|
(sc), \
|
|
(ids))
|
|
|
|
|
|
|
|
#ifdef WIN32
|
|
#define LockObj(lpobj) UNKOBJ_Lock((LPUNKOBJ)(lpobj))
|
|
__inline VOID
|
|
UNKOBJ_Lock( LPUNKOBJ lpunkobj )
|
|
{
|
|
EnterCriticalSection(&lpunkobj->csid);
|
|
}
|
|
|
|
#define UnlockObj(lpobj) UNKOBJ_Unlock((LPUNKOBJ)(lpobj))
|
|
__inline VOID
|
|
UNKOBJ_Unlock( LPUNKOBJ lpunkobj )
|
|
{
|
|
LeaveCriticalSection(&lpunkobj->csid);
|
|
}
|
|
#else
|
|
#define LockObj(lpobj)
|
|
#define UnlockObj(lpobj)
|
|
#endif
|
|
|
|
|
|
// Memory Management Macros for code readability
|
|
|
|
#define ScAllocateBuffer(lpobj,ulcb,lppv) \
|
|
UNKOBJ_ScAllocate((LPUNKOBJ)(lpobj), \
|
|
(ulcb), \
|
|
(LPVOID FAR *)(lppv))
|
|
|
|
|
|
#define ScAllocateMore(lpobj,ulcb,lpv,lppv) \
|
|
UNKOBJ_ScAllocateMore((LPUNKOBJ)(lpobj), \
|
|
(ulcb), \
|
|
(lpv), \
|
|
(LPVOID FAR *)(lppv))
|
|
|
|
#define ScFreeBuffer(lpobj,lpv) \
|
|
UNKOBJ_Free((LPUNKOBJ)(lpobj), (lpv))
|
|
|
|
#define ScCOAllocate(lpunkobj,ulcb,lplpv) \
|
|
UNKOBJ_ScCOAllocate((LPUNKOBJ)(lpunkobj),(ulcb),(lplpv))
|
|
|
|
|
|
#define ScCOReallocate(lpunkobj,ulcb,lplpv) \
|
|
UNKOBJ_ScCOReallocate((LPUNKOBJ)(lpunkobj),(ulcb),(lplpv))
|
|
|
|
|
|
#define COFree(lpunkobj,lpv) \
|
|
UNKOBJ_COFree((LPUNKOBJ)(lpunkobj),(lpv))
|
|
|
|
|
|
#define MAPIFreeRows(lpobj,lprows) \
|
|
UNKOBJ_FreeRows((LPUNKOBJ)(lpobj),(lprows))
|
|
|
|
|
|
|
|
|
|
/*============================================================================
|
|
* TAD (table data class)
|
|
*
|
|
* Implementes in-memory table data object.
|
|
*/
|
|
|
|
#undef INTERFACE
|
|
#define INTERFACE struct _TAD
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) MAPIMETHOD_DECLARE(type,method,TAD_)
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_ITABLEDATA_METHODS(IMPL)
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) MAPIMETHOD_TYPEDEF(type,method,TAD_)
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_ITABLEDATA_METHODS(IMPL)
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) STDMETHOD_(type,method)
|
|
|
|
DECLARE_MAPI_INTERFACE(TAD_)
|
|
{
|
|
BEGIN_INTERFACE
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_ITABLEDATA_METHODS(IMPL)
|
|
};
|
|
|
|
typedef struct _TAD
|
|
{
|
|
TAD_Vtbl FAR * lpVtbl;
|
|
UNKOBJ_MEMBERS;
|
|
|
|
UNKINST inst;
|
|
|
|
LPVUE lpvueList;
|
|
|
|
ULONG ulTableType;
|
|
ULONG ulPropTagIndexCol;
|
|
|
|
ULONG ulcColsMac;
|
|
LPSPropTagArray lpptaCols; // Initial view col set (CO)
|
|
|
|
ULONG ulcRowsAdd;
|
|
ULONG ulcRowMacAdd;
|
|
LPSRow * parglprowAdd; // Unsorted Row Set (CO)
|
|
|
|
ULONG ulcRowsIndex;
|
|
ULONG ulcRowMacIndex;
|
|
LPSRow * parglprowIndex; // Row Set Sorted by Index (CO)
|
|
|
|
LPVOID lpvDataSource; // used to store container specific data
|
|
ULONG cbDataSource; // bytes in lpvDataSource to copy to new allocation.
|
|
// If non-zero, CreateView should LocalAlloc this size
|
|
// and copy data from lpvDataSource into it. Release
|
|
// should LocalFree.
|
|
|
|
// With multiple containers, it becomes necessary to figure
|
|
// out which container the table represents. We cache the containers
|
|
// EID in the table for easy access. This is a pointer .. no need to free
|
|
LPSBinary pbinContEID;
|
|
|
|
// When calling get ContentsTable, we may sometimes want a list of
|
|
// contents from ALL the folders/containers for a particular profile and
|
|
// return those contents as a single contentstable. Following flag caches
|
|
// this setting so we collate contents of all folders. Works only if the
|
|
// container being opened was the PAB container and if bProfilesAPIEnabled
|
|
// (ie profiles were invoked explicitly)
|
|
BOOL bAllProfileContents;
|
|
|
|
// For PAB containers where profilesAPIEnabled=FALSE, GetContentsTable
|
|
// typically means return contents of ALL the WAB since user hasn;t asked for
|
|
// profiles. In this case we may want to have the option of opening only
|
|
// a particular folder and getting only the conetnts of that folder .. so we
|
|
// need a flag to cache this inverse option.
|
|
BOOL bContainerContentsOnly;
|
|
|
|
// When calling GetContentsTable, the caller can specify MAPI_UNICODE
|
|
// for unicode tables.. we cache that flag in case we need to refill the table
|
|
// at some later point ..
|
|
BOOL bMAPIUnicodeTable;
|
|
} TAD;
|
|
|
|
SCODE
|
|
ScCopyTadRowSet(
|
|
LPTAD lptad,
|
|
LPSRowSet lprowsetIn,
|
|
ULONG * pcNewTags,
|
|
ULONG * pcRows,
|
|
LPSRow * * pparglprowUnsortedCopy,
|
|
LPSRow * * pparglprowSortedCopy );
|
|
|
|
SCODE
|
|
ScCopyTadRow( LPTAD lptad,
|
|
LPSRow lprow,
|
|
ULONG * pTagsAdded,
|
|
LPSRow FAR * lplprowCopy );
|
|
|
|
VOID
|
|
UpdateViews( LPTAD lptad,
|
|
ULONG cRowsToRemove,
|
|
LPSRow * parglprowToRemove,
|
|
ULONG cRowsToAdd,
|
|
LPSRow * parglprowToAddUnsorted,
|
|
LPSRow * parglprowToAddSorted );
|
|
|
|
VOID
|
|
FixupView(
|
|
LPVUE lpvue,
|
|
ULONG cRowsToRemove,
|
|
LPSRow * parglprowToRemove,
|
|
ULONG cRowsToAdd,
|
|
LPSRow * parglprowToAddUnsorted,
|
|
LPSRow * parglprowToAddSorted );
|
|
|
|
SCODE
|
|
ScReplaceRows(
|
|
LPTAD lptad,
|
|
ULONG cRowsNew,
|
|
LPSRow * parglprowNew,
|
|
ULONG * pcRowsOld,
|
|
LPSRow * * pparglprowOld );
|
|
|
|
SCODE
|
|
ScFindRow( LPTAD lptad,
|
|
LPSPropValue lpprop,
|
|
LPSRow * * pplprow );
|
|
SCODE
|
|
ScAddRow( LPUNKOBJ lpunkobj,
|
|
LPSSortOrderSet lpsos,
|
|
LPSRow lprow,
|
|
ULONG uliRow,
|
|
ULONG * pulcRows,
|
|
ULONG * pulcRowsMac,
|
|
LPSRow ** pparglprows,
|
|
LPSRow ** pplprow );
|
|
|
|
|
|
|
|
|
|
|
|
/*============================================================================
|
|
* VUE (table view class)
|
|
*/
|
|
|
|
#undef INTERFACE
|
|
#define INTERFACE struct _VUE
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) MAPIMETHOD_DECLARE(type,method,VUE_)
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_IMAPITABLE_METHODS(IMPL)
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) MAPIMETHOD_TYPEDEF(type,method,VUE_)
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_IMAPITABLE_METHODS(IMPL)
|
|
#undef MAPIMETHOD_
|
|
#define MAPIMETHOD_(type,method) STDMETHOD_(type,method)
|
|
|
|
DECLARE_MAPI_INTERFACE(VUE_)
|
|
{
|
|
BEGIN_INTERFACE
|
|
MAPI_IUNKNOWN_METHODS(IMPL)
|
|
MAPI_IMAPITABLE_METHODS(IMPL)
|
|
};
|
|
|
|
/* BOOKMARK status
|
|
*
|
|
* dwfBKSFree is used for a bookmark that is NOT valid and
|
|
* is available for use
|
|
* dwfBKSValid is set for any used bookmark.
|
|
* dwfChanged is used with dwfBKSValid to indicate that the marked row
|
|
* has moved since the last query which in involved this
|
|
* bookmark
|
|
* dwfBKSMoving is used with dwfBKSValid to indicate that the marked row is
|
|
* in the process of being moved relative to other rows.
|
|
* dwfBKSStale is used with dwfBKSValid to indicate the given bookmark
|
|
* no longer marks a row but has not been Freed
|
|
* dwfBKSMask is the set of all valid bookmark status
|
|
*
|
|
*/
|
|
#define dwfBKSFree ((DWORD) 0x00000000)
|
|
#define dwfBKSValid ((DWORD) 0x00000001)
|
|
#define dwfBKSChanged ((DWORD) 0x00000002)
|
|
#define dwfBKSMoving ((DWORD) 0x00000004)
|
|
#define dwfBKSStale ((DWORD) 0x00000008)
|
|
#define dwfBKSMask (~(dwfBKSValid|dwfBKSChanged|dwfBKSMoving|dwfBKSStale))
|
|
|
|
#define FBadBookmark(lpvue,bk) \
|
|
((bk) >= cBookmarksMax || \
|
|
((lpvue)->rgbk[(bk)].dwfBKS == dwfBKSFree) || \
|
|
((lpvue)->rgbk[(bk)].dwfBKS & dwfBKSMask)) \
|
|
|
|
typedef struct
|
|
{
|
|
DWORD dwfBKS; // Bookmark status
|
|
union
|
|
{
|
|
ULONG uliRow; // dwfBKSValid || dwfBKSChanged
|
|
LPSRow lprow; // dwfBKSMoving
|
|
};
|
|
} BK, * PBK;
|
|
|
|
|
|
// There is a maximum of 42 client defined bookmarks for each VUE. This
|
|
// seems adequate for an in-memory table.
|
|
// Bookmarks are kept as an array of 45 where the first three are
|
|
// the MAPI predefined bookmarks.
|
|
|
|
#define cBookmarksMax 45 // Max. # of bookmarks including reserved ones
|
|
#define cBookmarksReserved 3 // # of reserved bookmarks (begin, cur, end)
|
|
|
|
#define BOOKMARK_MEMBERS \
|
|
struct \
|
|
{ \
|
|
union \
|
|
{ \
|
|
struct \
|
|
{ \
|
|
BK bkBeginning; \
|
|
BK bkCurrent; \
|
|
BK bkEnd; \
|
|
}; \
|
|
BK rgbk[cBookmarksMax]; \
|
|
}; \
|
|
} \
|
|
|
|
typedef BOOKMARK_MEMBERS UBK, * PUBK;
|
|
|
|
typedef struct _VUE
|
|
{
|
|
VUE_Vtbl FAR * lpVtbl;
|
|
UNKOBJ_MEMBERS;
|
|
|
|
LPVUE lpvueNext;
|
|
LPTAD lptadParent;
|
|
|
|
LPSPropTagArray lpptaCols; // Column set (MAPI)
|
|
LPSRestriction lpres; // Restriction (MAPI)
|
|
LPSSortOrderSet lpsos; // Sort order set (MAPI)
|
|
|
|
CALLERRELEASE FAR * lpfReleaseCallback;
|
|
ULONG ulReleaseData;
|
|
|
|
ULONG ulcRowMac; // Space available for rows
|
|
LPSRow * parglprows; // Sorted Row Set
|
|
|
|
BOOKMARK_MEMBERS;
|
|
|
|
LPADVISELIST lpAdviseList;
|
|
ULONG ulcAdvise;
|
|
MAPIUID mapiuidNotif;
|
|
|
|
LPVOID lpvDataSource; // used to store container specific data
|
|
ULONG cbDataSource; // bytes in lpvDataSource to copy to new allocation.
|
|
// If non-zero, CreateView should LocalAlloc this size
|
|
// and copy data from lpvDataSource into it. Release
|
|
// should LocalFree.
|
|
|
|
BOOL bMAPIUnicodeTable; //tracks whether parent table needs UNICODE data or not
|
|
|
|
} VUE;
|
|
|
|
typedef struct _VUENOTIFKEY
|
|
{
|
|
ULONG ulcb;
|
|
MAPIUID mapiuid;
|
|
|
|
} VUENOTIFKEY;
|
|
|
|
BOOL
|
|
FBookMarkStale( LPVUE lpvue,
|
|
BOOKMARK bk);
|
|
|
|
SCODE
|
|
ScLoadRows( ULONG ulcRowsSrc,
|
|
LPSRow * rglprowsSrc,
|
|
LPVUE lpvue,
|
|
LPSRestriction lpres,
|
|
LPSSortOrderSet lpsos );
|
|
|
|
SCODE
|
|
ScDeleteAllRows( LPTAD lptad);
|
|
|
|
SCODE
|
|
ScMaybeAddRow( LPVUE lpvue,
|
|
LPSRestriction lpres,
|
|
LPSSortOrderSet lpsos,
|
|
LPSRow lprow,
|
|
ULONG uliRow,
|
|
ULONG * pulcRows,
|
|
ULONG * pulcRowMac,
|
|
LPSRow ** pparglprows,
|
|
LPSRow ** pplprow );
|
|
|
|
SCODE
|
|
ScCopyVueRow( LPVUE lpvue,
|
|
LPSPropTagArray lpptaCols,
|
|
LPSRow lprowSrc,
|
|
LPSRow lprowDst );
|
|
|
|
|
|
|
|
|
|
/*============================================================================
|
|
* Utilities
|
|
*/
|
|
|
|
SCODE
|
|
ScDupRestriction( LPUNKOBJ lpunkobj,
|
|
LPSRestriction lpres,
|
|
LPSRestriction FAR * lplpresCopy );
|
|
|
|
SCODE
|
|
ScDupRestrictionMore( LPUNKOBJ lpunkobj,
|
|
LPSRestriction lpresSrc,
|
|
LPVOID lpvLink,
|
|
LPSRestriction lpresDst );
|
|
|
|
SCODE
|
|
ScSatisfiesRestriction( LPSRow lprow,
|
|
LPSRestriction lpres,
|
|
ULONG * pfSatisfies );
|
|
SCODE
|
|
ScDupRgbEx( LPUNKOBJ lpunkobj,
|
|
ULONG ulcb,
|
|
LPBYTE lpb,
|
|
ULONG ulcbExtra,
|
|
LPBYTE FAR * lplpbCopy );
|
|
|
|
LPSRow *
|
|
PlprowCollateRow( ULONG ulcRows,
|
|
LPSRow * rglprows,
|
|
LPSSortOrderSet lpsos,
|
|
BOOL fAfterExisting,
|
|
LPSRow lprow );
|
|
|
|
LPSRow *
|
|
PlprowByLprow( ULONG ulcRows,
|
|
LPSRow * rglprows,
|
|
LPSRow lprow );
|
|
|
|
LPSPropValue __fastcall
|
|
LpSPropValueFindColumn( LPSRow lprow,
|
|
ULONG ulPropTagColumn );
|
|
|
|
STDMETHODIMP_(SCODE)
|
|
ScBufAllocateMore( ULONG ulcb,
|
|
LPCMB lpcmb,
|
|
LPVOID FAR * lplpv );
|
|
|
|
ULONG
|
|
UlcbPropToCopy( LPSPropValue lpprop );
|
|
|
|
|
|
|
|
#ifndef WIN16 // WIN16 C (not C++) doesn't support INLINE functions.
|
|
// Functions are defined in ITABLE.C.
|
|
/*============================================================================
|
|
- FFindColumn()
|
|
-
|
|
* Checks a prop tag array to see if a given prop tag exists.
|
|
*
|
|
* NOTE! The prop tag must match completely (even type).
|
|
*
|
|
*
|
|
* Parameters:
|
|
* lpptaCols in Prop tag array to check
|
|
* ulPropTag in Prop tag to check for.
|
|
*
|
|
* Returns:
|
|
* TRUE if ulPropTag is in lpptaCols
|
|
* FALSE if ulPropTag is not in lpptaCols
|
|
*/
|
|
|
|
__inline BOOL
|
|
FFindColumn( LPSPropTagArray lpptaCols,
|
|
ULONG ulPropTag )
|
|
{
|
|
UNALIGNED ULONG * pulPropTag;
|
|
|
|
|
|
pulPropTag = lpptaCols->aulPropTag + lpptaCols->cValues;
|
|
while ( --pulPropTag >= lpptaCols->aulPropTag )
|
|
if ( *pulPropTag == ulPropTag )
|
|
return TRUE;
|
|
|
|
return FALSE;
|
|
}
|
|
|
|
|
|
|
|
/*============================================================================
|
|
- ScFindRow()
|
|
-
|
|
* Finds the first row in the table data whose index column property
|
|
* value is equal to that of the specified property and returns the
|
|
* location of that row in the table data, or, if no such row exists,
|
|
* the end of the table data.
|
|
*
|
|
* Parameters:
|
|
* lptad in TAD in which to find row
|
|
* lpprop in Index property to match
|
|
* puliRow out Pointer to location of found row
|
|
*
|
|
* Error returns:
|
|
* MAPI_E_INVALID_PARAMETER If proptag of property isn't the TAD's
|
|
* index column's proptag.
|
|
* MAPI_E_NOT_FOUND If no matching row is found (*pplprow
|
|
* is set to lptad->parglprows +
|
|
* lptad->cRows in this case).
|
|
*/
|
|
|
|
__inline SCODE
|
|
ScFindRow(
|
|
LPTAD lptad,
|
|
LPSPropValue lpprop,
|
|
LPSRow * * pplprow)
|
|
{
|
|
SCODE sc = S_OK;
|
|
SRow row = {0, 1, lpprop};
|
|
SizedSSortOrderSet(1, sosIndex) = { 1, 0, 0 };
|
|
|
|
if (lpprop->ulPropTag != lptad->ulPropTagIndexCol)
|
|
{
|
|
sc = MAPI_E_INVALID_PARAMETER;
|
|
goto ret;
|
|
}
|
|
|
|
Assert(!IsBadWritePtr(pplprow, sizeof(*pplprow)));
|
|
|
|
// Build a sort order set for the Index Column
|
|
sosIndex.aSort[0].ulPropTag = lptad->ulPropTagIndexCol;
|
|
sosIndex.aSort[0].ulOrder = TABLE_SORT_ASCEND;
|
|
|
|
*pplprow = PlprowCollateRow(lptad->ulcRowsIndex,
|
|
lptad->parglprowIndex,
|
|
(LPSSortOrderSet) &sosIndex,
|
|
FALSE,
|
|
&row);
|
|
|
|
// Find the row in the Index Sorted Row Set
|
|
if ( !lptad->ulcRowsIndex
|
|
|| (*pplprow >= (lptad->parglprowIndex + lptad->ulcRowsIndex))
|
|
|| LPropCompareProp( lpprop, (**pplprow)->lpProps))
|
|
{
|
|
sc = MAPI_E_NOT_FOUND;
|
|
}
|
|
|
|
ret:
|
|
return sc;
|
|
}
|
|
#else // !WIN16
|
|
BOOL FFindColumn( LPSPropTagArray lpptaCols, ULONG ulPropTag );
|
|
SCODE ScFindRow( LPTAD lptad, LPSPropValue lpprop, LPSRow * * pplprow);
|
|
#endif // !WIN16
|
|
|
|
|
|
// This macro is used on a ULONG or INT that is to be used as denominator
|
|
// If ul is non-zero it is returned unchanged. If ul is zero then a 1 is
|
|
// returned.
|
|
#define UlDenominator(ul) ((ul) | !(ul))
|
|
|
|
BOOL
|
|
FRowContainsProp(LPSRow lprow,
|
|
ULONG cValues,
|
|
LPSPropValue lpsv);
|
|
|
|
STDAPI_(SCODE)
|
|
CreateTableData(LPCIID lpiid,
|
|
ALLOCATEBUFFER FAR * lpfAllocateBuffer,
|
|
ALLOCATEMORE FAR * lpfAllocateMore,
|
|
FREEBUFFER FAR * lpfFreeBuffer,
|
|
LPVOID lpvReserved,
|
|
ULONG ulTableType,
|
|
ULONG ulPropTagIndexCol,
|
|
LPSPropTagArray lpptaCols,
|
|
LPVOID lpvDataSource,
|
|
ULONG cbDataSource,
|
|
LPSBinary pbinContEID,
|
|
ULONG ulFlags,
|
|
LPTABLEDATA FAR * lplptad);
|
|
|
|
HRESULT HrVUERestrict( LPVUE lpvue,
|
|
LPSRestriction lpres,
|
|
ULONG ulFlags );
|