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.
243 lines
6.7 KiB
243 lines
6.7 KiB
//+---------------------------------------------------------------------------
|
|
//
|
|
// Microsoft Windows
|
|
// Copyright (C) Microsoft Corporation, 1992 - 1993.
|
|
//
|
|
// File: df32.hxx
|
|
//
|
|
// Contents: Docfile generic header for 32-bit functions
|
|
//
|
|
// Classes: CGlobalSecurity
|
|
// CDfMutex
|
|
//
|
|
// History: 09-Oct-93 DrewB Created
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
#ifndef __DF32_HXX__
|
|
#define __DF32_HXX__
|
|
|
|
#ifdef WIN32
|
|
|
|
// Make an scode out of the last Win32 error
|
|
// Error that may map to STG_* scodes should go through Win32ErrorToScode
|
|
#define WIN32_SCODE(err) HRESULT_FROM_WIN32(err)
|
|
#define LAST_SCODE WIN32_SCODE(GetLastError())
|
|
#define LAST_STG_SCODE Win32ErrorToScode(GetLastError())
|
|
|
|
//+---------------------------------------------------------------------------
|
|
//
|
|
// Class: CGlobalSecurity (gs)
|
|
//
|
|
// Purpose: Encapsulates a global SECURITY_DESCRIPTOR and
|
|
// SECURITY_ATTRIBUTES
|
|
//
|
|
// Interface: See below
|
|
//
|
|
// History: 18-Jun-93 DrewB Created
|
|
//
|
|
// Notes: Only active for Win32 platforms which support security
|
|
// Init MUST be called before this is used
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
#if WIN32 == 100 || WIN32 > 200
|
|
|
|
// This leaves space for 8 sub authorities. Currently NT only uses 6
|
|
const DWORD SIZEOF_SID = 44;
|
|
|
|
// This leaves space for 1 access allowed ACEs in the ACL.
|
|
const DWORD SIZEOF_ACL = sizeof(ACL) + sizeof(ACCESS_ALLOWED_ACE) + SIZEOF_SID;
|
|
|
|
const DWORD SIZEOF_TOKEN_USER = sizeof(TOKEN_USER) + SIZEOF_SID;
|
|
|
|
class CGlobalSecurity
|
|
{
|
|
private:
|
|
BYTE _acl[SIZEOF_ACL];
|
|
SECURITY_DESCRIPTOR _sd;
|
|
BYTE _sdExt[SIZEOF_SID*2 + SIZEOF_ACL];
|
|
SECURITY_ATTRIBUTES _sa;
|
|
#if DBG == 1
|
|
BOOL _fInit;
|
|
#endif
|
|
|
|
public:
|
|
#if DBG == 1
|
|
CGlobalSecurity(void) { _fInit = FALSE; }
|
|
#endif
|
|
SCODE Init(BOOL fAcl)
|
|
{
|
|
#ifdef MULTIHEAP
|
|
ACL *pacl = fAcl ? (ACL *) &_acl : NULL;
|
|
BYTE pTokenUser[SIZEOF_TOKEN_USER];
|
|
|
|
if (pacl != NULL)
|
|
{
|
|
BOOL fToken = TRUE;
|
|
HANDLE hToken;
|
|
DWORD lIgnore;
|
|
|
|
// Initialize a new ACL.
|
|
if (!InitializeAcl( pacl, SIZEOF_ACL, ACL_REVISION))
|
|
return LAST_SCODE;
|
|
|
|
if (!OpenThreadToken(GetCurrentThread(), TOKEN_READ, TRUE, &hToken))
|
|
{
|
|
if (!OpenProcessToken(GetCurrentProcess(), TOKEN_READ, &hToken))
|
|
fToken = FALSE;
|
|
}
|
|
|
|
if (fToken)
|
|
{
|
|
if (!GetTokenInformation( hToken, TokenUser,
|
|
(TOKEN_USER*)pTokenUser, SIZEOF_TOKEN_USER, &lIgnore ))
|
|
{
|
|
CloseHandle (hToken);
|
|
return LAST_SCODE;
|
|
}
|
|
CloseHandle (hToken);
|
|
|
|
// Allow current user access.
|
|
if (!AddAccessAllowedAce( pacl, ACL_REVISION,
|
|
STANDARD_RIGHTS_ALL | GENERIC_ALL,
|
|
((TOKEN_USER *)pTokenUser)->User.Sid ))
|
|
return LAST_SCODE;
|
|
}
|
|
}
|
|
#else
|
|
ACL *pacl = NULL;
|
|
#endif
|
|
|
|
if (!InitializeSecurityDescriptor(&_sd, SECURITY_DESCRIPTOR_REVISION))
|
|
return LAST_SCODE;
|
|
|
|
if (!SetSecurityDescriptorDacl(&_sd, TRUE, pacl, FALSE))
|
|
return LAST_SCODE;
|
|
|
|
_sa.nLength = sizeof(SECURITY_ATTRIBUTES);
|
|
_sa.lpSecurityDescriptor = &_sd;
|
|
_sa.bInheritHandle = FALSE;
|
|
#if DBG == 1
|
|
_fInit = TRUE;
|
|
#endif
|
|
return S_OK;
|
|
}
|
|
|
|
operator SECURITY_DESCRIPTOR *(void) { olAssert(_fInit); return &_sd; }
|
|
operator SECURITY_ATTRIBUTES *(void) { olAssert(_fInit); return &_sa; }
|
|
};
|
|
#endif
|
|
|
|
|
|
//
|
|
// Global Critical Sections have two components. One piece is shared between
|
|
// all applications using the global lock. This portion will typically reside
|
|
// in some sort of shared memory. The second piece is per-process. This
|
|
// contains a per-process handle to the shared critical section lock semaphore.
|
|
// The semaphore is itself shared, but each process may have a different handle
|
|
// value to the semaphore.
|
|
//
|
|
// Global critical sections are attached to by name. The application wishing to
|
|
// attach must know the name of the critical section (actually the name of the
|
|
// shared lock semaphore, and must know the address of the global portion of
|
|
// the critical section
|
|
//
|
|
|
|
#define SUPPORT_RECURSIVE_LOCK
|
|
|
|
typedef struct _GLOBAL_SHARED_CRITICAL_SECTION {
|
|
LONG LockCount;
|
|
#ifdef SUPPORT_RECURSIVE_LOCK
|
|
LONG RecursionCount;
|
|
DWORD OwningThread;
|
|
#else
|
|
#if DBG == 1
|
|
DWORD OwningThread;
|
|
#endif
|
|
#endif
|
|
DWORD Reserved;
|
|
} GLOBAL_SHARED_CRITICAL_SECTION, *PGLOBAL_SHARED_CRITICAL_SECTION;
|
|
|
|
|
|
|
|
//+---------------------------------------------------------------------------
|
|
//
|
|
// Class: CDfMutex (dmtx)
|
|
//
|
|
// Purpose: A multi-process synchronization object
|
|
//
|
|
// Interface: See below
|
|
//
|
|
// History: 05-Apr-93 DrewB Created
|
|
// 19-Jul-95 SusiA Added HaveMutex
|
|
//
|
|
// Notes: Only active for Win32 implementations which support threads
|
|
// For platforms with security, a global security descriptor is
|
|
// used
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
// Default timeout of twenty minutes
|
|
#define DFM_TIMEOUT 1200000
|
|
|
|
class CDfMutex
|
|
{
|
|
public:
|
|
inline CDfMutex(void);
|
|
SCODE Init(TCHAR *ptcsName);
|
|
~CDfMutex(void);
|
|
|
|
SCODE Take(DWORD dwTimeout);
|
|
void Release(void);
|
|
|
|
BOOL IsHandleValid (TCHAR *ptcsName);
|
|
|
|
#if DBG == 1
|
|
//check to see if the current thread already has the mutex
|
|
inline BOOL HaveMutex(void);
|
|
#endif
|
|
private:
|
|
PGLOBAL_SHARED_CRITICAL_SECTION _pGlobalPortion;
|
|
HANDLE _hLockSemaphore;
|
|
HANDLE _hSharedMapping;
|
|
};
|
|
|
|
inline CDfMutex::CDfMutex(void)
|
|
{
|
|
_pGlobalPortion = NULL;
|
|
_hLockSemaphore = NULL;
|
|
_hSharedMapping = NULL;
|
|
}
|
|
|
|
#if DBG == 1
|
|
//+--------------------------------------------------------------
|
|
//
|
|
// Member: CDfMutex::HaveMutex, public
|
|
//
|
|
// Synopsis: This routine checks to see if the current thread
|
|
// already has the mutex
|
|
//
|
|
// History: 19-Jul-95 SusiA Created
|
|
//
|
|
// Algorithm: Checks the current thread to see if it already owns
|
|
// the mutex. Returns TRUE if it does, FALSE otherwise
|
|
//
|
|
//
|
|
//---------------------------------------------------------------
|
|
|
|
inline BOOL
|
|
CDfMutex::HaveMutex(
|
|
void
|
|
)
|
|
{
|
|
if ( _pGlobalPortion->OwningThread == GetCurrentThreadId())
|
|
return TRUE;
|
|
else
|
|
return FALSE;
|
|
}
|
|
#endif // DBG == 1
|
|
|
|
#endif // WIN32
|
|
|
|
#endif // #ifndef __DF32_HXX__
|