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.
 
 
 
 
 
 

510 lines
12 KiB

///////////////////////////////////////////////////////////////////////////////
//
// Copyright (c) Microsoft Corporation
//
// SYNOPSIS
//
// Defines the class DatabasePage.
//
///////////////////////////////////////////////////////////////////////////////
#include "Precompiled.h"
#include "dbpage.h"
#include "changenotification.h"
#include "dbconfig.h"
#include "dbnode.h"
#include "loggingmethodsnode.h"
#include "iasutil.h"
DatabasePage::DatabasePage(
LONG_PTR notifyHandle,
wchar_t* title,
DatabaseNode* newSrc
)
: CIASPropertyPage<DatabasePage>(notifyHandle, title, TRUE),
src(newSrc),
initString(0),
dbConfigDirty(false),
sdoConfigDirty(false)
{
}
DatabasePage::~DatabasePage() throw ()
{
CoTaskMemFree(initString);
}
HRESULT DatabasePage::Initialize(
ISdo* config,
ISdoServiceControl* control
) throw ()
{
HRESULT hr = CoMarshalInterThreadInterfaceInStream(
__uuidof(ISdo),
config,
&configStream
);
if (FAILED(hr))
{
return hr;
}
hr = CoMarshalInterThreadInterfaceInStream(
__uuidof(ISdoServiceControl),
control,
&controlStream
);
if (FAILED(hr))
{
return hr;
}
if (src->GetInitString() != 0)
{
initString = com_wcsdup(src->GetInitString());
dataSourceName = src->GetDataSourceName();
if ((initString == 0) || !dataSourceName)
{
return E_OUTOFMEMORY;
}
}
return S_OK;
}
BOOL DatabasePage::OnApply() throw ()
{
HRESULT hr;
// Validate the max sessions.
UINT maxSessions = GetDlgItemInt(IDC_DB_EDIT_MAX_SESSIONS, 0, FALSE);
if ((maxSessions < 1) || (maxSessions > 100))
{
ShowErrorDialog(
m_hWnd,
IDS_DB_E_INVALID_SESSIONS,
0,
0,
IDS_DB_E_TITLE
);
::SetFocus(GetDlgItem(IDC_DB_EDIT_MAX_SESSIONS));
return FALSE;
}
if (dbConfigDirty)
{
hr = IASStoreDatabaseConfig(
src->GetServerName(),
initString,
dataSourceName
);
if (SUCCEEDED(hr))
{
// We only need to send a change notification for the database config
// since the SDO config is never cached.
CChangeNotification* chg = new (std::nothrow) CChangeNotification();
if (chg != 0)
{
chg->m_dwFlags = CHANGE_UPDATE_RESULT_NODE;
chg->m_pNode = src;
chg->m_pParentNode = src->Parent();
PropertyChangeNotify(reinterpret_cast<LPARAM>(chg));
}
dbConfigDirty = false;
}
else
{
ShowErrorDialog(
m_hWnd,
IDS_DB_E_CANT_WRITE_DB_CONFIG,
0,
hr,
IDS_DB_E_TITLE
);
}
}
if (sdoConfigDirty)
{
SaveBool(
IDC_DB_CHECK_ACCT,
PROPERTY_ACCOUNTING_LOG_ACCOUNTING
);
SaveBool(
IDC_DB_CHECK_AUTH,
PROPERTY_ACCOUNTING_LOG_AUTHENTICATION
);
SaveBool(
IDC_DB_CHECK_INTERIM,
PROPERTY_ACCOUNTING_LOG_ACCOUNTING_INTERIM
);
VARIANT v;
V_VT(&v) = VT_I4;
V_I4(&v) = maxSessions;
configSdo->PutProperty(PROPERTY_ACCOUNTING_SQL_MAX_SESSIONS, &v);
hr = configSdo->Apply();
if (SUCCEEDED(hr))
{
sdoConfigDirty = false;
}
else
{
ShowErrorDialog(
m_hWnd,
IDS_DB_E_CANT_WRITE_SDO_CONFIG,
0,
hr,
IDS_DB_E_TITLE
);
}
}
controlSdo->ResetService();
return TRUE;
}
HRESULT DatabasePage::ConfigureConnection() throw ()
{
HRESULT hr;
// Create the MSDAINITIALIZE object if necessary.
if (dataInitialize == 0)
{
hr = CoCreateInstance(
CLSID_MSDAINITIALIZE,
0,
CLSCTX_INPROC_SERVER,
__uuidof(IDataInitialize),
reinterpret_cast<void**>(&dataInitialize)
);
if (FAILED(hr))
{
return hr;
}
}
// Create the current data source if necessary.
if ((initString != 0) && !dataSource)
{
dataInitialize->GetDataSource(
0,
CLSCTX_INPROC_SERVER,
initString,
__uuidof(IDBProperties),
reinterpret_cast<IUnknown**>(&dataSource)
);
// Ignore errors. If the init string is invalid, we'll just let the
// user create a new one from scratch.
}
// Create the DataLinks object if necessary.
if (dataLinks == 0)
{
hr = CoCreateInstance(
CLSID_DataLinks,
0,
CLSCTX_INPROC_SERVER,
__uuidof(IDBPromptInitialize),
reinterpret_cast<void**>(&dataLinks)
);
if (FAILED(hr))
{
return hr;
}
}
// Since we don't want to let the admin choose the provider, we have to
// supply a data source object to the DataLinks UI. If one is currently
// configured we use that; otherwise, we create an empty SQL Server
// provider.
CComPtr<IDBProperties> newDataSource;
if (dataSource)
{
newDataSource = dataSource;
}
else
{
CLSID clsid;
hr = CLSIDFromProgID(L"SQLOLEDB", &clsid);
if (FAILED(hr))
{
return hr;
}
hr = CoCreateInstance(
clsid,
0,
CLSCTX_INPROC_SERVER,
__uuidof(IDBProperties),
reinterpret_cast<void**>(&newDataSource)
);
if (FAILED(hr))
{
return hr;
}
}
// Bring up the UI to let the user configure the data source.
hr = dataLinks->PromptDataSource(
0,
m_hWnd,
(DBPROMPTOPTIONS_PROPERTYSHEET |
DBPROMPTOPTIONS_DISABLE_PROVIDER_SELECTION),
0,
0,
0,
__uuidof(IDBProperties),
reinterpret_cast<IUnknown**>(&(newDataSource.p))
);
if (FAILED(hr))
{
return hr;
}
// Get the data source name.
DBPROPID propId = DBPROP_INIT_DATASOURCE;
DBPROPIDSET propIdSet;
propIdSet.rgPropertyIDs = &propId;
propIdSet.cPropertyIDs = 1;
propIdSet.guidPropertySet = DBPROPSET_DBINIT;
ULONG numPropSets;
DBPROPSET* propSets = 0;
hr = newDataSource->GetProperties(
1,
&propIdSet,
&numPropSets,
&propSets
);
CComBSTR newDataSourceName;
if (SUCCEEDED(hr))
{
newDataSourceName.Attach(V_BSTR(&(propSets[0].rgProperties[0].vValue)));
}
// Have to clean up even in some failure cases.
if (propSets != 0)
{
CoTaskMemFree(propSets[0].rgProperties);
CoTaskMemFree(propSets);
}
if (FAILED(hr))
{
return hr;
}
// Get the initialization string.
LPOLESTR newInitString;
hr = dataInitialize->GetInitializationString(
newDataSource,
1,
&newInitString
);
if (FAILED(hr))
{
return hr;
}
// All went well, so store the result.
CoTaskMemFree(initString);
initString = newInitString;
dataSourceName.Empty();
dataSourceName.Attach(newDataSourceName.Detach());
dataSource = newDataSource;
return S_OK;
}
void DatabasePage::LoadBool(UINT control, LONG propId) throw ()
{
VARIANT v;
VariantInit(&v);
HRESULT hr = configSdo->GetProperty(propId, &v);
if (SUCCEEDED(hr))
{
if ((V_VT(&v) == VT_BOOL) && V_BOOL(&v))
{
::SendMessage(GetDlgItem(control), BM_SETCHECK, 1, 0);
}
VariantClear(&v);
}
}
void DatabasePage::SaveBool(UINT control, LONG propId) throw ()
{
BOOL newVal = SendDlgItemMessage(control, BM_GETCHECK, 0, 0);
VARIANT v;
V_VT(&v) = VT_BOOL;
V_BOOL(&v) = newVal ? VARIANT_TRUE : VARIANT_FALSE;
configSdo->PutProperty(propId, &v);
}
LRESULT DatabasePage::OnInitDialog(
UINT uMsg,
WPARAM wParam,
LPARAM lParam,
BOOL& bHandled
)
{
HRESULT hr = CoUnmarshalInterface(
configStream,
__uuidof(ISdo),
reinterpret_cast<void**>(&configSdo)
);
if (SUCCEEDED(hr))
{
hr = CoUnmarshalInterface(
controlStream,
__uuidof(ISdoServiceControl),
reinterpret_cast<void**>(&controlSdo)
);
}
configStream.Release();
controlStream.Release();
if (FAILED(hr))
{
ShowErrorDialog(
m_hWnd,
IDS_DB_E_CANT_INIT_DIALOG,
0,
hr,
IDS_DB_E_TITLE
);
EnableWindow(FALSE);
}
LoadBool(
IDC_DB_CHECK_ACCT,
PROPERTY_ACCOUNTING_LOG_ACCOUNTING
);
LoadBool(
IDC_DB_CHECK_AUTH,
PROPERTY_ACCOUNTING_LOG_AUTHENTICATION
);
LoadBool(
IDC_DB_CHECK_INTERIM,
PROPERTY_ACCOUNTING_LOG_ACCOUNTING_INTERIM
);
VARIANT maxSessions;
VariantInit(&maxSessions);
hr = configSdo->GetProperty(
PROPERTY_ACCOUNTING_SQL_MAX_SESSIONS,
&maxSessions
);
if (SUCCEEDED(hr))
{
if (V_VT(&maxSessions) == VT_I4)
{
SetDlgItemInt(IDC_DB_EDIT_MAX_SESSIONS, V_I4(&maxSessions), FALSE);
}
VariantClear(&maxSessions);
}
// Max sessions is 100, so don't let the user enter more than 3 digits.
::SendMessage(GetDlgItem(IDC_DB_EDIT_MAX_SESSIONS), EM_LIMITTEXT, 3, 0);
if (dataSourceName != 0)
{
SetDlgItemText(IDC_DB_EDIT_DATA_SOURCE, dataSourceName);
}
return TRUE;
}
LRESULT DatabasePage::OnChange(
WORD wNotifyCode,
WORD wID,
HWND hWndCtl,
BOOL& bHandled
)
{
sdoConfigDirty = true;
SetModified(TRUE);
return 0;
}
LRESULT DatabasePage::OnClear(
WORD wNotifyCode,
WORD wID,
HWND hWndCtl,
BOOL& bHandled
)
{
if (initString != 0)
{
// Clear out the config.
CoTaskMemFree(initString);
initString = 0;
dataSourceName.Empty();
dataSource.Release();
// Clear out the UI.
SetDlgItemText(IDC_DB_EDIT_DATA_SOURCE, L"");
// Mark ourselves as modified.
dbConfigDirty = true;
SetModified(TRUE);
}
return 0;
}
LRESULT DatabasePage::OnConfigure(
WORD wNotifyCode,
WORD wID,
HWND hWndCtl,
BOOL& bHandled
)
{
HRESULT hr = ConfigureConnection();
if (SUCCEEDED(hr))
{
// Update the UI.
if (dataSourceName)
{
SetDlgItemText(IDC_DB_EDIT_DATA_SOURCE, dataSourceName);
}
else
{
SetDlgItemText(IDC_DB_EDIT_DATA_SOURCE, L"");
}
// Mark ourselves as modified.
dbConfigDirty = true;
SetModified(TRUE);
}
return 0;
}