555 lines
13 KiB
C++
555 lines
13 KiB
C++
|
//*********************************************************************
|
||
|
//* Microsoft Windows **
|
||
|
//* Copyright(c) Microsoft Corp., 1994-1995 **
|
||
|
//*********************************************************************
|
||
|
|
||
|
//
|
||
|
// CLSUTIL.C - some small, useful C++ classes to wrap memory allocation,
|
||
|
// registry access, etc.
|
||
|
//
|
||
|
|
||
|
// HISTORY:
|
||
|
//
|
||
|
// 12/07/94 jeremys Borrowed from WNET common library
|
||
|
//
|
||
|
|
||
|
#include "inetcplp.h"
|
||
|
#define DECL_CRTFREE
|
||
|
#include <crtfree.h>
|
||
|
|
||
|
BOOL BUFFER::Alloc( UINT cbBuffer )
|
||
|
{
|
||
|
_lpBuffer = (LPTSTR)::GlobalAlloc(GPTR,cbBuffer);
|
||
|
if (_lpBuffer != NULL) {
|
||
|
_cb = cbBuffer;
|
||
|
return TRUE;
|
||
|
}
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
BOOL BUFFER::Realloc( UINT cbNew )
|
||
|
{
|
||
|
LPVOID lpNew = ::GlobalReAlloc((HGLOBAL)_lpBuffer, cbNew,
|
||
|
GMEM_MOVEABLE | GMEM_ZEROINIT);
|
||
|
if (lpNew == NULL)
|
||
|
return FALSE;
|
||
|
|
||
|
_lpBuffer = (LPTSTR)lpNew;
|
||
|
_cb = cbNew;
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
BUFFER::BUFFER( UINT cbInitial /* =0 */ )
|
||
|
: BUFFER_BASE(),
|
||
|
_lpBuffer( NULL )
|
||
|
{
|
||
|
if (cbInitial)
|
||
|
Alloc( cbInitial );
|
||
|
}
|
||
|
|
||
|
BUFFER::~BUFFER()
|
||
|
{
|
||
|
if (_lpBuffer != NULL) {
|
||
|
GlobalFree((HGLOBAL) _lpBuffer);
|
||
|
_lpBuffer = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
BOOL BUFFER::Resize( UINT cbNew )
|
||
|
{
|
||
|
BOOL fSuccess;
|
||
|
|
||
|
if (QuerySize() == 0)
|
||
|
fSuccess = Alloc( cbNew );
|
||
|
else {
|
||
|
fSuccess = Realloc( cbNew );
|
||
|
}
|
||
|
if (fSuccess)
|
||
|
_cb = cbNew;
|
||
|
return fSuccess;
|
||
|
}
|
||
|
|
||
|
RegEntry::RegEntry(const TCHAR *pszSubKey, HKEY hkey, REGSAM regsam)
|
||
|
{
|
||
|
_error = RegCreateKeyEx(hkey, pszSubKey, 0, NULL, 0, regsam, NULL, &_hkey, NULL);
|
||
|
if (_error) {
|
||
|
bhkeyValid = FALSE;
|
||
|
}
|
||
|
else {
|
||
|
bhkeyValid = TRUE;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
RegEntry::~RegEntry()
|
||
|
{
|
||
|
if (bhkeyValid) {
|
||
|
RegCloseKey(_hkey);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
long RegEntry::SetValue(const TCHAR *pszValue, const TCHAR *string)
|
||
|
{
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegSetValueEx(_hkey, pszValue, 0, REG_SZ,
|
||
|
(LPBYTE)string, (lstrlen(string)+1)*sizeof(TCHAR));
|
||
|
}
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
long RegEntry::SetValue(const TCHAR *pszValue, unsigned long dwNumber)
|
||
|
{
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegSetValueEx(_hkey, pszValue, 0, REG_BINARY,
|
||
|
(LPBYTE)&dwNumber, sizeof(dwNumber));
|
||
|
}
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
long RegEntry::DeleteValue(const TCHAR *pszValue)
|
||
|
{
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegDeleteValue(_hkey, (LPTSTR) pszValue);
|
||
|
}
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
|
||
|
TCHAR *RegEntry::GetString(const TCHAR *pszValue, TCHAR *string, unsigned long length)
|
||
|
{
|
||
|
DWORD dwType;
|
||
|
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegQueryValueEx(_hkey, (LPTSTR) pszValue, 0, &dwType, (LPBYTE)string,
|
||
|
&length);
|
||
|
}
|
||
|
if (_error) {
|
||
|
*string = '\0';
|
||
|
return NULL;
|
||
|
}
|
||
|
|
||
|
return string;
|
||
|
}
|
||
|
|
||
|
long RegEntry::GetNumber(const TCHAR *pszValue, long dwDefault)
|
||
|
{
|
||
|
DWORD dwType;
|
||
|
long dwNumber = 0L;
|
||
|
DWORD dwSize = sizeof(dwNumber);
|
||
|
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegQueryValueEx(_hkey, (LPTSTR) pszValue, 0, &dwType, (LPBYTE)&dwNumber,
|
||
|
&dwSize);
|
||
|
}
|
||
|
if (_error)
|
||
|
dwNumber = dwDefault;
|
||
|
|
||
|
return dwNumber;
|
||
|
}
|
||
|
|
||
|
long RegEntry::MoveToSubKey(const TCHAR *pszSubKeyName)
|
||
|
{
|
||
|
HKEY _hNewKey;
|
||
|
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegOpenKeyEx ( _hkey,
|
||
|
pszSubKeyName,
|
||
|
0,
|
||
|
KEY_READ|KEY_WRITE,
|
||
|
&_hNewKey );
|
||
|
if (_error == ERROR_SUCCESS) {
|
||
|
RegCloseKey(_hkey);
|
||
|
_hkey = _hNewKey;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
long RegEntry::FlushKey()
|
||
|
{
|
||
|
if (bhkeyValid) {
|
||
|
_error = RegFlushKey(_hkey);
|
||
|
}
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
RegEnumValues::RegEnumValues(RegEntry *pReqRegEntry)
|
||
|
: pRegEntry(pReqRegEntry),
|
||
|
iEnum(0),
|
||
|
pchName(NULL),
|
||
|
pbValue(NULL)
|
||
|
{
|
||
|
_error = pRegEntry->GetError();
|
||
|
if (_error == ERROR_SUCCESS) {
|
||
|
_error = RegQueryInfoKey ( pRegEntry->GetKey(), // Key
|
||
|
NULL, // Buffer for class string
|
||
|
NULL, // Size of class string buffer
|
||
|
NULL, // Reserved
|
||
|
NULL, // Number of subkeys
|
||
|
NULL, // Longest subkey name
|
||
|
NULL, // Longest class string
|
||
|
&cEntries, // Number of value entries
|
||
|
&cMaxValueName, // Longest value name
|
||
|
&cMaxData, // Longest value data
|
||
|
NULL, // Security descriptor
|
||
|
NULL ); // Last write time
|
||
|
}
|
||
|
if (_error == ERROR_SUCCESS) {
|
||
|
if (cEntries != 0) {
|
||
|
cMaxValueName = cMaxValueName + 1; // REG_SZ needs one more for null
|
||
|
cMaxData = cMaxData + 1; // REG_SZ needs one more for null
|
||
|
pchName = new TCHAR[cMaxValueName];
|
||
|
if (!pchName) {
|
||
|
_error = ERROR_NOT_ENOUGH_MEMORY;
|
||
|
}
|
||
|
else {
|
||
|
if (cMaxData) {
|
||
|
pbValue = new BYTE[cMaxData];
|
||
|
if (!pbValue) {
|
||
|
_error = ERROR_NOT_ENOUGH_MEMORY;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
RegEnumValues::~RegEnumValues()
|
||
|
{
|
||
|
delete pchName;
|
||
|
delete pbValue;
|
||
|
}
|
||
|
|
||
|
long RegEnumValues::Next()
|
||
|
{
|
||
|
if (_error != ERROR_SUCCESS) {
|
||
|
return _error;
|
||
|
}
|
||
|
if (cEntries == iEnum) {
|
||
|
return ERROR_NO_MORE_ITEMS;
|
||
|
}
|
||
|
|
||
|
DWORD cchName = cMaxValueName;
|
||
|
|
||
|
dwDataLength = cMaxData;
|
||
|
_error = RegEnumValue ( pRegEntry->GetKey(), // Key
|
||
|
iEnum, // Index of value
|
||
|
pchName, // Address of buffer for value name
|
||
|
&cchName, // Address for size of buffer
|
||
|
NULL, // Reserved
|
||
|
&dwType, // Data type
|
||
|
pbValue, // Address of buffer for value data
|
||
|
&dwDataLength ); // Address for size of data
|
||
|
iEnum++;
|
||
|
return _error;
|
||
|
}
|
||
|
|
||
|
//////////////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CAccessibleWrapper implementation
|
||
|
//
|
||
|
//////////////////////////////////////////////////////////////////////////////
|
||
|
|
||
|
|
||
|
|
||
|
CAccessibleWrapper::CAccessibleWrapper( IAccessible * pAcc )
|
||
|
: m_ref( 1 ),
|
||
|
m_pAcc( pAcc ),
|
||
|
m_pEnumVar( NULL ),
|
||
|
m_pOleWin( NULL )
|
||
|
{
|
||
|
m_pAcc->AddRef();
|
||
|
}
|
||
|
|
||
|
CAccessibleWrapper::~CAccessibleWrapper()
|
||
|
{
|
||
|
m_pAcc->Release();
|
||
|
if( m_pEnumVar )
|
||
|
m_pEnumVar->Release();
|
||
|
if( m_pOleWin )
|
||
|
m_pOleWin->Release();
|
||
|
}
|
||
|
|
||
|
|
||
|
// IUnknown
|
||
|
// Implement refcounting ourselves
|
||
|
// Also implement QI ourselves, so that we return a ptr back to the wrapper.
|
||
|
STDMETHODIMP CAccessibleWrapper::QueryInterface(REFIID riid, void** ppv)
|
||
|
{
|
||
|
HRESULT hr;
|
||
|
*ppv = NULL;
|
||
|
|
||
|
if ((riid == IID_IUnknown) ||
|
||
|
(riid == IID_IDispatch) ||
|
||
|
(riid == IID_IAccessible))
|
||
|
{
|
||
|
*ppv = (IAccessible *) this;
|
||
|
}
|
||
|
else if( riid == IID_IEnumVARIANT )
|
||
|
{
|
||
|
// Get the IEnumVariant from the object we are sub-classing so we can delegate
|
||
|
// calls.
|
||
|
if( ! m_pEnumVar )
|
||
|
{
|
||
|
hr = m_pAcc->QueryInterface( IID_IEnumVARIANT, (void **) & m_pEnumVar );
|
||
|
if( FAILED( hr ) )
|
||
|
{
|
||
|
m_pEnumVar = NULL;
|
||
|
return hr;
|
||
|
}
|
||
|
// Paranoia (in case QI returns S_OK with NULL...)
|
||
|
if( ! m_pEnumVar )
|
||
|
return E_NOINTERFACE;
|
||
|
}
|
||
|
|
||
|
*ppv = (IEnumVARIANT *) this;
|
||
|
}
|
||
|
else if( riid == IID_IOleWindow )
|
||
|
{
|
||
|
// Get the IOleWindow from the object we are sub-classing so we can delegate
|
||
|
// calls.
|
||
|
if( ! m_pOleWin )
|
||
|
{
|
||
|
hr = m_pAcc->QueryInterface( IID_IOleWindow, (void **) & m_pOleWin );
|
||
|
if( FAILED( hr ) )
|
||
|
{
|
||
|
m_pOleWin = NULL;
|
||
|
return hr;
|
||
|
}
|
||
|
// Paranoia (in case QI returns S_OK with NULL...)
|
||
|
if( ! m_pOleWin )
|
||
|
return E_NOINTERFACE;
|
||
|
}
|
||
|
|
||
|
*ppv = (IOleWindow*) this;
|
||
|
}
|
||
|
else
|
||
|
return(E_NOINTERFACE);
|
||
|
|
||
|
AddRef();
|
||
|
return(NOERROR);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP_(ULONG) CAccessibleWrapper::AddRef()
|
||
|
{
|
||
|
return ++m_ref;
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP_(ULONG) CAccessibleWrapper::Release()
|
||
|
{
|
||
|
ULONG ulRet = --m_ref;
|
||
|
|
||
|
if( ulRet == 0 )
|
||
|
delete this;
|
||
|
|
||
|
return ulRet;
|
||
|
}
|
||
|
|
||
|
|
||
|
// IDispatch
|
||
|
// - pass all through m_pAcc
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::GetTypeInfoCount(UINT* pctinfo)
|
||
|
{
|
||
|
return m_pAcc->GetTypeInfoCount(pctinfo);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::GetTypeInfo(UINT itinfo, LCID lcid, ITypeInfo** pptinfo)
|
||
|
{
|
||
|
return m_pAcc->GetTypeInfo(itinfo, lcid, pptinfo);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::GetIDsOfNames(REFIID riid, OLECHAR** rgszNames, UINT cNames,
|
||
|
LCID lcid, DISPID* rgdispid)
|
||
|
{
|
||
|
return m_pAcc->GetIDsOfNames(riid, rgszNames, cNames, lcid, rgdispid);
|
||
|
}
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::Invoke(DISPID dispidMember, REFIID riid, LCID lcid, WORD wFlags,
|
||
|
DISPPARAMS* pdispparams, VARIANT* pvarResult, EXCEPINFO* pexcepinfo,
|
||
|
UINT* puArgErr)
|
||
|
{
|
||
|
return m_pAcc->Invoke(dispidMember, riid, lcid, wFlags,
|
||
|
pdispparams, pvarResult, pexcepinfo,
|
||
|
puArgErr);
|
||
|
}
|
||
|
|
||
|
|
||
|
// IAccessible
|
||
|
// - pass all through m_pAcc
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accParent(IDispatch ** ppdispParent)
|
||
|
{
|
||
|
return m_pAcc->get_accParent(ppdispParent);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accChildCount(long* pChildCount)
|
||
|
{
|
||
|
return m_pAcc->get_accChildCount(pChildCount);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accChild(VARIANT varChild, IDispatch ** ppdispChild)
|
||
|
{
|
||
|
return m_pAcc->get_accChild(varChild, ppdispChild);
|
||
|
}
|
||
|
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accName(VARIANT varChild, BSTR* pszName)
|
||
|
{
|
||
|
return m_pAcc->get_accName(varChild, pszName);
|
||
|
}
|
||
|
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accValue(VARIANT varChild, BSTR* pszValue)
|
||
|
{
|
||
|
return m_pAcc->get_accValue(varChild, pszValue);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accDescription(VARIANT varChild, BSTR* pszDescription)
|
||
|
{
|
||
|
return m_pAcc->get_accDescription(varChild, pszDescription);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accRole(VARIANT varChild, VARIANT *pvarRole)
|
||
|
{
|
||
|
return m_pAcc->get_accRole(varChild, pvarRole);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accState(VARIANT varChild, VARIANT *pvarState)
|
||
|
{
|
||
|
return m_pAcc->get_accState(varChild, pvarState);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accHelp(VARIANT varChild, BSTR* pszHelp)
|
||
|
{
|
||
|
return m_pAcc->get_accHelp(varChild, pszHelp);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accHelpTopic(BSTR* pszHelpFile, VARIANT varChild, long* pidTopic)
|
||
|
{
|
||
|
return m_pAcc->get_accHelpTopic(pszHelpFile, varChild, pidTopic);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accKeyboardShortcut(VARIANT varChild, BSTR* pszKeyboardShortcut)
|
||
|
{
|
||
|
return m_pAcc->get_accKeyboardShortcut(varChild, pszKeyboardShortcut);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accFocus(VARIANT * pvarFocusChild)
|
||
|
{
|
||
|
return m_pAcc->get_accFocus(pvarFocusChild);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accSelection(VARIANT * pvarSelectedChildren)
|
||
|
{
|
||
|
return m_pAcc->get_accSelection(pvarSelectedChildren);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::get_accDefaultAction(VARIANT varChild, BSTR* pszDefaultAction)
|
||
|
{
|
||
|
return m_pAcc->get_accDefaultAction(varChild, pszDefaultAction);
|
||
|
}
|
||
|
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::accSelect(long flagsSel, VARIANT varChild)
|
||
|
{
|
||
|
return m_pAcc->accSelect(flagsSel, varChild);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::accLocation(long* pxLeft, long* pyTop, long* pcxWidth, long* pcyHeight, VARIANT varChild)
|
||
|
{
|
||
|
return m_pAcc->accLocation(pxLeft, pyTop, pcxWidth, pcyHeight, varChild);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::accNavigate(long navDir, VARIANT varStart, VARIANT * pvarEndUpAt)
|
||
|
{
|
||
|
return m_pAcc->accNavigate(navDir, varStart, pvarEndUpAt);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::accHitTest(long xLeft, long yTop, VARIANT * pvarChildAtPoint)
|
||
|
{
|
||
|
return m_pAcc->accHitTest(xLeft, yTop, pvarChildAtPoint);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::accDoDefaultAction(VARIANT varChild)
|
||
|
{
|
||
|
return m_pAcc->accDoDefaultAction(varChild);
|
||
|
}
|
||
|
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::put_accName(VARIANT varChild, BSTR szName)
|
||
|
{
|
||
|
return m_pAcc->put_accName(varChild, szName);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::put_accValue(VARIANT varChild, BSTR pszValue)
|
||
|
{
|
||
|
return m_pAcc->put_accValue(varChild, pszValue);
|
||
|
}
|
||
|
|
||
|
|
||
|
// IEnumVARIANT
|
||
|
// - pass all through m_pEnumVar
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::Next(ULONG celt, VARIANT* rgvar, ULONG * pceltFetched)
|
||
|
{
|
||
|
return m_pEnumVar->Next(celt, rgvar, pceltFetched);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::Skip(ULONG celt)
|
||
|
{
|
||
|
return m_pEnumVar->Skip(celt);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::Reset()
|
||
|
{
|
||
|
return m_pEnumVar->Reset();
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::Clone(IEnumVARIANT ** ppenum)
|
||
|
{
|
||
|
return m_pEnumVar->Clone(ppenum);
|
||
|
}
|
||
|
|
||
|
// IOleWindow
|
||
|
// - pass all through m_pOleWin
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::GetWindow(HWND* phwnd)
|
||
|
{
|
||
|
return m_pOleWin->GetWindow(phwnd);
|
||
|
}
|
||
|
|
||
|
|
||
|
STDMETHODIMP CAccessibleWrapper::ContextSensitiveHelp(BOOL fEnterMode)
|
||
|
{
|
||
|
return m_pOleWin->ContextSensitiveHelp(fEnterMode);
|
||
|
}
|
||
|
|