4772 lines
124 KiB
C++
4772 lines
124 KiB
C++
/**********************************************************************/
|
|
/** Microsoft Windows/NT **/
|
|
/** Copyright(c) Microsoft Corporation, 1997 - 1999 **/
|
|
/**********************************************************************/
|
|
|
|
/*
|
|
actreg.cpp
|
|
WINS active registrations node information.
|
|
|
|
FILE HISTORY:
|
|
|
|
*/
|
|
|
|
#include "stdafx.h"
|
|
#include "nodes.h"
|
|
#include "actreg.h"
|
|
#include "server.h"
|
|
#include "Queryobj.h"
|
|
#include "statmapp.h"
|
|
#include "fndrcdlg.h"
|
|
#include <string.h>
|
|
#include "pushtrig.h"
|
|
#include "tregkey.h"
|
|
#include "chkrgdlg.h"
|
|
#include "dynrecpp.h"
|
|
#include "vrfysrv.h"
|
|
#include "delrcdlg.h"
|
|
#include "delowner.h"
|
|
#include "cprogdlg.h"
|
|
#include "loadrecs.h"
|
|
|
|
#include "verify.h"
|
|
|
|
WORD gwUnicodeHeader = 0xFEFF;
|
|
|
|
#define INFINITE_EXPIRATION 0x7FFFFFFF
|
|
#define BADNAME_CHAR _T('-') // This char is substituted for bad characters
|
|
// NetBIOS names.
|
|
UINT guActregMessageStrings[] =
|
|
{
|
|
IDS_ACTREG_MESSAGE_BODY1,
|
|
IDS_ACTREG_MESSAGE_BODY2,
|
|
IDS_ACTREG_MESSAGE_BODY3,
|
|
-1
|
|
};
|
|
|
|
BOOL
|
|
WinsIsPrint(char * pChar)
|
|
{
|
|
WORD charType;
|
|
|
|
// isprint isn't working for thai characters, so use the GetStringType
|
|
// API and figure it out ourselves.
|
|
BOOL fRet = GetStringTypeA(LOCALE_SYSTEM_DEFAULT, CT_CTYPE1, pChar, 1, &charType);
|
|
if (!fRet)
|
|
return 0;
|
|
|
|
return !(charType & C1_CNTRL) ? 1 : 0;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
class CSortWorker
|
|
---------------------------------------------------------------------------*/
|
|
CSortWorker::CSortWorker(IWinsDatabase * pCurrentDatabase,
|
|
int nColumn,
|
|
DWORD dwSortOptions)
|
|
{
|
|
m_pCurrentDatabase = pCurrentDatabase;
|
|
m_nColumn = nColumn;
|
|
m_dwSortOptions = dwSortOptions;
|
|
}
|
|
|
|
|
|
CSortWorker::~CSortWorker()
|
|
{
|
|
}
|
|
|
|
|
|
void
|
|
CSortWorker::OnDoAction()
|
|
{
|
|
#ifdef DEBUG
|
|
CString strType;
|
|
CTime timeStart, timeFinish;
|
|
timeStart = CTime::GetCurrentTime();
|
|
#endif
|
|
|
|
WINSDB_SORT_TYPE uSortType = WINSDB_SORT_BY_NAME;
|
|
|
|
switch (m_nColumn)
|
|
{
|
|
case ACTREG_COL_NAME:
|
|
uSortType = WINSDB_SORT_BY_NAME;
|
|
break;
|
|
|
|
case ACTREG_COL_TYPE:
|
|
uSortType = WINSDB_SORT_BY_TYPE;
|
|
break;
|
|
|
|
case ACTREG_COL_IPADDRESS:
|
|
uSortType = WINSDB_SORT_BY_IP;
|
|
break;
|
|
|
|
case ACTREG_COL_STATE:
|
|
uSortType = WINSDB_SORT_BY_STATE;
|
|
break;
|
|
|
|
case ACTREG_COL_STATIC:
|
|
uSortType = WINSDB_SORT_BY_STATIC;
|
|
break;
|
|
|
|
case ACTREG_COL_VERSION:
|
|
uSortType = WINSDB_SORT_BY_VERSION;
|
|
break;
|
|
|
|
case ACTREG_COL_EXPIRATION:
|
|
uSortType = WINSDB_SORT_BY_EXPIRATION;
|
|
break;
|
|
|
|
case ACTREG_COL_OWNER:
|
|
uSortType = WINSDB_SORT_BY_OWNER;
|
|
break;
|
|
}
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
m_pCurrentDatabase->Sort(uSortType, m_dwSortOptions);
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
#ifdef DEBUG
|
|
timeFinish = CTime::GetCurrentTime();
|
|
CTimeSpan timeDelta = timeFinish - timeStart;
|
|
CString str = timeDelta.Format(_T("%H:%M:%S"));
|
|
|
|
Trace2("Record Sorting for the column: %d, total time %s\n",
|
|
uSortType, str);
|
|
#endif
|
|
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CActiveRegistrationsHandler
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
CActiveRegistrationsHandler::CActiveRegistrationsHandler(ITFSComponentData *pCompData)
|
|
: CMTWinsHandler(pCompData), m_dlgLoadRecords(IDS_VIEW_RECORDS)
|
|
{
|
|
m_winsdbState = WINSDB_NORMAL;
|
|
m_bExpanded = FALSE;
|
|
m_pCurrentDatabase = NULL;
|
|
m_fFindNameOrIP = TRUE;
|
|
m_NonBlocking = 1;
|
|
|
|
m_pServerInfoArray = NULL;
|
|
|
|
m_fLoadedOnce = FALSE;
|
|
m_fFindLoaded = FALSE;
|
|
m_fDbLoaded = FALSE;
|
|
m_fForceReload = TRUE;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::~CActiveRegistrationsHandler
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
CActiveRegistrationsHandler::~CActiveRegistrationsHandler()
|
|
{
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::DestroyHandler
|
|
Release and pointers we have here
|
|
Author: EricDav
|
|
----------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::DestroyHandler
|
|
(
|
|
ITFSNode * pNode
|
|
)
|
|
{
|
|
m_spServerNode.Set(NULL);
|
|
return hrOK;
|
|
}
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::InitializeNode
|
|
Initializes node specific data
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::InitializeNode
|
|
(
|
|
ITFSNode * pNode
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
CString strTemp;
|
|
|
|
m_strActiveReg.LoadString(IDS_ACTIVEREG);
|
|
SetDisplayName(m_strActiveReg);
|
|
|
|
m_strDesp.LoadString(IDS_ACTIVEREG_DISC);
|
|
|
|
// Make the node immediately visible
|
|
pNode->SetData(TFS_DATA_COOKIE, (LPARAM) pNode);
|
|
pNode->SetData(TFS_DATA_IMAGEINDEX, GetImageIndex(FALSE));
|
|
pNode->SetData(TFS_DATA_OPENIMAGEINDEX, GetImageIndex(TRUE));
|
|
pNode->SetData(TFS_DATA_USER, (LPARAM) this);
|
|
pNode->SetData(TFS_DATA_TYPE, WINSSNAP_ACTIVE_REGISTRATIONS);
|
|
pNode->SetData(TFS_DATA_SCOPE_LEAF_NODE, TRUE);
|
|
|
|
SetColumnStringIDs(&aColumns[WINSSNAP_ACTIVE_REGISTRATIONS][0]);
|
|
SetColumnWidths(&aColumnWidths[WINSSNAP_ACTIVE_REGISTRATIONS][0]);
|
|
|
|
if (g_strStaticTypeUnique.IsEmpty())
|
|
{
|
|
g_strStaticTypeUnique.LoadString(IDS_STATIC_RECORD_TYPE_UNIQUE);
|
|
g_strStaticTypeDomainName.LoadString(IDS_STATIC_RECORD_TYPE_DOMAIN_NAME);
|
|
g_strStaticTypeMultihomed.LoadString(IDS_STATIC_RECORD_TYPE_MULTIHOMED);
|
|
g_strStaticTypeGroup.LoadString(IDS_STATIC_RECORD_TYPE_GROUP);
|
|
g_strStaticTypeInternetGroup.LoadString(IDS_STATIC_RECORD_TYPE_INTERNET_GROUP);
|
|
g_strStaticTypeUnknown.LoadString(IDS_STATIC_RECORD_TYPE_UNKNOWN);
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnCreateNodeId2
|
|
Returns a unique string for this node
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT CActiveRegistrationsHandler::OnCreateNodeId2(ITFSNode * pNode, CString & strId, DWORD * dwFlags)
|
|
{
|
|
const GUID * pGuid = pNode->GetNodeType();
|
|
|
|
CString strGuid;
|
|
|
|
StringFromGUID2(*pGuid, strGuid.GetBuffer(256), 256);
|
|
strGuid.ReleaseBuffer();
|
|
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
strId = pServer->m_strServerAddress + strGuid;
|
|
|
|
return hrOK;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
Overridden base handler functions
|
|
---------------------------------------------------------------------------*/
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetString
|
|
Implementation of ITFSNodeHandler::GetString
|
|
Author: KennT
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP_(LPCTSTR)
|
|
CActiveRegistrationsHandler::GetString
|
|
(
|
|
ITFSNode * pNode,
|
|
int nCol
|
|
)
|
|
{
|
|
if (nCol == 0 || nCol == -1)
|
|
{
|
|
return GetDisplayName();
|
|
}
|
|
else
|
|
if (nCol ==1)
|
|
{
|
|
return m_strDesp;
|
|
}
|
|
else
|
|
{
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnExpand
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnExpand
|
|
(
|
|
ITFSNode * pNode,
|
|
LPDATAOBJECT pDataObject,
|
|
DWORD dwType,
|
|
LPARAM arg,
|
|
LPARAM param
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
SPITFSNode spNode;
|
|
SPITFSNodeHandler spHandler;
|
|
ITFSQueryObject * pQuery = NULL;
|
|
CString strIP;
|
|
DWORD dwIP;
|
|
CString strMachineName;
|
|
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
// get the config info for later
|
|
m_Config = pServer->GetConfig();
|
|
|
|
m_RecList.RemoveAll();
|
|
|
|
if (m_bExpanded)
|
|
{
|
|
return hr;
|
|
}
|
|
|
|
strMachineName = _T("\\\\") + pServer->GetServerAddress();
|
|
|
|
// load the name type mapping from the registry
|
|
m_NameTypeMap.SetMachineName(strMachineName);
|
|
m_NameTypeMap.Load();
|
|
|
|
// start the database download for the surrent owner
|
|
if (!m_spWinsDatabase)
|
|
{
|
|
dwIP = pServer->GetServerIP();
|
|
MakeIPAddress(dwIP, strIP);
|
|
|
|
m_dlgLoadRecords.ResetFiltering();
|
|
|
|
CORg(CreateWinsDatabase(strIP, strIP, &m_spWinsDatabase));
|
|
|
|
// set the owner to the current owner
|
|
m_spWinsDatabase->SetApiInfo(
|
|
dwIP,
|
|
NULL,
|
|
FALSE);
|
|
}
|
|
|
|
m_bExpanded = TRUE;
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CWinsServerHandler::OnResultRefresh
|
|
Refreshes the data realting to the server
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnResultRefresh
|
|
(
|
|
ITFSComponent * pComponent,
|
|
LPDATAOBJECT pDataObject,
|
|
MMC_COOKIE cookie,
|
|
LPARAM arg,
|
|
LPARAM lParam
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
SPITFSNode spNode;
|
|
|
|
CORg (m_spNodeMgr->FindNode(cookie, &spNode));
|
|
|
|
// get the stae of the databse if not normal, ie in the loading or filtering state
|
|
// don't let refresh
|
|
if (m_winsdbState != WINSDB_NORMAL)
|
|
{
|
|
return hrOK;
|
|
}
|
|
|
|
RefreshResults(spNode);
|
|
|
|
Error:
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnCreateQuery
|
|
Description
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
ITFSQueryObject *
|
|
CActiveRegistrationsHandler::OnCreateQuery(ITFSNode * pNode)
|
|
{
|
|
CNodeTimerQueryObject * pQObj = new CNodeTimerQueryObject();
|
|
|
|
pQObj->SetTimerInterval(2000);
|
|
|
|
return pQObj;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnHaveData
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::OnHaveData
|
|
(
|
|
ITFSNode * pParentNode,
|
|
LPARAM Data,
|
|
LPARAM Type
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
// This is how we get non-node data back from the background thread.
|
|
HRESULT hr = hrOK;
|
|
WINSDB_STATE uState;
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
if (Type == QDATA_TIMER)
|
|
{
|
|
BOOL bDone;
|
|
|
|
m_spWinsDatabase->GetCurrentState(&uState);
|
|
|
|
bDone = (m_winsdbState == WINSDB_LOADING && uState != WINSDB_LOADING) ||
|
|
(m_winsdbState == WINSDB_FILTERING && uState != WINSDB_LOADING);
|
|
|
|
// if records per owner are downloaded, clear and redraw the
|
|
// items as the records are inserted, rather than being added.
|
|
//if (TRUE /*m_dwOwnerFilter != -1*/)
|
|
//{
|
|
// UpdateCurrentView(pParentNode);
|
|
//}
|
|
|
|
// call into the WinsDatbase object and check the count.
|
|
// if we need to update call..UpdateAllViews
|
|
UpdateListboxCount(pParentNode);
|
|
|
|
UpdateCurrentView(pParentNode);
|
|
|
|
if (m_nState != loading)
|
|
{
|
|
m_nState = loading;
|
|
OnChangeState(pParentNode);
|
|
}
|
|
|
|
|
|
// take care of the tomer in case of the filetr records case
|
|
if (bDone)
|
|
{
|
|
Trace0("ActiveRegHandler::OnHaveData - Done loading DB\n");
|
|
|
|
DatabaseLoadingCleanup();
|
|
|
|
if ( (m_nState != loaded) &&
|
|
(m_nState != unableToLoad) )
|
|
{
|
|
m_nState = loaded;
|
|
m_dwErr = 0;
|
|
OnChangeState(pParentNode);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
return;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CActiveRegistrationsHandler
|
|
Description
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
int CActiveRegistrationsHandler::GetImageIndex(BOOL bOpenImage)
|
|
{
|
|
int nIndex = 0;
|
|
switch (m_nState)
|
|
{
|
|
case notLoaded:
|
|
case loaded:
|
|
case unableToLoad:
|
|
if (bOpenImage)
|
|
nIndex = ICON_IDX_ACTREG_FOLDER_OPEN;
|
|
else
|
|
nIndex = ICON_IDX_ACTREG_FOLDER_CLOSED;
|
|
break;
|
|
|
|
case loading:
|
|
if (bOpenImage)
|
|
nIndex = ICON_IDX_ACTREG_FOLDER_OPEN_BUSY;
|
|
else
|
|
nIndex = ICON_IDX_ACTREG_FOLDER_CLOSED_BUSY;
|
|
break;
|
|
|
|
default:
|
|
ASSERT(FALSE);
|
|
}
|
|
return nIndex;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnAddMenuItems
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::OnAddMenuItems
|
|
(
|
|
ITFSNode * pNode,
|
|
LPCONTEXTMENUCALLBACK pContextMenuCallback,
|
|
LPDATAOBJECT lpDataObject,
|
|
DATA_OBJECT_TYPES type,
|
|
DWORD dwType,
|
|
long * pInsertionAllowed
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = S_OK;
|
|
LONG lFlags = 0;
|
|
CString strMenuItem;
|
|
|
|
if (!m_Config.IsAdmin())
|
|
{
|
|
lFlags = MF_GRAYED;
|
|
}
|
|
|
|
if (type == CCT_SCOPE)
|
|
{
|
|
// these menu items go in the new menu,
|
|
// only visible from scope pane
|
|
if (*pInsertionAllowed & CCM_INSERTIONALLOWED_TOP)
|
|
{
|
|
|
|
// find record
|
|
//strMenuItem.LoadString(IDS_ACTIVEREG_FIND_RECORD);
|
|
//hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
// strMenuItem,
|
|
// IDS_ACTIVEREG_FIND_RECORD,
|
|
// CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
// 0 );
|
|
//ASSERT( SUCCEEDED(hr) );
|
|
|
|
// start database load if th state is normal
|
|
if (m_winsdbState == WINSDB_NORMAL)
|
|
{
|
|
strMenuItem.LoadString(IDS_DATABASE_LOAD_START);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_DATABASE_LOAD_START,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
0 );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
}
|
|
else
|
|
{
|
|
strMenuItem.LoadString(IDS_DATABASE_LOAD_STOP);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_DATABASE_LOAD_STOP,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
0 );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
}
|
|
|
|
// separator
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
0,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
MF_SEPARATOR);
|
|
ASSERT( SUCCEEDED(hr) );
|
|
|
|
// create static mapping
|
|
strMenuItem.LoadString(IDS_ACTIVEREG_CREATE_STATIC_MAPPING);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_ACTIVEREG_CREATE_STATIC_MAPPING,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
0 );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
|
|
// separator
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
0,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
MF_SEPARATOR);
|
|
ASSERT( SUCCEEDED(hr) );
|
|
|
|
// import LMHOSTS file
|
|
strMenuItem.LoadString(IDS_ACTIVEREG_IMPORT_LMHOSTS);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_ACTIVEREG_IMPORT_LMHOSTS,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
0 );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
|
|
// only available to admins
|
|
strMenuItem.LoadString(IDS_ACTREG_CHECK_REG_NAMES);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_ACTREG_CHECK_REG_NAMES,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
lFlags );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
|
|
strMenuItem.LoadString(IDS_ACTREG_DELETE_OWNER);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDS_ACTREG_DELETE_OWNER,
|
|
CCM_INSERTIONPOINTID_PRIMARY_TOP,
|
|
0 );
|
|
ASSERT( SUCCEEDED(hr) );
|
|
}
|
|
|
|
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnCommand
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::OnCommand
|
|
(
|
|
ITFSNode * pNode,
|
|
long nCommandId,
|
|
DATA_OBJECT_TYPES type,
|
|
LPDATAOBJECT pDataObject,
|
|
DWORD dwType
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
switch (nCommandId)
|
|
{
|
|
case IDS_ACTIVEREG_CREATE_STATIC_MAPPING:
|
|
OnCreateMapping(pNode);
|
|
break;
|
|
|
|
case IDS_DATABASE_LOAD_START:
|
|
OnDatabaseLoadStart(pNode);
|
|
break;
|
|
|
|
case IDS_DATABASE_LOAD_STOP:
|
|
OnDatabaseLoadStop(pNode);
|
|
break;
|
|
|
|
case IDS_ACTIVEREG_IMPORT_LMHOSTS:
|
|
OnImportLMHOSTS(pNode);
|
|
break;
|
|
|
|
case IDS_ACTIVEREG_EXPORT_WINSENTRIES:
|
|
OnExportEntries();
|
|
break;
|
|
|
|
case IDS_ACTREG_CHECK_REG_NAMES:
|
|
OnCheckRegNames(pNode);
|
|
break;
|
|
|
|
case IDS_ACTREG_DELETE_OWNER:
|
|
OnDeleteOwner(pNode);
|
|
break;
|
|
|
|
default:
|
|
break;
|
|
}
|
|
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::AddMenuItems
|
|
Over-ride this to add our view menu item
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::AddMenuItems
|
|
(
|
|
ITFSComponent * pComponent,
|
|
MMC_COOKIE cookie,
|
|
LPDATAOBJECT pDataObject,
|
|
LPCONTEXTMENUCALLBACK pContextMenuCallback,
|
|
long * pInsertionAllowed
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = S_OK;
|
|
CString strMenuItem;
|
|
LONG lFlags = 0;
|
|
|
|
// figure out if we need to pass this to the scope pane menu handler
|
|
hr = HandleScopeMenus(cookie, pDataObject, pContextMenuCallback, pInsertionAllowed);
|
|
|
|
if (*pInsertionAllowed & CCM_INSERTIONALLOWED_VIEW)
|
|
{
|
|
if (m_fLoadedOnce)
|
|
{
|
|
lFlags = MF_CHECKED|MFT_RADIOCHECK;
|
|
}
|
|
else
|
|
{
|
|
lFlags = 0;
|
|
}
|
|
|
|
strMenuItem.LoadString(IDS_ACTREG_SHOW_ENTIRE);
|
|
hr = LoadAndAddMenuItem( pContextMenuCallback,
|
|
strMenuItem,
|
|
IDM_FILTER_DATABASE,
|
|
CCM_INSERTIONPOINTID_PRIMARY_VIEW,
|
|
lFlags);
|
|
ASSERT( SUCCEEDED(hr) );
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::Command
|
|
Handles commands for the current view
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::Command
|
|
(
|
|
ITFSComponent * pComponent,
|
|
MMC_COOKIE cookie,
|
|
int nCommandID,
|
|
LPDATAOBJECT pDataObject
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = S_OK;
|
|
SPITFSNode spNode;
|
|
|
|
CORg (m_spNodeMgr->FindNode(cookie, &spNode));
|
|
|
|
switch (nCommandID)
|
|
{
|
|
case IDM_FILTER_DATABASE:
|
|
if (m_fDbLoaded)
|
|
{
|
|
UpdateCurrentView(spNode);
|
|
}
|
|
else
|
|
{
|
|
OnDatabaseLoadStart(spNode);
|
|
}
|
|
break;
|
|
|
|
// this may have come from the scope pane handler, so pass it up
|
|
default:
|
|
hr = HandleScopeCommand(cookie, nCommandID, pDataObject);
|
|
break;
|
|
}
|
|
|
|
Error:
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::HasPropertyPages
|
|
Implementation of ITFSNodeHandler::HasPropertyPages
|
|
NOTE: the root node handler has to over-ride this function to
|
|
handle the snapin manager property page (wizard) case!!!
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::HasPropertyPages
|
|
(
|
|
ITFSNode * pNode,
|
|
LPDATAOBJECT pDataObject,
|
|
DATA_OBJECT_TYPES type,
|
|
DWORD dwType
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
if (dwType & TFS_COMPDATA_CREATE)
|
|
{
|
|
// This is the case where we are asked to bring up property
|
|
// pages when the user is adding a new snapin. These calls
|
|
// are forwarded to the root node to handle.
|
|
hr = hrFalse;
|
|
}
|
|
else
|
|
{
|
|
// we have property pages in the normal case
|
|
hr = hrOK;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CreatePropertyPages
|
|
The active registrations node (scope pane) doesn't have
|
|
any property pages. We should never get here.
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::CreatePropertyPages
|
|
(
|
|
ITFSNode * pNode,
|
|
LPPROPERTYSHEETCALLBACK lpProvider,
|
|
LPDATAOBJECT pDataObject,
|
|
LONG_PTR handle,
|
|
DWORD dwType
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
// we use this to create static mappings, but we don't show it
|
|
// through the properties verb. We invoke this mechanism when the
|
|
// user selects create static mapping
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
// Object gets deleted when the page is destroyed
|
|
SPIComponentData spComponentData;
|
|
m_spNodeMgr->GetComponentData(&spComponentData);
|
|
|
|
// show the same page as the statis mapping properties
|
|
CStaticMappingProperties * pMapping =
|
|
new CStaticMappingProperties (pNode,
|
|
spComponentData,
|
|
NULL,
|
|
NULL,
|
|
TRUE);
|
|
|
|
pMapping->m_ppageGeneral->m_uImage = ICON_IDX_CLIENT;
|
|
|
|
pMapping->CreateModelessSheet(lpProvider, handle);
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::HasPropertyPages
|
|
Implementation of ITFSResultHandler::HasPropertyPages
|
|
Author: KennT
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::HasPropertyPages
|
|
(
|
|
ITFSComponent * pComponent,
|
|
MMC_COOKIE cookie,
|
|
LPDATAOBJECT pDataObject
|
|
)
|
|
{
|
|
return hrOK;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CreatePropertyPages
|
|
Implementation of ITFSResultHandler::CreatePropertyPages
|
|
Author: KennT
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::CreatePropertyPages
|
|
(
|
|
ITFSComponent * pComponent,
|
|
MMC_COOKIE cookie,
|
|
LPPROPERTYSHEETCALLBACK lpProvider,
|
|
LPDATAOBJECT pDataObject,
|
|
LONG_PTR handle
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
HPROPSHEETPAGE hPage;
|
|
SPINTERNAL spInternal;
|
|
SPIComponentData spComponentData;
|
|
SPIComponent spComponent;
|
|
SPITFSNode spNode;
|
|
SPIResultData spResultData;
|
|
int nIndex ;
|
|
HROW hRowSel;
|
|
WinsRecord wRecord;
|
|
WinsStrRecord *pwstrRecord;
|
|
int nCount;
|
|
|
|
// get the resultdata interface
|
|
CORg (pComponent->GetResultData(&spResultData));
|
|
|
|
spInternal = ExtractInternalFormat(pDataObject);
|
|
|
|
// virtual listbox notifications come to the handler of the node
|
|
// that is selected. check to see if this notification is for a
|
|
// virtual listbox item or the active registrations node itself.
|
|
|
|
if (spInternal->HasVirtualIndex())
|
|
{
|
|
// we gotta do special stuff for the virtual index items
|
|
m_spNodeMgr->FindNode(cookie, &spNode);
|
|
|
|
CORg(spComponent.HrQuery(pComponent));
|
|
Assert(spComponent);
|
|
|
|
m_nSelectedIndex = spInternal->GetVirtualIndex();
|
|
nIndex = m_nSelectedIndex;
|
|
|
|
// if an invalid index, return
|
|
m_pCurrentDatabase->GetCurrentCount(&nCount);
|
|
|
|
if (nIndex < 0 || nIndex >= nCount)
|
|
{
|
|
return hrOK;
|
|
}
|
|
|
|
// get the correct data for the record selected
|
|
m_spWinsDatabase->GetHRow(nIndex, &hRowSel);
|
|
m_spWinsDatabase->GetData(hRowSel, &wRecord);
|
|
|
|
GetRecordOwner(spNode, &wRecord);
|
|
|
|
// put up different page depending on wheter static or dynamic
|
|
if (wRecord.dwState & WINSDB_REC_STATIC)
|
|
{
|
|
m_CurrentRecord = wRecord;
|
|
|
|
CStaticMappingProperties * pStat =
|
|
new CStaticMappingProperties(spNode,
|
|
spComponent,
|
|
NULL,
|
|
&wRecord,
|
|
FALSE);
|
|
pStat->m_ppageGeneral->m_uImage = GetVirtualImage(nIndex);
|
|
|
|
Assert(lpProvider != NULL);
|
|
|
|
return pStat->CreateModelessSheet(lpProvider, handle);
|
|
}
|
|
// dynamic case
|
|
else
|
|
{
|
|
CDynamicMappingProperties *pDyn =
|
|
new CDynamicMappingProperties(spNode,
|
|
spComponent,
|
|
NULL,
|
|
&wRecord);
|
|
|
|
pDyn->m_pageGeneral.m_uImage = GetVirtualImage(nIndex);
|
|
Assert(lpProvider != NULL);
|
|
|
|
return pDyn->CreateModelessSheet(lpProvider, handle);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
Assert(FALSE);
|
|
}
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnPropertyChange
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnPropertyChange
|
|
(
|
|
ITFSNode * pNode,
|
|
LPDATAOBJECT pDataobject,
|
|
DWORD dwType,
|
|
LPARAM arg,
|
|
LPARAM lParam
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
CStaticMappingProperties * pProp =
|
|
reinterpret_cast<CStaticMappingProperties *>(lParam);
|
|
|
|
LONG_PTR changeMask = 0;
|
|
|
|
// tell the property page to do whatever now that we are back on the
|
|
// main thread
|
|
pProp->OnPropertyChange(TRUE, &changeMask);
|
|
pProp->AcknowledgeNotify();
|
|
|
|
// refresh the result pane
|
|
if (changeMask)
|
|
UpdateListboxCount(pNode);
|
|
|
|
return hrOK;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnResultPropertyChange
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnResultPropertyChange
|
|
(
|
|
ITFSComponent * pComponent,
|
|
LPDATAOBJECT pDataObject,
|
|
MMC_COOKIE cookie,
|
|
LPARAM arg,
|
|
LPARAM param
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
SPINTERNAL spInternal;
|
|
SPITFSNode spNode;
|
|
|
|
m_spNodeMgr->FindNode(cookie, &spNode);
|
|
|
|
CStaticMappingProperties * pProp = reinterpret_cast<CStaticMappingProperties *>(param);
|
|
|
|
LONG_PTR changeMask = 0;
|
|
|
|
// tell the property page to do whatever now that we are back on the
|
|
// main thread
|
|
pProp->SetComponent(pComponent);
|
|
pProp->OnPropertyChange(TRUE, &changeMask);
|
|
pProp->AcknowledgeNotify();
|
|
|
|
// refresh the result pane
|
|
if (changeMask)
|
|
UpdateListboxCount(spNode);
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnResultDelete
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnResultDelete
|
|
(
|
|
ITFSComponent * pComponent,
|
|
LPDATAOBJECT pDataObject,
|
|
MMC_COOKIE cookie,
|
|
LPARAM arg,
|
|
LPARAM lParam
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
Trace0("CActiveRegistrationsHandler::OnResultDelete received\n");
|
|
|
|
SPINTERNAL spInternal;
|
|
|
|
spInternal = ExtractInternalFormat(pDataObject);
|
|
|
|
// virtual listbox notifications come to the handler of the node
|
|
// that is selected. check to see if this notification is for a
|
|
// virtual listbox item or the active registrations node itself.
|
|
if (spInternal->HasVirtualIndex())
|
|
{
|
|
// we gotta do special stuff for the virtual index items
|
|
DeleteRegistration(pComponent, spInternal->GetVirtualIndex());
|
|
}
|
|
else
|
|
{
|
|
// just call the base class to update verbs for the
|
|
CMTWinsHandler::OnResultDelete(pComponent,
|
|
pDataObject,
|
|
cookie,
|
|
arg,
|
|
lParam);
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnResultSelect
|
|
Handles the MMCN_SELECT notifcation
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnResultSelect
|
|
(
|
|
ITFSComponent * pComponent,
|
|
LPDATAOBJECT pDataObject,
|
|
MMC_COOKIE cookie,
|
|
LPARAM arg,
|
|
LPARAM lParam
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
int i;
|
|
WINSDB_STATE uState = WINSDB_LOADING;
|
|
SPINTERNAL spInternal;
|
|
SPIConsoleVerb spConsoleVerb;
|
|
SPIConsole spConsole;
|
|
BOOL bStates[ARRAYLEN(g_ConsoleVerbs)];
|
|
SPITFSNode spNode;
|
|
|
|
// show the result pane message
|
|
if (!m_fLoadedOnce)
|
|
{
|
|
CString strTitle, strBody, strTemp;
|
|
|
|
m_spResultNodeMgr->FindNode(cookie, &spNode);
|
|
|
|
strTitle.LoadString(IDS_ACTREG_MESSAGE_TITLE);
|
|
|
|
for (i = 0; ; i++)
|
|
{
|
|
if (guActregMessageStrings[i] == -1)
|
|
break;
|
|
|
|
strTemp.LoadString(guActregMessageStrings[i]);
|
|
strBody += strTemp;
|
|
}
|
|
|
|
ShowMessage(spNode, strTitle, strBody, Icon_Information);
|
|
}
|
|
else
|
|
{
|
|
ULARGE_INTEGER data, *pData;
|
|
|
|
// fill in the result pane
|
|
if (m_spWinsDatabase)
|
|
{
|
|
m_spWinsDatabase->GetCurrentState(&uState);
|
|
|
|
// check to see if we are done
|
|
if (m_winsdbState == WINSDB_LOADING &&
|
|
uState != WINSDB_LOADING)
|
|
{
|
|
Trace0("ActiveRegHandler::OnResultSelect - Done loading DB\n");
|
|
|
|
DatabaseLoadingCleanup();
|
|
}
|
|
}
|
|
|
|
if (m_pCurrentDatabase)
|
|
{
|
|
// Get the count from the database
|
|
CORg (m_pCurrentDatabase->GetCurrentScanned((int*)&data.LowPart));
|
|
CORg (m_pCurrentDatabase->GetCurrentCount((int*)&data.HighPart));
|
|
pData = &data;
|
|
}
|
|
else
|
|
{
|
|
pData = NULL;
|
|
}
|
|
|
|
// now notify the virtual listbox
|
|
CORg ( m_spNodeMgr->GetConsole(&spConsole) );
|
|
CORg ( spConsole->UpdateAllViews(pDataObject,
|
|
(LPARAM)pData,
|
|
RESULT_PANE_SET_VIRTUAL_LB_SIZE) );
|
|
}
|
|
|
|
// now update the verbs...
|
|
spInternal = ExtractInternalFormat(pDataObject);
|
|
Assert(spInternal);
|
|
|
|
// virtual listbox notifications come to the handler of the node
|
|
// that is selected.check to see if this notification is for a
|
|
// virtual listbox item or the active registrations node itself.
|
|
if (spInternal->HasVirtualIndex())
|
|
{
|
|
// is this a multiselect?
|
|
BOOL fMultiSelect = spInternal->m_cookie == MMC_MULTI_SELECT_COOKIE ? TRUE : FALSE;
|
|
|
|
if (!fMultiSelect)
|
|
{
|
|
// when something is selected in the result pane we want the default verb to be properties
|
|
m_verbDefault = MMC_VERB_PROPERTIES;
|
|
}
|
|
else
|
|
{
|
|
// we don't support multi-select properties
|
|
m_verbDefault = MMC_VERB_NONE;
|
|
}
|
|
|
|
// we gotta do special stuff for the virtual index items
|
|
CORg (pComponent->GetConsoleVerb(&spConsoleVerb));
|
|
|
|
UpdateConsoleVerbs(spConsoleVerb, WINSSNAP_REGISTRATION, fMultiSelect);
|
|
}
|
|
else
|
|
{
|
|
// when the active registrations node itself is selected, default should be open
|
|
m_verbDefault = MMC_VERB_OPEN;
|
|
|
|
g_ConsoleVerbStates[WINSSNAP_ACTIVE_REGISTRATIONS][6] = ENABLED;
|
|
|
|
// just call the base class to update verbs for the
|
|
CMTWinsHandler::OnResultSelect(pComponent,
|
|
pDataObject,
|
|
cookie,
|
|
arg,
|
|
lParam);
|
|
}
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::DatabaseLoadingCleanup
|
|
Description
|
|
Author: ericdav
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::DatabaseLoadingCleanup()
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
m_winsdbState = WINSDB_NORMAL;
|
|
|
|
// check for any errors
|
|
HRESULT hrLastError;
|
|
m_spWinsDatabase->GetLastError(&hrLastError);
|
|
|
|
// Kill the timer thread
|
|
if (m_spQuery)
|
|
{
|
|
// Signal the thread to abort
|
|
m_spQuery->SetAbortEvent();
|
|
}
|
|
|
|
if (FAILED(hrLastError))
|
|
{
|
|
CString strError, strIp;
|
|
|
|
LPTSTR pBuf = strIp.GetBuffer(256);
|
|
m_spWinsDatabase->GetIP(pBuf, 256);
|
|
|
|
strIp.ReleaseBuffer();
|
|
|
|
AfxFormatString1(strError, IDS_ERR_LOADING_DB, strIp);
|
|
theApp.MessageBox(strError, WIN32_FROM_HRESULT(hrLastError));
|
|
|
|
m_fForceReload = TRUE;
|
|
}
|
|
|
|
WaitForThreadToExit();
|
|
}
|
|
|
|
|
|
void
|
|
CActiveRegistrationsHandler::FilterCleanup(ITFSNode *pNode)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
m_winsdbState = WINSDB_NORMAL;
|
|
|
|
// check for any errors
|
|
HRESULT hrLastError;
|
|
m_spWinsDatabase->GetLastError(&hrLastError);
|
|
|
|
// Kill the timer thread
|
|
if (m_spQuery)
|
|
{
|
|
// Signal the thread to abort
|
|
m_spQuery->SetAbortEvent();
|
|
}
|
|
|
|
if (FAILED(hrLastError))
|
|
{
|
|
CString strError, strIp;
|
|
|
|
LPTSTR pBuf = strIp.GetBuffer(256);
|
|
m_spWinsDatabase->GetIP(pBuf, 256);
|
|
|
|
strIp.ReleaseBuffer();
|
|
|
|
AfxFormatString1(strError, IDS_ERR_LOADING_DB, strIp);
|
|
theApp.MessageBox(strError, WIN32_FROM_HRESULT(hrLastError));
|
|
|
|
m_fForceReload = TRUE;
|
|
}
|
|
|
|
WaitForThreadToExit();
|
|
|
|
// change the icon to normal
|
|
pNode->SetData(TFS_DATA_IMAGEINDEX, GetImageIndex(FALSE));
|
|
pNode->SetData(TFS_DATA_OPENIMAGEINDEX, GetImageIndex(TRUE));
|
|
|
|
pNode->ChangeNode(SCOPE_PANE_CHANGE_ITEM);
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::UpdateListboxCount
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::UpdateListboxCount(ITFSNode * pNode, BOOL bClear)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
SPIComponentData spCompData;
|
|
SPIConsole spConsole;
|
|
IDataObject* pDataObject;
|
|
LONG_PTR hint;
|
|
// need to pass up two counter values:one is the total number of records scanned
|
|
// the other is the total number of records filtered. I put these two in a 64 bit
|
|
// value: the most significant 32bits is the number of records actually filtered
|
|
// the less significant 32bits is the total number of records scanned.
|
|
ULARGE_INTEGER data;
|
|
ULARGE_INTEGER *pData;
|
|
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
if (!m_pCurrentDatabase)
|
|
{
|
|
pData = NULL;
|
|
hint = RESULT_PANE_CLEAR_VIRTUAL_LB;
|
|
}
|
|
else
|
|
{
|
|
CORg (m_pCurrentDatabase->GetCurrentScanned((int*)&data.LowPart));
|
|
CORg (m_pCurrentDatabase->GetCurrentCount((int*)&data.HighPart));
|
|
hint = RESULT_PANE_SET_VIRTUAL_LB_SIZE;
|
|
pData = &data;
|
|
}
|
|
|
|
m_spNodeMgr->GetComponentData(&spCompData);
|
|
|
|
CORg ( spCompData->QueryDataObject((MMC_COOKIE) pNode,
|
|
CCT_RESULT,
|
|
&pDataObject) );
|
|
|
|
CORg ( m_spNodeMgr->GetConsole(&spConsole) );
|
|
|
|
CORg ( spConsole->UpdateAllViews(pDataObject,
|
|
(LPARAM)pData,
|
|
hint) );
|
|
|
|
pDataObject->Release();
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::UpdateVerbs
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::UpdateVerbs(ITFSNode * pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
LONG_PTR hint;
|
|
int i;
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
g_ConsoleVerbStates[WINSSNAP_ACTIVE_REGISTRATIONS][6] = ENABLED;
|
|
|
|
if (!pNode)
|
|
{
|
|
hint = WINSSNAP_REGISTRATION;
|
|
}
|
|
else
|
|
{
|
|
hint = WINSSNAP_ACTIVE_REGISTRATIONS;
|
|
}
|
|
|
|
|
|
UpdateStandardVerbs(pNode, hint);
|
|
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
Command handlers
|
|
---------------------------------------------------------------------------*/
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetServerIP
|
|
Description
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::GetServerIP(ITFSNode * pNode,
|
|
DWORD &dwIP,
|
|
CString &strIP)
|
|
{
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
dwIP = pServer->GetServerIP();
|
|
|
|
::MakeIPAddress(dwIP, strIP);
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnCreateMapping
|
|
Description
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnCreateMapping(ITFSNode *pNode)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
// Object gets deleted when the page is destroyed
|
|
SPIComponentData spComponentData;
|
|
m_spNodeMgr->GetComponentData(&spComponentData);
|
|
|
|
// HACK WARNING: because we do this in a MMC provided property sheet, we
|
|
// need to invoke the correct mechanism so we get a callback handle.
|
|
// otherwise when we create the static mapping, we're on another thread
|
|
// and it can do bad things when we try to update the UI
|
|
hr = DoPropertiesOurselvesSinceMMCSucks(pNode, spComponentData, _T(""));
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnDatabaseLoadStart
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnDatabaseLoadStart(ITFSNode *pNode)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
SPITFSNode spNode;
|
|
SPITFSNodeHandler spHandler;
|
|
ITFSQueryObject * pQuery = NULL;
|
|
SPITFSNode spServerNode;
|
|
DWORD dwIP;
|
|
CString strIP;
|
|
BOOL fReload = FALSE;
|
|
int nCount, pos;
|
|
CTypeFilterInfo typeFilterInfo;
|
|
|
|
pNode->GetParent(&spServerNode);
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
dwIP = pServer->GetServerIP();
|
|
|
|
if (!m_bExpanded)
|
|
{
|
|
m_dlgLoadRecords.ResetFiltering();
|
|
}
|
|
|
|
if (m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter.GetSize() == 0)
|
|
{
|
|
fReload = TRUE;
|
|
|
|
// initialize the record type filter array
|
|
for (nCount = 0; nCount < m_NameTypeMap.GetSize(); nCount++)
|
|
{
|
|
if (m_NameTypeMap[nCount].dwWinsType == -1)
|
|
{
|
|
typeFilterInfo.dwType = m_NameTypeMap[nCount].dwNameType;
|
|
typeFilterInfo.fShow = TRUE;
|
|
m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter.Add(typeFilterInfo);
|
|
}
|
|
}
|
|
}
|
|
|
|
// if a download is running, ask the user if they want to stop it
|
|
if (m_winsdbState != WINSDB_NORMAL)
|
|
{
|
|
OnDatabaseLoadStop(pNode);
|
|
}
|
|
|
|
// bring up the Owner Dialog
|
|
// fill in the owner page info
|
|
GetOwnerInfo(m_dlgLoadRecords.m_pageOwners.m_ServerInfoArray);
|
|
// fill in the type filter page info
|
|
m_dlgLoadRecords.m_pageTypes.m_pNameTypeMap = &m_NameTypeMap;
|
|
// save the original number of owners. In case this is one
|
|
// and several other are added, will reload the database.
|
|
|
|
//------------------Display popup ----------------------------
|
|
if (m_dlgLoadRecords.DoModal() != IDOK)
|
|
return hrFalse;
|
|
|
|
SetLoadedOnce(pNode);
|
|
m_fDbLoaded = TRUE;
|
|
|
|
Lock();
|
|
|
|
MakeIPAddress(dwIP, strIP);
|
|
|
|
// stop the database if we were loading or create one if we haven't yet
|
|
if (!m_spWinsDatabase)
|
|
{
|
|
CORg (CreateWinsDatabase(strIP, strIP, &m_spWinsDatabase));
|
|
fReload = TRUE;
|
|
}
|
|
else
|
|
{
|
|
CORg (m_spWinsDatabase->Stop());
|
|
}
|
|
|
|
//~~~~~~~~~~~~~~~~~~~~~~~~~ need to revise the logic for reloading ~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
//
|
|
// we try to make the decision whether the records we already loaded (if we did) are sufficient
|
|
// to apply the new filters: set fReload to TRUE if reload is needed or to FALSE otherwise.
|
|
// Since fReload could have been already set go into this process only if reloading is not yet
|
|
// decided. Assume reload will eventualy be decided and break out as soon as this is confirmed
|
|
// If the end of the "while" block is reached, this means database doesn't need to be reloaded
|
|
// so break out.
|
|
while(!fReload)
|
|
{
|
|
BOOL bDbCacheEnabled;
|
|
// assume a reload will be needed
|
|
fReload = TRUE;
|
|
// if reload imposed by external causes (first time call or refresh was done), break out
|
|
if (m_fForceReload)
|
|
break;
|
|
|
|
m_spWinsDatabase->GetCachingFlag(&bDbCacheEnabled);
|
|
|
|
if (bDbCacheEnabled)
|
|
{
|
|
BOOL bReload;
|
|
|
|
// currently the database is loaded with "enable caching" checked. This means:
|
|
// if db "owner" api setting is set (non 0xffffffff) then
|
|
// all records owned by "owner" are loaded (case 1)
|
|
// else --> "owner" is set to "multiple" (0xffffffff)
|
|
// if db "name" api is set (non null) then
|
|
// all records prefixed with "name" are loaded (case 2)
|
|
// else
|
|
// entire database is loaded (case 3)
|
|
// .
|
|
// .
|
|
// if (case 1) applies then
|
|
// if we want to filter on a different or no owner then
|
|
// reload SUGGESTED
|
|
// else
|
|
// reload NOT SUGGESTED
|
|
// .
|
|
// else if (case 2) applies then
|
|
// if we want to filter on a different or no name prefix then
|
|
// reload SUGGESTED
|
|
// else
|
|
// reload NOT SUGGESTED
|
|
// .
|
|
// else if (case 3) applies)
|
|
// reload NOT SUGGESTED
|
|
// .
|
|
//
|
|
// This logic is followed in CheckApiInfoCovered call from below
|
|
m_spWinsDatabase->ReloadSuggested(
|
|
m_dlgLoadRecords.m_pageOwners.GetOwnerForApi(),
|
|
m_dlgLoadRecords.m_pageIpAddress.GetNameForApi(),
|
|
&bReload);
|
|
|
|
if (bReload)
|
|
break;
|
|
}
|
|
else
|
|
{
|
|
// currently the database is loaded without "enable caching" checked. This means:
|
|
// the records currentLy in the database match all the filters as they were specified
|
|
// in the filtering dialog before it was popped-up. Consequently, if any of these
|
|
// filters (owner, name, ipaddr, type) changed, database has to be reloaded. Otherwise,
|
|
// since the filters are the same.
|
|
if (m_dlgLoadRecords.m_pageIpAddress.m_bDirtyName ||
|
|
m_dlgLoadRecords.m_pageIpAddress.m_bDirtyAddr ||
|
|
m_dlgLoadRecords.m_pageIpAddress.m_bDirtyMask ||
|
|
m_dlgLoadRecords.m_pageOwners.m_bDirtyOwners ||
|
|
m_dlgLoadRecords.m_pageTypes.m_bDirtyTypes)
|
|
break;
|
|
}
|
|
|
|
// if we are here it means reload is not actually needed, so reset the flag back and
|
|
// break the loop
|
|
fReload = FALSE;
|
|
break;
|
|
};
|
|
|
|
// if the final decision is to reload the db, then prepare this operation
|
|
if (fReload)
|
|
{
|
|
m_fForceReload = FALSE;
|
|
m_spWinsDatabase->Clear();
|
|
// set the Api parameters to be used by the database
|
|
m_spWinsDatabase->SetApiInfo(
|
|
m_dlgLoadRecords.m_pageOwners.GetOwnerForApi(),
|
|
m_dlgLoadRecords.m_pageIpAddress.GetNameForApi(),
|
|
m_dlgLoadRecords.m_bEnableCache);
|
|
}
|
|
//
|
|
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
UpdateCurrentView(pNode);
|
|
|
|
// start loading records if necessary
|
|
if (fReload)
|
|
{
|
|
// start loading records
|
|
CORg (m_spWinsDatabase->Init());
|
|
|
|
// update our internal state
|
|
m_winsdbState = WINSDB_LOADING;
|
|
|
|
// update the node's icon
|
|
OnChangeState(pNode);
|
|
|
|
// kick off the background thread to do the timer updates
|
|
pQuery = OnCreateQuery(pNode);
|
|
Assert(pQuery);
|
|
|
|
Verify(StartBackgroundThread(pNode,
|
|
m_spTFSCompData->GetHiddenWnd(),
|
|
pQuery));
|
|
|
|
pQuery->Release();
|
|
}
|
|
|
|
// fill in any record type filter information
|
|
nCount = (int)m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter.GetSize();
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_TYPE);
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_TYPE,
|
|
m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter[pos].dwType,
|
|
m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter[pos].fShow,
|
|
NULL);
|
|
}
|
|
|
|
// fill in any owner filter information
|
|
nCount = (int)m_dlgLoadRecords.m_pageOwners.m_dwaOwnerFilter.GetSize();
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_OWNER);
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_OWNER,
|
|
m_dlgLoadRecords.m_pageOwners.m_dwaOwnerFilter[pos],
|
|
0,
|
|
NULL);
|
|
}
|
|
|
|
// fill in any ip address filter information
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_IPADDR);
|
|
if (m_dlgLoadRecords.m_pageIpAddress.m_bFilterIpAddr)
|
|
{
|
|
nCount = (int)m_dlgLoadRecords.m_pageIpAddress.m_dwaIPAddrs.GetSize();
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_IPADDR,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_dwaIPAddrs[pos],
|
|
m_dlgLoadRecords.m_pageIpAddress.GetIPMaskForFilter(pos),
|
|
NULL);
|
|
}
|
|
}
|
|
|
|
// fill in any name filter information
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_NAME);
|
|
if (m_dlgLoadRecords.m_pageIpAddress.m_bFilterName)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_NAME,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_bMatchCase,
|
|
0,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_strName);
|
|
}
|
|
|
|
// now that the filters are all set database can start downloading
|
|
if (fReload)
|
|
// start loading records
|
|
CORg (m_spWinsDatabase->Start());
|
|
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
Sleep(100);
|
|
|
|
// filter any records that may have been downloaded before we set the
|
|
// filter information (in the case when we had to reload the database).
|
|
// any records that come in after we set the
|
|
// filter info will be filtered correctly.
|
|
m_spWinsDatabase->FilterRecords(WINSDB_FILTER_BY_TYPE, 0,0);
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
if (fReload)
|
|
{
|
|
// do the initial update of the virutal listbox
|
|
OnHaveData(pNode, 0, QDATA_TIMER);
|
|
}
|
|
else
|
|
{
|
|
// just a filter changed, just need to update the result pane
|
|
UpdateListboxCount(pNode);
|
|
}
|
|
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnDatabaseLoadStop
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnDatabaseLoadStop(ITFSNode *pNode)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
if (IDYES != AfxMessageBox(IDS_STOP_DB_LOAD_CONFIRM, MB_YESNO))
|
|
{
|
|
return hrFalse;
|
|
}
|
|
|
|
if (m_spWinsDatabase)
|
|
{
|
|
CORg (m_spWinsDatabase->Stop());
|
|
|
|
DatabaseLoadingCleanup();
|
|
UpdateListboxCount(pNode);
|
|
}
|
|
|
|
m_fForceReload = TRUE;
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnGetResultViewType
|
|
Description
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnGetResultViewType
|
|
(
|
|
ITFSComponent * pComponent,
|
|
MMC_COOKIE cookie,
|
|
LPOLESTR * ppViewType,
|
|
long * pViewOptions
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = S_FALSE;
|
|
|
|
if (cookie != NULL)
|
|
{
|
|
// call the base class to see if it is handling this
|
|
if (CMTWinsHandler::OnGetResultViewType(pComponent, cookie, ppViewType, pViewOptions) != S_OK)
|
|
{
|
|
*pViewOptions = MMC_VIEW_OPTIONS_OWNERDATALIST |
|
|
MMC_VIEW_OPTIONS_MULTISELECT;
|
|
|
|
hr = S_FALSE;
|
|
}
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetVirtualImage
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
int
|
|
CActiveRegistrationsHandler::GetVirtualImage
|
|
(
|
|
int nIndex
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
WinsRecord ws;
|
|
HROW hrow;
|
|
int nImage = ICON_IDX_CLIENT;
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
if (!m_pCurrentDatabase)
|
|
return -1;
|
|
|
|
CORg (m_pCurrentDatabase->GetHRow(nIndex, &hrow));
|
|
CORg (m_pCurrentDatabase->GetData(hrow, &ws));
|
|
|
|
if (HIWORD(ws.dwType) != WINSINTF_E_UNIQUE)
|
|
{
|
|
nImage = ICON_IDX_CLIENT_GROUP;
|
|
}
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
return nImage;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetVirtualString
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
LPCWSTR
|
|
CActiveRegistrationsHandler::GetVirtualString
|
|
(
|
|
int nIndex,
|
|
int nCol
|
|
)
|
|
{
|
|
HRESULT hr;
|
|
int nCount;
|
|
|
|
if (m_pCurrentDatabase)
|
|
{
|
|
// check if nIndex is within limits, if not crashes when the last
|
|
// record deleted and properties chosen.
|
|
m_pCurrentDatabase->GetCurrentCount(&nCount);
|
|
|
|
// 0 based index
|
|
if (nIndex < 0 || nIndex >= nCount)
|
|
{
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
// check our cache to see if we have this one.
|
|
WinsStrRecord * pwsr = m_RecList.FindItem(nIndex);
|
|
if (pwsr == NULL)
|
|
{
|
|
Trace1("ActRegHandler::GetVirtualString - Index %d not in string cache\n", nIndex);
|
|
|
|
// doesn't exist in our cache, need to add this one.
|
|
pwsr = BuildWinsStrRecord(nIndex);
|
|
if (pwsr)
|
|
m_RecList.AddTail(pwsr);
|
|
}
|
|
|
|
if (pwsr)
|
|
{
|
|
switch (nCol)
|
|
{
|
|
case ACTREG_COL_NAME:
|
|
return pwsr->strName;
|
|
break;
|
|
|
|
case ACTREG_COL_TYPE:
|
|
return pwsr->strType;
|
|
break;
|
|
|
|
case ACTREG_COL_IPADDRESS:
|
|
return pwsr->strIPAdd;
|
|
break;
|
|
|
|
case ACTREG_COL_STATE:
|
|
return pwsr->strActive;
|
|
break;
|
|
|
|
case ACTREG_COL_STATIC:
|
|
return pwsr->strStatic;
|
|
break;
|
|
|
|
case ACTREG_COL_OWNER:
|
|
return pwsr->strOwner;
|
|
break;
|
|
|
|
case ACTREG_COL_VERSION:
|
|
return pwsr->strVersion;
|
|
break;
|
|
|
|
case ACTREG_COL_EXPIRATION:
|
|
return pwsr->strExpiration;
|
|
break;
|
|
|
|
default:
|
|
Panic0("ActRegHandler::GetVirtualString - Unknown column!\n");
|
|
break;
|
|
}
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::BuildWinsStrRecord
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
WinsStrRecord *
|
|
CActiveRegistrationsHandler::BuildWinsStrRecord(int nIndex)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
int nCount;
|
|
HRESULT hr = hrOK;
|
|
WinsStrRecord * pwsr = NULL;
|
|
WinsRecord ws;
|
|
HROW hrow;
|
|
CString strTemp;
|
|
|
|
if (!m_pCurrentDatabase)
|
|
{
|
|
return NULL;
|
|
}
|
|
|
|
if (FAILED(m_pCurrentDatabase->GetHRow(nIndex, &hrow)))
|
|
return NULL;
|
|
|
|
if (FAILED(m_pCurrentDatabase->GetData(hrow, &ws)))
|
|
return NULL;
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
pwsr = new WinsStrRecord;
|
|
|
|
// set the index for this record
|
|
pwsr->nIndex = nIndex;
|
|
|
|
// build the name string
|
|
CleanNetBIOSName(ws.szRecordName,
|
|
pwsr->strName,
|
|
TRUE, // Expand
|
|
TRUE, // Truncate
|
|
IsLanManCompatible(),
|
|
TRUE, // name is OEM
|
|
FALSE, // No double backslash
|
|
ws.dwNameLen);
|
|
|
|
// now the type
|
|
CString strValue;
|
|
strValue.Format(_T("[%02Xh] "),
|
|
((int) ws.szRecordName[15] & 0x000000FF));
|
|
|
|
CString strName;
|
|
DWORD dwNameType = (0x000000FF & ws.szRecordName[15]);
|
|
|
|
m_NameTypeMap.TypeToCString(dwNameType, MAKELONG(HIWORD(ws.dwType), 0), strName);
|
|
|
|
pwsr->strType = strValue + strName;
|
|
|
|
// IP address
|
|
// Gets changed in the case of static records of the type Special Group,
|
|
// where the first IP address in the list of IP addresses is of the Owner
|
|
if ( (ws.dwState & WINSDB_REC_UNIQUE) ||
|
|
(ws.dwState & WINSDB_REC_NORM_GROUP) )
|
|
{
|
|
MakeIPAddress(ws.dwIpAdd[0], pwsr->strIPAdd);
|
|
}
|
|
else
|
|
{
|
|
if (ws.dwNoOfAddrs > 0)
|
|
{
|
|
if (ws.dwIpAdd[1] == 0)
|
|
{
|
|
pwsr->strIPAdd.Empty();
|
|
}
|
|
else
|
|
{
|
|
MakeIPAddress(ws.dwIpAdd[1], pwsr->strIPAdd);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
pwsr->strIPAdd.Empty();
|
|
}
|
|
}
|
|
|
|
// active status
|
|
GetStateString(ws.dwState, pwsr->strActive);
|
|
|
|
// static flag
|
|
if (ws.dwState & WINSDB_REC_STATIC)
|
|
{
|
|
pwsr->strStatic = _T("x");
|
|
}
|
|
else
|
|
{
|
|
pwsr->strStatic = _T("");
|
|
}
|
|
|
|
// expiration time
|
|
if (ws.dwExpiration == INFINITE_EXPIRATION)
|
|
{
|
|
Verify(pwsr->strExpiration.LoadString(IDS_INFINITE));
|
|
}
|
|
else
|
|
{
|
|
CTime time(ws.dwExpiration);
|
|
FormatDateTime(pwsr->strExpiration, time);
|
|
}
|
|
|
|
// version
|
|
GetVersionInfo(ws.liVersion.LowPart,
|
|
ws.liVersion.HighPart,
|
|
pwsr->strVersion);
|
|
|
|
// owner
|
|
if (m_Config.FSupportsOwnerId())
|
|
{
|
|
MakeIPAddress(ws.dwOwner, pwsr->strOwner);
|
|
}
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
return pwsr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetStateString
|
|
Description Returns the state of the record, Active, Tomstoned,
|
|
realeased or deleted
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void CActiveRegistrationsHandler::GetStateString(DWORD dwState,
|
|
CString& strState)
|
|
{
|
|
if (dwState & WINSDB_REC_ACTIVE )
|
|
{
|
|
strState.LoadString(IDS_RECORD_STATE_ACTIVE);
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_DELETED )
|
|
{
|
|
strState.LoadString(IDS_RECORD_STATE_DELETED);
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_RELEASED )
|
|
{
|
|
strState.LoadString(IDS_RECORD_STATE_RELEASED);
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_TOMBSTONE )
|
|
{
|
|
strState.LoadString(IDS_RECORD_STATE_TOMBSTONED);
|
|
}
|
|
else
|
|
{
|
|
strState.LoadString(IDS_RECORD_STATE_UNKNOWN);
|
|
}
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetStateString
|
|
Description Returns the static type for the record, Unique,
|
|
Multihomed, Inetrne Group, Normal Group, Multihomed
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void CActiveRegistrationsHandler::GetStaticTypeString(DWORD dwState,
|
|
CString& strStaticType)
|
|
{
|
|
if (dwState & WINSDB_REC_UNIQUE )
|
|
{
|
|
strStaticType = g_strStaticTypeUnique;
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_SPEC_GROUP )
|
|
{
|
|
strStaticType = g_strStaticTypeDomainName;
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_MULTIHOMED )
|
|
{
|
|
strStaticType = g_strStaticTypeMultihomed;
|
|
}
|
|
else
|
|
if (dwState & WINSDB_REC_NORM_GROUP )
|
|
{
|
|
strStaticType = g_strStaticTypeGroup;
|
|
}
|
|
else
|
|
{
|
|
strStaticType = g_strStaticTypeUnknown;
|
|
}
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetVersionInfo
|
|
Description Gives the version INfo as string in Hex Notation
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void CActiveRegistrationsHandler::GetVersionInfo(LONG lLowWord,
|
|
LONG lHighWord,
|
|
CString& strVersionCount)
|
|
{
|
|
strVersionCount.Empty();
|
|
|
|
TCHAR sz[20];
|
|
TCHAR *pch = sz;
|
|
::wsprintf(sz, _T("%08lX%08lX"), lHighWord, lLowWord);
|
|
// Kill leading zero's
|
|
while (*pch == '0')
|
|
{
|
|
++pch;
|
|
}
|
|
// At least one digit...
|
|
if (*pch == '\0')
|
|
{
|
|
--pch;
|
|
}
|
|
|
|
strVersionCount = pch;
|
|
}
|
|
|
|
BOOL
|
|
CActiveRegistrationsHandler::IsLanManCompatible()
|
|
{
|
|
BOOL fCompatible = TRUE;
|
|
|
|
if (m_spServerNode)
|
|
{
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, m_spServerNode);
|
|
|
|
fCompatible = (pServer->m_dwFlags & FLAG_LANMAN_COMPATIBLE) ? TRUE : FALSE;
|
|
}
|
|
|
|
return fCompatible;
|
|
}
|
|
|
|
//
|
|
// Convert the netbios name to a displayable format, with
|
|
// beginning slashes, the unprintable characters converted
|
|
// to '-' characters, and the 16th character displayed in brackets.
|
|
// Convert the string to ANSI/Unicode before displaying it.
|
|
//
|
|
//
|
|
void
|
|
CActiveRegistrationsHandler::CleanNetBIOSName
|
|
(
|
|
LPCSTR lpszSrc,
|
|
CString & strDest,
|
|
BOOL fExpandChars,
|
|
BOOL fTruncate,
|
|
BOOL fLanmanCompatible,
|
|
BOOL fOemName,
|
|
BOOL fWackwack,
|
|
int nLength
|
|
)
|
|
{
|
|
static CHAR szWacks[] = "\\\\";
|
|
BYTE ch16 = 0;
|
|
|
|
if (!lpszSrc ||
|
|
(strcmp(lpszSrc, "") == 0) )
|
|
{
|
|
strDest = _T("---------");
|
|
return;
|
|
}
|
|
|
|
int nLen, nDisplayLen;
|
|
int nMaxDisplayLen = fLanmanCompatible ? 15 : 16;
|
|
|
|
if (!fWackwack && fLanmanCompatible)
|
|
{
|
|
//
|
|
// Don't want backslahes, but if they do exist,
|
|
// remove them.
|
|
//
|
|
if (!::strncmp(lpszSrc, szWacks, ::strlen(szWacks)))
|
|
{
|
|
lpszSrc += ::strlen(szWacks);
|
|
if (nLength)
|
|
{
|
|
nLength -= 2;
|
|
}
|
|
}
|
|
}
|
|
|
|
if ((nDisplayLen = nLen = nLength ? nLength : ::strlen(lpszSrc)) > 15)
|
|
{
|
|
ch16 = (BYTE)lpszSrc[15];
|
|
nDisplayLen = fTruncate ? nMaxDisplayLen : nLen;
|
|
}
|
|
|
|
char szTarget[MAX_PATH] = {0};
|
|
char szRestore[MAX_PATH] = {0};
|
|
char * pTarget = &szTarget[0];
|
|
|
|
if (fWackwack)
|
|
{
|
|
::strcpy(pTarget, szWacks);
|
|
pTarget += ::strlen(szWacks);
|
|
}
|
|
|
|
if (lpszSrc == NULL)
|
|
{
|
|
int i = 1;
|
|
}
|
|
|
|
if (fOemName)
|
|
{
|
|
::OemToCharBuffA(lpszSrc, pTarget, nLen);
|
|
}
|
|
else
|
|
{
|
|
::memcpy(pTarget, lpszSrc, nLen);
|
|
}
|
|
|
|
int n = 0;
|
|
while (n < nDisplayLen)
|
|
{
|
|
if (fExpandChars)
|
|
{
|
|
#ifdef FE_SB
|
|
if (::IsDBCSLeadByte(*pTarget))
|
|
{
|
|
++n;
|
|
++pTarget;
|
|
}
|
|
else if (!WinsIsPrint(pTarget))
|
|
#else
|
|
if (!WinsIsPrint(pTarget))
|
|
#endif // FE_SB
|
|
{
|
|
*pTarget = BADNAME_CHAR;
|
|
}
|
|
}
|
|
|
|
++n;
|
|
++pTarget;
|
|
}
|
|
|
|
if (fLanmanCompatible)
|
|
{
|
|
//
|
|
// Back up over the spaces.
|
|
//
|
|
while (*(--pTarget) == ' ') /**/ ;
|
|
++pTarget;
|
|
}
|
|
|
|
// if there's a scope name attached, append the scope name
|
|
// to the strTarget before returning.
|
|
|
|
// check the length of lpSrc, if greater than NetBIOS name
|
|
// length, it has a scope name attached
|
|
if (nLength > 16)
|
|
{
|
|
if (lpszSrc[0x10] == '.')
|
|
{
|
|
::OemToCharBuffA(&lpszSrc[0x10], szRestore, sizeof(szRestore));
|
|
|
|
memcpy(pTarget, szRestore, nLength - 16);
|
|
pTarget += (nLength - 16);
|
|
}
|
|
}
|
|
|
|
*pTarget = '\0';
|
|
|
|
// convert the string to unicode. We've already done the oem to ansi
|
|
// conversion so use the Ansi code page now
|
|
MBCSToWide(szTarget, strDest, CP_ACP);
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CacheHint
|
|
Description
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::CacheHint
|
|
(
|
|
int nStartIndex,
|
|
int nEndIndex
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
HROW hrow;
|
|
|
|
Trace2("CacheHint - Start %d, End %d\n", nStartIndex, nEndIndex);
|
|
|
|
m_RecList.RemoveAllEntries();
|
|
|
|
WinsRecord ws;
|
|
WinsStrRecord * pwsr;
|
|
|
|
for (int i = nStartIndex; i <= nEndIndex; i++)
|
|
{
|
|
pwsr = BuildWinsStrRecord(i);
|
|
if (pwsr)
|
|
m_RecList.AddTail(pwsr);
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::SortItems
|
|
Description
|
|
Author: EricDav, v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
STDMETHODIMP
|
|
CActiveRegistrationsHandler::SortItems
|
|
(
|
|
int nColumn,
|
|
DWORD dwSortOptions,
|
|
LPARAM lUserParam
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
WINSDB_STATE uState = WINSDB_NORMAL;
|
|
if (!m_pCurrentDatabase)
|
|
{
|
|
return hr;
|
|
}
|
|
|
|
m_pCurrentDatabase->GetCurrentState(&uState);
|
|
if (uState != WINSDB_NORMAL)
|
|
{
|
|
AfxMessageBox(IDS_RECORDS_DOWNLOADING, MB_OK|MB_ICONINFORMATION);
|
|
return hr;
|
|
}
|
|
|
|
// put up the busy dialog
|
|
CSortWorker * pWorker = new CSortWorker(m_pCurrentDatabase,
|
|
nColumn,
|
|
dwSortOptions);
|
|
|
|
CLongOperationDialog dlgBusy(pWorker, IDR_AVI2);
|
|
|
|
dlgBusy.LoadTitleString(IDS_SNAPIN_DESC);
|
|
dlgBusy.LoadDescriptionString(IDS_SORTING);
|
|
|
|
// disable the system menu and the cancel buttons
|
|
dlgBusy.EnableCancel(FALSE);
|
|
|
|
dlgBusy.DoModal();
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::SetVirtualLbSize
|
|
Sets the virtual listbox count. Over-ride this if you need to
|
|
specify and options.
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::SetVirtualLbSize
|
|
(
|
|
ITFSComponent * pComponent,
|
|
LPARAM data
|
|
)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState( ));
|
|
|
|
HRESULT hr = hrOK;
|
|
SPIResultData spResultData;
|
|
CString strDescBarText;
|
|
CString strData;
|
|
ULARGE_INTEGER nullData;
|
|
ULARGE_INTEGER *pData = (ULARGE_INTEGER *)data;
|
|
|
|
nullData.HighPart = nullData.LowPart = 0;
|
|
pData = (data == NULL)? &nullData : (ULARGE_INTEGER*)data;
|
|
|
|
// just to avoid those cases when filtered shows up larger than scanned
|
|
if (pData->LowPart < pData->HighPart)
|
|
pData->HighPart = pData->LowPart;
|
|
|
|
strDescBarText.Empty();
|
|
strDescBarText.LoadString(IDS_RECORDS_FILTERED);
|
|
strData.Format(_T(" %d -- "), pData->HighPart);
|
|
strDescBarText += strData;
|
|
strData.LoadString(IDS_RECORDS_SCANNED);
|
|
strDescBarText += strData;
|
|
strData.Format(_T(" %d"), pData->LowPart);
|
|
strDescBarText += strData;
|
|
|
|
CORg (pComponent->GetResultData(&spResultData));
|
|
|
|
if (pData->HighPart == 0)
|
|
{
|
|
//CORg (spResultData->DeleteAllRsltItems());
|
|
CORg (spResultData->SetItemCount((int) pData->HighPart, MMCLV_UPDATE_NOSCROLL));
|
|
}
|
|
else
|
|
{
|
|
CORg (spResultData->SetItemCount((int) pData->HighPart, MMCLV_UPDATE_NOSCROLL));
|
|
}
|
|
|
|
CORg (spResultData->SetDescBarText((LPTSTR) (LPCTSTR) strDescBarText));
|
|
|
|
Error:
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::UpdateCurrentView
|
|
Updates the current view -- the MenuButton control and the result
|
|
pane.
|
|
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::UpdateCurrentView
|
|
(
|
|
ITFSNode * pNode
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
SPIComponentData spCompData;
|
|
SPIConsole spConsole;
|
|
IDataObject* pDataObject;
|
|
|
|
// update our current database to point to the correct one
|
|
m_pCurrentDatabase = m_spWinsDatabase;
|
|
|
|
// update our current database to point to the correct one
|
|
m_spWinsDatabase->SetActiveView(WINSDB_VIEW_FILTERED_DATABASE);
|
|
|
|
// Need to tell all of the views up update themselves with the new state.
|
|
m_spNodeMgr->GetComponentData(&spCompData);
|
|
|
|
CORg ( spCompData->QueryDataObject((MMC_COOKIE) pNode,
|
|
CCT_RESULT,
|
|
&pDataObject) );
|
|
|
|
CORg ( m_spNodeMgr->GetConsole(&spConsole) );
|
|
|
|
pDataObject->Release();
|
|
|
|
// update the listbox with the correct count for this view
|
|
UpdateListboxCount(pNode);
|
|
|
|
UpdateVerbs(pNode);
|
|
|
|
Error:
|
|
return hr;
|
|
}
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::CompareRecName
|
|
Checks if the name matches the Find record criterion
|
|
Author: EricDav, v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
BOOL
|
|
CActiveRegistrationsHandler::CompareRecName(LPSTR szNewName)
|
|
{
|
|
// convert the MBCS name to a wide string using the OEM
|
|
// code page so we can do the compare.
|
|
CString strTemp;
|
|
MBCSToWide(szNewName, strTemp, WINS_NAME_CODE_PAGE);
|
|
|
|
// when some invalid records get passed
|
|
if (strTemp.IsEmpty())
|
|
{
|
|
return FALSE;
|
|
}
|
|
|
|
CString strFindNameU = m_strFindName;
|
|
|
|
if (!m_fMatchCase)
|
|
{
|
|
strTemp.MakeUpper();
|
|
}
|
|
|
|
int nLen = strFindNameU.GetLength();
|
|
|
|
for (int nPos = 0; nPos < nLen; nPos++)
|
|
{
|
|
if (strFindNameU[nPos] == _T('*'))
|
|
{
|
|
break;
|
|
}
|
|
|
|
// the passed record has a smaller string length
|
|
if (nPos >= strTemp.GetLength())
|
|
{
|
|
return FALSE;
|
|
}
|
|
|
|
if (strTemp[nPos] != strFindNameU[nPos])
|
|
{
|
|
return FALSE;
|
|
}
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
|
|
/*!--------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::DeleteRegistration
|
|
Removes a registration from the server and the virtual listbox.
|
|
Need to remove the entry from both the find database and the
|
|
full database.
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::DeleteRegistration
|
|
(
|
|
ITFSComponent * pComponent,
|
|
int nIndex
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
DWORD err = 0;
|
|
CVirtualIndexArray arraySelectedIndicies;
|
|
int i;
|
|
int nCurrentCount;
|
|
WinsRecord ws;
|
|
int nCount;
|
|
SPIConsole spConsole;
|
|
LPDATAOBJECT pDataObject= NULL;
|
|
BOOL fDelete;
|
|
|
|
// ask whether to delete or tombstone the record
|
|
CDeleteRecordDlg dlgDel;
|
|
SPIResultData spResultData;
|
|
SPITFSNode spNode;
|
|
|
|
CORg (pComponent->GetResultData(&spResultData));
|
|
|
|
// build a list of the selected indicies in the virtual listbox
|
|
CORg (BuildVirtualSelectedItemList(pComponent, &arraySelectedIndicies));
|
|
nCount = (int)arraySelectedIndicies.GetSize();
|
|
|
|
dlgDel.m_fMultiple = (nCount > 1) ? TRUE : FALSE;
|
|
|
|
if (IDOK != dlgDel.DoModal())
|
|
{
|
|
return hrOK;
|
|
}
|
|
|
|
fDelete = (dlgDel.m_nDeleteRecord == 0);
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
for (i = 0; i < nCount; i++)
|
|
{
|
|
HROW hrowDel;
|
|
|
|
// remove each selected index
|
|
int nDelIndex = arraySelectedIndicies.GetAt(nCount -1 - i);
|
|
|
|
// from internal storage
|
|
CORg(m_spWinsDatabase->GetHRow(nDelIndex, &hrowDel));
|
|
CORg(m_spWinsDatabase->GetData(hrowDel, &ws));
|
|
|
|
if (fDelete)
|
|
{
|
|
// delete this record
|
|
err = DeleteMappingFromServer(pComponent, &ws, nDelIndex);
|
|
}
|
|
else
|
|
{
|
|
// tombstone the record
|
|
err = TombstoneRecords(pComponent, &ws);
|
|
}
|
|
|
|
// if a particular record could not be deleted, see if they want to cancel
|
|
if (err != ERROR_SUCCESS)
|
|
{
|
|
// put up
|
|
if (WinsMessageBox(err, MB_OKCANCEL) == IDCANCEL)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// remove from local storage if we are deleting this record
|
|
if (fDelete)
|
|
{
|
|
CORg(m_spWinsDatabase->DeleteRecord(hrowDel));
|
|
}
|
|
|
|
// remove from UI if delete is selected, othewise update the state (tombstone)
|
|
if (dlgDel.m_nDeleteRecord == 0)
|
|
{
|
|
CORg(spResultData->DeleteItem(nDelIndex, 0));
|
|
}
|
|
else
|
|
{
|
|
UpdateRecord(pComponent, &ws, nDelIndex);
|
|
}
|
|
}
|
|
}
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
// get the actreg node and redraw the list box
|
|
pComponent->GetSelectedNode(&spNode);
|
|
|
|
// now set the count.. this effectively redraws the contents
|
|
CORg (m_pCurrentDatabase->GetCurrentCount(&nCurrentCount));
|
|
|
|
UpdateListboxCount(spNode);
|
|
|
|
// if we are tombstoning, then there will still be selections
|
|
// in the result pane. In this case we need to pass in NULL
|
|
// for the node type so that the verbs get updated correctly.
|
|
if (!fDelete)
|
|
spNode.Set(NULL);
|
|
|
|
// update the cuurent view
|
|
UpdateCurrentView(spNode);
|
|
|
|
Error:
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler:: AddMapping(ITFSNode* pNode)
|
|
Adds a new Mapping to the server
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::AddMapping(ITFSNode* pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
DWORD err = ERROR_SUCCESS;
|
|
|
|
// get the server
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
BOOL fInternetGroup = FALSE;
|
|
|
|
if (m_strStaticMappingType.CompareNoCase(g_strStaticTypeInternetGroup) == 0)
|
|
{
|
|
fInternetGroup = TRUE;
|
|
}
|
|
|
|
CString strName(m_strStaticMappingName);
|
|
|
|
// check if valid NetBIOSNAme
|
|
if (pServer->IsValidNetBIOSName(strName, IsLanManCompatible(), FALSE))
|
|
{
|
|
m_Multiples.SetNetBIOSName(m_strStaticMappingName);
|
|
m_Multiples.SetNetBIOSNameLength(m_strStaticMappingName.GetLength());
|
|
|
|
int nMappings = 0;
|
|
int i;
|
|
|
|
switch(m_nStaticMappingType)
|
|
{
|
|
case WINSINTF_E_UNIQUE:
|
|
case WINSINTF_E_NORM_GROUP:
|
|
{
|
|
|
|
nMappings = 1;
|
|
LONG l;
|
|
|
|
m_Multiples.SetIpAddress(m_lArrayIPAddress.GetAt(0));
|
|
}
|
|
break;
|
|
|
|
case WINSINTF_E_SPEC_GROUP:
|
|
case WINSINTF_E_MULTIHOMED:
|
|
nMappings = (int)m_lArrayIPAddress.GetSize();
|
|
ASSERT(nMappings <= WINSINTF_MAX_MEM);
|
|
if (!fInternetGroup && nMappings == 0)
|
|
{
|
|
//return E_FAIL;
|
|
}
|
|
for (i = 0; i < nMappings; ++i)
|
|
{
|
|
m_Multiples.SetIpAddress(i,m_lArrayIPAddress.GetAt(i) );
|
|
}
|
|
break;
|
|
|
|
default:
|
|
ASSERT(0 && "Invalid mapping type!");
|
|
}
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
// add to the server
|
|
err = AddMappingToServer(pNode,
|
|
m_nStaticMappingType,
|
|
nMappings,
|
|
m_Multiples);
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
if (err == ERROR_SUCCESS)
|
|
{
|
|
//
|
|
// Added succesfully
|
|
//
|
|
}
|
|
else
|
|
{
|
|
//
|
|
// WINS disallowed the mapping. Put up the
|
|
// error message, and highlight the name
|
|
//
|
|
return HRESULT_FROM_WIN32(err);
|
|
}
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::EditMappingToServer(
|
|
ITFSNode* pNode,
|
|
int nType,
|
|
int nCount,
|
|
CMultipleIpNamePair& mipnp,
|
|
BOOL fEdit,
|
|
WinsRecord *pRecord
|
|
)
|
|
|
|
Edits the maping stored in the server database, WinsRecordAction is called
|
|
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::EditMappingToServer(
|
|
ITFSNode* pNode,
|
|
int nType,
|
|
int nCount,
|
|
CMultipleIpNamePair& mipnp,
|
|
BOOL fEdit, // Editing existing mapping?
|
|
WinsRecord *pRecord
|
|
)
|
|
{
|
|
SPITFSNode spNode;
|
|
pNode->GetParent(&spNode);
|
|
|
|
CWinsServerHandler* pServer = GETHANDLER(CWinsServerHandler, spNode);
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
WINSINTF_RECORD_ACTION_T RecAction;
|
|
PWINSINTF_RECORD_ACTION_T pRecAction;
|
|
|
|
DWORD dwLastStatus;
|
|
|
|
ASSERT(nType >= WINSINTF_E_UNIQUE && nType <= WINSINTF_E_MULTIHOMED);
|
|
|
|
ZeroMemory(&RecAction, sizeof(RecAction));
|
|
|
|
RecAction.TypOfRec_e = nType;
|
|
RecAction.Cmd_e = WINSINTF_E_INSERT;
|
|
RecAction.pAdd = NULL;
|
|
RecAction.pName = NULL;
|
|
pRecAction = &RecAction;
|
|
|
|
if (nType == WINSINTF_E_UNIQUE ||
|
|
nType == WINSINTF_E_NORM_GROUP)
|
|
{
|
|
RecAction.NoOfAdds = 1;
|
|
RecAction.Add.IPAdd = (LONG)mipnp.GetIpAddress();
|
|
RecAction.Add.Type = 0;
|
|
RecAction.Add.Len = 4;
|
|
}
|
|
else
|
|
{
|
|
ASSERT(nCount <= WINSINTF_MAX_MEM);
|
|
|
|
RecAction.pAdd = (WINSINTF_ADD_T *)::WinsAllocMem(
|
|
sizeof(WINSINTF_ADD_T) * nCount);
|
|
|
|
if (RecAction.pAdd == NULL)
|
|
{
|
|
return ERROR_NOT_ENOUGH_MEMORY;
|
|
}
|
|
|
|
RecAction.NoOfAdds = nCount;
|
|
int i;
|
|
for (i = 0; i < nCount; ++i)
|
|
{
|
|
(RecAction.pAdd+i)->IPAdd = (LONG)mipnp.GetIpAddress(i);
|
|
(RecAction.pAdd+i)->Type = 0;
|
|
(RecAction.pAdd+i)->Len = 4;
|
|
}
|
|
|
|
RecAction.NodeTyp = WINSINTF_E_PNODE;
|
|
}
|
|
RecAction.fStatic = TRUE;
|
|
|
|
// Don't copy the beginning slashes when adding.
|
|
//
|
|
int nLen = pRecord->dwNameLen;
|
|
|
|
//
|
|
// Must have at least enough room for 16 character string
|
|
//
|
|
RecAction.pName = (LPBYTE)::WinsAllocMem(nLen + 1);
|
|
if (RecAction.pName == NULL)
|
|
{
|
|
if (RecAction.pAdd)
|
|
{
|
|
::WinsFreeMem(RecAction.pAdd);
|
|
}
|
|
|
|
return ERROR_NOT_ENOUGH_MEMORY;
|
|
}
|
|
|
|
if (fEdit)
|
|
{
|
|
//
|
|
// No need to convert if already existing in the database.
|
|
//
|
|
// convert to ASCII string and copy
|
|
::memcpy((char *)RecAction.pName,
|
|
(LPCSTR) pRecord->szRecordName,
|
|
nLen+1
|
|
);
|
|
RecAction.NameLen = nLen;
|
|
}
|
|
else
|
|
{
|
|
::CharToOemBuff(mipnp.GetNetBIOSName(),
|
|
(char *)RecAction.pName,
|
|
nLen
|
|
);
|
|
}
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(), &pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (RecAction.pName != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pName);
|
|
}
|
|
|
|
if (RecAction.pAdd != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pAdd);
|
|
}
|
|
|
|
return dwLastStatus;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::AddMappingToServer(
|
|
ITFSNode* pNode,
|
|
int nType,
|
|
int nCount,
|
|
CMultipleIpNamePair& mipnp,
|
|
BOOL fEdit
|
|
)
|
|
Adds the cleaned record to the server, WinsRecordAction acalled with
|
|
WINSINTF_INSERT option
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
DWORD
|
|
CActiveRegistrationsHandler::AddMappingToServer(
|
|
ITFSNode* pNode,
|
|
int nType,
|
|
int nCount,
|
|
CMultipleIpNamePair& mipnp,
|
|
BOOL fEdit
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
WINSINTF_RECORD_ACTION_T RecAction;
|
|
PWINSINTF_RECORD_ACTION_T pRecAction;
|
|
|
|
SPITFSNode spNode;
|
|
pNode->GetParent(&spNode);
|
|
|
|
CWinsServerHandler *pServer = GETHANDLER(CWinsServerHandler, spNode);
|
|
|
|
DWORD dwLastStatus;
|
|
|
|
ASSERT(nType >= WINSINTF_E_UNIQUE && nType <= WINSINTF_E_MULTIHOMED);
|
|
|
|
ZeroMemory(&RecAction, sizeof(RecAction));
|
|
|
|
RecAction.TypOfRec_e = nType;
|
|
RecAction.Cmd_e = WINSINTF_E_INSERT;
|
|
RecAction.pAdd = NULL;
|
|
RecAction.pName = NULL;
|
|
pRecAction = &RecAction;
|
|
|
|
if (nType == WINSINTF_E_UNIQUE ||
|
|
nType == WINSINTF_E_NORM_GROUP)
|
|
{
|
|
RecAction.NoOfAdds = 1;
|
|
RecAction.Add.IPAdd = (LONG)mipnp.GetIpAddress();
|
|
RecAction.Add.Type = 0;
|
|
RecAction.Add.Len = 4;
|
|
}
|
|
else
|
|
{
|
|
ASSERT(nCount <= WINSINTF_MAX_MEM);
|
|
|
|
RecAction.pAdd = (WINSINTF_ADD_T *)::WinsAllocMem(
|
|
sizeof(WINSINTF_ADD_T) * nCount);
|
|
|
|
if (RecAction.pAdd == NULL)
|
|
{
|
|
return ERROR_NOT_ENOUGH_MEMORY;
|
|
}
|
|
|
|
RecAction.NoOfAdds = nCount;
|
|
int i;
|
|
for (i = 0; i < nCount; ++i)
|
|
{
|
|
(RecAction.pAdd+i)->IPAdd = (LONG)mipnp.GetIpAddress(i);
|
|
(RecAction.pAdd+i)->Type = 0;
|
|
(RecAction.pAdd+i)->Len = 4;
|
|
}
|
|
|
|
RecAction.NodeTyp = WINSINTF_E_PNODE;
|
|
}
|
|
|
|
RecAction.fStatic = TRUE;
|
|
|
|
//
|
|
// Don't copy the beginning slashes when adding.
|
|
//
|
|
int nLen = mipnp.GetNetBIOSNameLength();
|
|
|
|
//
|
|
// Must have at least enough room for 256 character string,
|
|
// includes the scope name too
|
|
//
|
|
RecAction.pName = (LPBYTE)::WinsAllocMem(257);
|
|
if (RecAction.pName == NULL)
|
|
{
|
|
return HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
|
|
}
|
|
|
|
ZeroMemory(RecAction.pName, 257);
|
|
|
|
LPSTR szTemp = (char *) alloca(100);
|
|
CString strTemp = mipnp.GetNetBIOSName();
|
|
|
|
// This should be OEM
|
|
WideToMBCS(strTemp, szTemp, WINS_NAME_CODE_PAGE);
|
|
|
|
nLen = strlen(szTemp);
|
|
|
|
::memcpy((char *)RecAction.pName,
|
|
(LPCSTR) szTemp,
|
|
nLen+1
|
|
);
|
|
|
|
if (nLen < 16)
|
|
{
|
|
if (nType == WINSINTF_E_SPEC_GROUP)
|
|
{
|
|
::memset(RecAction.pName+nLen, (int)' ',16-nLen);
|
|
RecAction.pName[15] = 0x1C;
|
|
RecAction.pName[16] = '\0';
|
|
RecAction.NameLen = nLen = 16;
|
|
|
|
char szAppend[MAX_PATH];
|
|
|
|
if (!m_strStaticMappingScope.IsEmpty())
|
|
{
|
|
AppendScopeName((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
strcpy((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
RecAction.NameLen = nLen = strlen((LPSTR)RecAction.pName);
|
|
}
|
|
|
|
pRecAction = &RecAction;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(),
|
|
&pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (dwLastStatus != ERROR_SUCCESS)
|
|
{
|
|
}
|
|
else
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
// query the server for correct info
|
|
PWINSINTF_RECORD_ACTION_T pRecAction1 = QueryForName(pNode, pRecAction);
|
|
|
|
if (pRecAction1 == NULL)
|
|
{
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction, pNode);
|
|
}
|
|
else
|
|
{
|
|
// the record found and correct info displayed
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction1, pNode);
|
|
free(pRecAction1->pName);
|
|
}
|
|
|
|
}
|
|
}
|
|
else
|
|
if (nType == WINSINTF_E_NORM_GROUP)
|
|
{
|
|
::memset(RecAction.pName+nLen, (int)' ',16-nLen);
|
|
RecAction.pName[15] = 0x1E;
|
|
RecAction.pName[16] = '\0';
|
|
RecAction.NameLen = nLen = 16;
|
|
|
|
char szAppend[MAX_PATH];
|
|
|
|
if (!m_strStaticMappingScope.IsEmpty())
|
|
{
|
|
AppendScopeName((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
strcpy((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
RecAction.NameLen = nLen = strlen((LPSTR)RecAction.pName);
|
|
|
|
}
|
|
|
|
pRecAction = &RecAction;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(),&pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (dwLastStatus != ERROR_SUCCESS)
|
|
{
|
|
}
|
|
else
|
|
{
|
|
// query the server for correct info
|
|
PWINSINTF_RECORD_ACTION_T pRecAction1 = QueryForName(pNode, pRecAction);
|
|
if (pRecAction1 == NULL)
|
|
{
|
|
hr = AddToLocalStorage(pRecAction, pNode);
|
|
}
|
|
else
|
|
{
|
|
// the record found and correct info displayed
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction1, pNode);
|
|
free(pRecAction1->pName);
|
|
}
|
|
|
|
}
|
|
}
|
|
else
|
|
{
|
|
//
|
|
// NOTICE:: When lanman compatible, the name is added
|
|
// three times - once each as worksta, server
|
|
// and messenger. This will change when we allow
|
|
// different 16th bytes to be set.
|
|
//
|
|
if (IsLanManCompatible() && !fEdit)
|
|
{
|
|
BYTE ab[] = { 0x00, 0x03, 0x20 };
|
|
::memset(RecAction.pName + nLen, (int)' ', 16-nLen);
|
|
int i;
|
|
for (i = 0; i < sizeof(ab) / sizeof(ab[0]); ++i)
|
|
{
|
|
*(RecAction.pName+15) = ab[i];
|
|
*(RecAction.pName+16) = '\0';
|
|
RecAction.NameLen = nLen = 16;
|
|
|
|
// append the scope name here, if present
|
|
|
|
if (!m_strStaticMappingScope.IsEmpty())
|
|
{
|
|
// don't allow the scope to be appended if the 16th char is 00,
|
|
// consistent with WinsCL
|
|
if (i != 0)
|
|
{
|
|
char *lpAppend = new char [MAX_PATH];
|
|
|
|
AppendScopeName((LPSTR)RecAction.pName, (LPSTR)lpAppend);
|
|
strcpy((LPSTR)RecAction.pName, (LPSTR)lpAppend);
|
|
RecAction.NameLen = nLen = strlen((LPSTR)RecAction.pName);
|
|
|
|
delete [] lpAppend;
|
|
}
|
|
}
|
|
pRecAction = &RecAction;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(),&pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
Trace1("WinsRecAction suceeded for '%lx'\n", ab[i]);
|
|
|
|
if (dwLastStatus != ERROR_SUCCESS)
|
|
{
|
|
break;
|
|
}
|
|
else
|
|
{
|
|
// query the server for correct info
|
|
PWINSINTF_RECORD_ACTION_T pRecAction1 = QueryForName(pNode, pRecAction);
|
|
|
|
if (pRecAction1 == NULL)
|
|
{
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction, pNode);
|
|
}
|
|
else
|
|
{
|
|
// the record found and correct info displayed
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction1, pNode);
|
|
free(pRecAction1->pName);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
::memset(RecAction.pName+nLen, (int)'\0',16-nLen);
|
|
*(RecAction.pName+15) = 0x20;
|
|
*(RecAction.pName+16) = '\0';
|
|
RecAction.NameLen = nLen;
|
|
|
|
char szAppend[MAX_PATH];
|
|
|
|
if (!m_strStaticMappingScope.IsEmpty())
|
|
{
|
|
AppendScopeName((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
strcpy((LPSTR)RecAction.pName, (LPSTR)szAppend);
|
|
RecAction.NameLen = nLen = strlen((LPSTR)RecAction.pName);
|
|
}
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(),&pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (dwLastStatus != ERROR_SUCCESS)
|
|
{
|
|
}
|
|
else
|
|
{
|
|
// query the server for correct info
|
|
PWINSINTF_RECORD_ACTION_T pRecAction1 = QueryForName(pNode, pRecAction);
|
|
|
|
if (pRecAction1 == NULL)
|
|
{
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction, pNode);
|
|
}
|
|
else
|
|
{
|
|
// the record found and correct info displayed
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction1, pNode);
|
|
free(pRecAction1->pName);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
RecAction.NameLen = nLen;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(),&pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (dwLastStatus != ERROR_SUCCESS)
|
|
{
|
|
}
|
|
else
|
|
{
|
|
// query the server for correct info
|
|
PWINSINTF_RECORD_ACTION_T pRecAction1 = QueryForName(pNode, pRecAction);
|
|
|
|
if (pRecAction1 == NULL)
|
|
{
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction, pNode);
|
|
}
|
|
else
|
|
{
|
|
// the record found and correct info displayed
|
|
//add it to the m_spWinsDatabase
|
|
hr = AddToLocalStorage(pRecAction1, pNode);
|
|
free(pRecAction1->pName);
|
|
}
|
|
}
|
|
}
|
|
|
|
if (RecAction.pName != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pName);
|
|
}
|
|
|
|
if (RecAction.pAdd != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pAdd);
|
|
}
|
|
|
|
return dwLastStatus;
|
|
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::AddToLocalStorage(
|
|
PWINSINTF_RECORD_ACTION_T pRecAction,
|
|
ITFSNode* pNode
|
|
)
|
|
add it to the m_spWinsDatabase, after getting all the information(Version, Exp etc)
|
|
from the server
|
|
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::AddToLocalStorage(PWINSINTF_RECORD_ACTION_T pRecAction,
|
|
ITFSNode* pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
BOOL bIPOk = FALSE;
|
|
|
|
WinsRecord ws;
|
|
|
|
// convert WINS_RECORD_ACTION to internal record
|
|
WinsIntfToWinsRecord(pRecAction, ws);
|
|
if (pRecAction->OwnerId < (UINT) m_pServerInfoArray->GetSize())
|
|
ws.dwOwner = (*m_pServerInfoArray)[pRecAction->OwnerId].m_dwIp;
|
|
|
|
if (m_spWinsDatabase)
|
|
{
|
|
hr = m_spWinsDatabase->AddRecord(&ws);
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnImportLMHOSTS(ITFSNode* pNode)
|
|
Command Handler for Import LMHosts
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnImportLMHOSTS(ITFSNode* pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
CString strTitle;
|
|
CString strFilter;
|
|
strFilter.LoadString(IDS_ALL_FILES);
|
|
|
|
// put up the file dlg to get the file
|
|
CFileDialog dlgFile(TRUE,
|
|
NULL,
|
|
NULL,
|
|
OFN_FILEMUSTEXIST | OFN_HIDEREADONLY,
|
|
strFilter);
|
|
|
|
dlgFile.m_ofn.lpstrTitle = strTitle;
|
|
|
|
DWORD err = ERROR_SUCCESS;
|
|
|
|
if (dlgFile.DoModal() == IDOK)
|
|
{
|
|
//
|
|
// If this is a local connection, we copy the file to
|
|
// temporary name (the source may be on a remote drive
|
|
// which is not accessible to the WINS service.
|
|
//
|
|
// If this is not a local connection, attempt to copy
|
|
// the file to a temp name on C$ of the WINS server
|
|
//
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
CString strMappingFile(dlgFile.GetPathName());
|
|
|
|
do
|
|
{
|
|
if (IsLocalConnection(pNode))
|
|
{
|
|
CString strWins;
|
|
strWins.LoadString(IDS_WINS);
|
|
CString strTmpFile(_tempnam(NULL, "WINS"));
|
|
//
|
|
// First copy file to a temporary name (since the file
|
|
// could be remote), and then import and delete this file
|
|
//
|
|
if (!CopyFile(strMappingFile, strTmpFile, TRUE))
|
|
{
|
|
err = ::GetLastError();
|
|
break;
|
|
}
|
|
//
|
|
// Now import the temporary file, and delete the file
|
|
// afterwards.
|
|
//
|
|
err = ImportStaticMappingsFile(pNode, strTmpFile, TRUE);
|
|
}
|
|
else
|
|
{
|
|
//
|
|
// Try copying to the remote machine C: drive
|
|
//
|
|
CString strServerName;
|
|
GetServerName(pNode, strServerName);
|
|
|
|
CString strWins;
|
|
strWins.LoadString(IDS_WINS);
|
|
|
|
CString strTemp;
|
|
strTemp.Format(_T("\\\\%s\\C$"), strServerName);
|
|
|
|
// Find a suitable remote file name
|
|
CString strRemoteFile;
|
|
DWORD dwErr = RemoteTmp(strTemp, strWins, strRemoteFile);
|
|
|
|
if (dwErr != ERROR_SUCCESS)
|
|
{
|
|
CString strError, strMessage;
|
|
|
|
::GetSystemMessage(dwErr, strError.GetBuffer(1024), 1024);
|
|
strError.ReleaseBuffer();
|
|
|
|
AfxFormatString1(strMessage, IDS_ERR_REMOTE_IMPORT, strError);
|
|
AfxMessageBox(strMessage);
|
|
|
|
goto Error;
|
|
}
|
|
|
|
//
|
|
// First copy file to a temporary name (since the file
|
|
// could be remote), and then import and delete this file
|
|
//
|
|
if (!CopyFile(strMappingFile, strRemoteFile, TRUE))
|
|
{
|
|
err = ::GetLastError();
|
|
break;
|
|
}
|
|
|
|
//
|
|
// fixup the filename so it looks local to the wins server
|
|
//
|
|
LPTSTR pch = strRemoteFile.GetBuffer(256);
|
|
|
|
//
|
|
// Now replace the remote path with a local path
|
|
// for the remote WINS server
|
|
//
|
|
while (*pch != '$')
|
|
{
|
|
++pch;
|
|
}
|
|
*pch = ':';
|
|
--pch;
|
|
CString strRemoteFileNew(pch);
|
|
strRemoteFile.ReleaseBuffer();
|
|
|
|
//
|
|
// Now import the temporary file, and delete the file
|
|
// afterwards.
|
|
//
|
|
err = ImportStaticMappingsFile(pNode, strRemoteFileNew, TRUE);
|
|
}
|
|
}
|
|
while(FALSE);
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
if (err == ERROR_SUCCESS)
|
|
{
|
|
AfxMessageBox(IDS_MSG_IMPORT, MB_ICONINFORMATION);
|
|
|
|
// refresh the result pane now.
|
|
RefreshResults(pNode);
|
|
}
|
|
else
|
|
{
|
|
::WinsMessageBox(err, MB_OK);
|
|
}
|
|
|
|
// refresh the server statistics
|
|
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
// rferesh the statistics
|
|
pServer->GetStatistics(spServerNode, NULL);
|
|
}
|
|
|
|
Error:
|
|
return err;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
|
|
CActiveRegistrationsHandler::IsLocalConnection(ITFSNode *pNode)
|
|
Check if the loacl machine is being managed
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
BOOL
|
|
CActiveRegistrationsHandler::IsLocalConnection(ITFSNode *pNode)
|
|
{
|
|
// get the server netbios name
|
|
CString strServerName;
|
|
GetServerName(pNode,strServerName);
|
|
|
|
// address of name buffer
|
|
TCHAR szBuffer[MAX_COMPUTERNAME_LENGTH + 1];
|
|
DWORD nSize = MAX_COMPUTERNAME_LENGTH + 1 ;
|
|
|
|
::GetComputerName(szBuffer, &nSize);
|
|
|
|
CString strCompName(szBuffer);
|
|
|
|
if (strCompName == strServerName)
|
|
{
|
|
return TRUE;
|
|
}
|
|
|
|
return FALSE;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetServerName(ITFSNode * pNode,
|
|
CString &strServerName)
|
|
Talk to the parent node and get the server name
|
|
we are managing
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::GetServerName(ITFSNode * pNode,
|
|
CString &strServerName)
|
|
{
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
strServerName = pServer->GetServerAddress();
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::ImportStaticMappingsFile(CString strFile,
|
|
BOOL fDelete)
|
|
Call the WINS API to import the statis mappings text file
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::ImportStaticMappingsFile(ITFSNode *pNode,
|
|
CString strFile,
|
|
BOOL fDelete)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
LPTSTR lpszTemp = strFile.GetBuffer(MAX_PATH * 2);
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
DWORD dwLastStatus = ::WinsDoStaticInit(pServer->GetBinding(),
|
|
(LPTSTR)lpszTemp,
|
|
fDelete);
|
|
#else
|
|
DWORD dwLastStatus = ::WinsDoStaticInit((LPTSTR)lpszTemp, fDelete);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
strFile.ReleaseBuffer();
|
|
|
|
return dwLastStatus;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::RemoteTmp(CString strDir,CString strPrefix )
|
|
Get a temporary file on a remote drive
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
DWORD
|
|
CActiveRegistrationsHandler::RemoteTmp(CString & strDir, CString & strPrefix, CString & strRemoteFile)
|
|
{
|
|
DWORD dwErr = ERROR_SUCCESS;
|
|
CString strReturn;
|
|
int n = 0;
|
|
|
|
while (TRUE)
|
|
{
|
|
strReturn.Format(_T("%s\\%s%d"), strDir, strPrefix, ++n);
|
|
|
|
if (GetFileAttributes(strReturn) == -1)
|
|
{
|
|
dwErr = GetLastError();
|
|
if (dwErr == ERROR_FILE_NOT_FOUND)
|
|
{
|
|
strRemoteFile = strReturn;
|
|
dwErr = ERROR_SUCCESS;
|
|
}
|
|
|
|
break;
|
|
}
|
|
}
|
|
|
|
return dwErr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::DeleteMappingFromServer(ITFSComponent * pComponent,
|
|
WinsRecord *pws,int nIndex)
|
|
Deletes wins record from the Wins Server
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
DWORD
|
|
CActiveRegistrationsHandler::DeleteMappingFromServer
|
|
(
|
|
ITFSComponent * pComponent,
|
|
WinsRecord * pws,
|
|
int nIndex
|
|
)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
//check if the record is static
|
|
WINSINTF_RECORD_ACTION_T RecAction;
|
|
PWINSINTF_RECORD_ACTION_T pRecAction;
|
|
|
|
ZeroMemory(&RecAction, sizeof(RecAction));
|
|
|
|
SPITFSNode spNode;
|
|
pComponent->GetSelectedNode(&spNode);
|
|
|
|
SPITFSNode spParentNode;
|
|
spNode->GetParent(&spParentNode);
|
|
|
|
CWinsServerHandler* pServer = GETHANDLER(CWinsServerHandler, spParentNode);
|
|
|
|
if (pws->dwState & WINSDB_REC_STATIC)
|
|
{
|
|
RecAction.fStatic = TRUE;
|
|
|
|
if (pws->dwState & WINSDB_REC_UNIQUE)
|
|
{
|
|
RecAction.TypOfRec_e = WINSINTF_E_UNIQUE;
|
|
}
|
|
else
|
|
if (pws->dwState & WINSDB_REC_SPEC_GROUP)
|
|
{
|
|
RecAction.TypOfRec_e = WINSINTF_E_SPEC_GROUP;
|
|
}
|
|
else
|
|
if (pws->dwState & WINSDB_REC_NORM_GROUP)
|
|
{
|
|
RecAction.TypOfRec_e = WINSINTF_E_NORM_GROUP;
|
|
}
|
|
else
|
|
if (pws->dwState & WINSDB_REC_MULTIHOMED)
|
|
{
|
|
RecAction.TypOfRec_e = WINSINTF_E_MULTIHOMED;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
RecAction.fStatic = FALSE;
|
|
}
|
|
|
|
RecAction.Cmd_e = WINSINTF_E_DELETE;
|
|
RecAction.State_e = WINSINTF_E_DELETED;
|
|
|
|
RecAction.pName = NULL;
|
|
RecAction.pAdd = NULL;
|
|
|
|
pRecAction = &RecAction;
|
|
|
|
RecAction.pName = (LPBYTE)::WinsAllocMem(pws->dwNameLen+1);
|
|
if (RecAction.pName == NULL)
|
|
{
|
|
return ::GetLastError();
|
|
}
|
|
|
|
ZeroMemory(RecAction.pName, pws->dwNameLen+1);
|
|
memcpy(RecAction.pName, pws->szRecordName, pws->dwNameLen);
|
|
|
|
if (pws->dwNameLen)
|
|
{
|
|
RecAction.NameLen = pws->dwNameLen;
|
|
}
|
|
else
|
|
{
|
|
RecAction.NameLen = ::strlen((LPSTR)RecAction.pName);
|
|
}
|
|
|
|
RecAction.OwnerId = pws->dwOwner;
|
|
|
|
DWORD dwLastStatus = ERROR_SUCCESS;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
dwLastStatus = ::WinsRecordAction(pServer->GetBinding(), &pRecAction);
|
|
#else
|
|
dwLastStatus = ::WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (RecAction.pName != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pName);
|
|
}
|
|
|
|
if (RecAction.pAdd != NULL)
|
|
{
|
|
::WinsFreeMem(RecAction.pAdd);
|
|
}
|
|
|
|
return dwLastStatus;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::EditMapping(ITFSNode *pNode)
|
|
Edit the already mapping , the user might have changed the IP address
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::EditMapping(ITFSNode *pNode,
|
|
ITFSComponent *pComponent,
|
|
int nIndex)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
DWORD err = ERROR_SUCCESS;
|
|
int i;
|
|
int nCurrentCount;
|
|
|
|
// get the server
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
BOOL fInternetGroup = FALSE;
|
|
|
|
if (m_strStaticMappingType.CompareNoCase(g_strStaticTypeInternetGroup) == 0)
|
|
{
|
|
fInternetGroup = TRUE;
|
|
}
|
|
|
|
// create the multiple IPNamePr
|
|
if (pServer->IsValidNetBIOSName(m_strStaticMappingName, IsLanManCompatible(), FALSE))
|
|
{
|
|
m_Multiples.SetNetBIOSName(m_strStaticMappingName);
|
|
m_Multiples.SetNetBIOSNameLength(m_strStaticMappingName.GetLength());
|
|
|
|
int nMappings = 0;
|
|
int i;
|
|
|
|
switch(m_nStaticMappingType)
|
|
{
|
|
case WINSINTF_E_UNIQUE:
|
|
case WINSINTF_E_NORM_GROUP:
|
|
{
|
|
nMappings = 1;
|
|
LONG l;
|
|
|
|
m_Multiples.SetIpAddress(m_lArrayIPAddress.GetAt(0));
|
|
}
|
|
break;
|
|
|
|
case WINSINTF_E_SPEC_GROUP:
|
|
case WINSINTF_E_MULTIHOMED:
|
|
nMappings = (int)m_lArrayIPAddress.GetSize();
|
|
ASSERT(nMappings <= WINSINTF_MAX_MEM);
|
|
if (!fInternetGroup && nMappings == 0)
|
|
{
|
|
//return E_FAIL;
|
|
}
|
|
for (i = 0; i < nMappings; ++i)
|
|
{
|
|
m_Multiples.SetIpAddress(i,m_lArrayIPAddress.GetAt(i) );
|
|
}
|
|
break;
|
|
|
|
default:
|
|
ASSERT(0 && "Invalid mapping type!");
|
|
}
|
|
|
|
HROW hrowDel;
|
|
WinsRecord ws;
|
|
|
|
// from internal storage
|
|
CORg(m_spWinsDatabase->GetHRow(m_nSelectedIndex, &hrowDel));
|
|
CORg(m_spWinsDatabase->GetData(hrowDel, &ws));
|
|
|
|
if (m_nStaticMappingType == WINSINTF_E_SPEC_GROUP ||
|
|
m_nStaticMappingType == WINSINTF_E_MULTIHOMED)
|
|
{
|
|
//
|
|
// An internet group being edited cannot simply be
|
|
// re-added, since it will add ip addresses, not
|
|
// overwrite them, so it must first be removed.
|
|
//
|
|
err = DeleteMappingFromServer(pComponent, &ws, m_nSelectedIndex);
|
|
}
|
|
|
|
//
|
|
// We edit the mapping by merely re-adding it, which
|
|
// has the same effect.
|
|
//
|
|
if (err == ERROR_SUCCESS)
|
|
{
|
|
err = EditMappingToServer(pNode,
|
|
m_nStaticMappingType,
|
|
nMappings,
|
|
m_Multiples,
|
|
TRUE,
|
|
&m_CurrentRecord);
|
|
}
|
|
|
|
if (err != ERROR_SUCCESS)
|
|
{
|
|
return err;
|
|
}
|
|
|
|
WINSINTF_ADD_T OwnAdd;
|
|
|
|
//
|
|
// Fill in current owner
|
|
//
|
|
OwnAdd.Len = 4;
|
|
OwnAdd.Type = 0;
|
|
OwnAdd.IPAdd = pServer->GetServerIP();
|
|
|
|
WINSINTF_RECS_T Recs;
|
|
Recs.pRow = NULL;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
err = ::WinsGetDbRecsByName(pServer->GetBinding(),
|
|
&OwnAdd,
|
|
WINSINTF_BEGINNING,
|
|
(LPBYTE) ws.szRecordName,
|
|
ws.dwNameLen,
|
|
1,
|
|
(ws.dwState & WINSDB_REC_STATIC)
|
|
? WINSINTF_STATIC : WINSINTF_DYNAMIC,
|
|
&Recs);
|
|
|
|
#else
|
|
err = ::WinsGetDbRecsByName(&OwnAdd,
|
|
WINSINTF_BEGINNING,
|
|
(LPBYTE) ws.szRecordName,
|
|
ws.dwNameLen,
|
|
1,
|
|
(ws.dwState & WINSDB_REC_STATIC)
|
|
? WINSINTF_STATIC : WINSINTF_DYNAMIC,
|
|
&Recs);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
if (err == ERROR_SUCCESS)
|
|
{
|
|
TRY
|
|
{
|
|
ASSERT(Recs.NoOfRecs == 1);
|
|
if (Recs.NoOfRecs == 0)
|
|
{
|
|
//
|
|
// the record can not be found.
|
|
// This should not happen!
|
|
//
|
|
//Trace("Unable to find the record to refresh:\n");
|
|
return ERROR_REC_NON_EXISTENT;
|
|
}
|
|
|
|
PWINSINTF_RECORD_ACTION_T pRow1 = Recs.pRow;
|
|
WinsRecord wRecord;
|
|
|
|
WinsIntfToWinsRecord(pRow1, wRecord);
|
|
if (pRow1->OwnerId < (UINT) m_pServerInfoArray->GetSize())
|
|
wRecord.dwOwner = (*m_pServerInfoArray)[pRow1->OwnerId].m_dwIp;
|
|
|
|
// RefreshData(Recs.pRow), delete this particular record and add it again;
|
|
// from internal storage
|
|
CORg(m_spWinsDatabase->DeleteRecord(hrowDel));
|
|
CORg(m_spWinsDatabase->AddRecord(&wRecord));
|
|
|
|
// now set the count.. this effectively redraws the contents
|
|
CORg (m_pCurrentDatabase->GetCurrentCount(&nCurrentCount));
|
|
|
|
UpdateCurrentView(pNode);
|
|
}
|
|
CATCH_ALL(e)
|
|
{
|
|
return ::GetLastError();
|
|
}
|
|
END_CATCH_ALL;
|
|
}
|
|
|
|
if (Recs.pRow != NULL)
|
|
{
|
|
::WinsFreeMem(Recs.pRow);
|
|
}
|
|
}
|
|
|
|
Error:
|
|
return err;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::QueryForName()
|
|
queries WINS server given the name and gets info to be displayed in the
|
|
result pane
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
PWINSINTF_RECORD_ACTION_T
|
|
CActiveRegistrationsHandler::QueryForName
|
|
(
|
|
ITFSNode * pNode,
|
|
PWINSINTF_RECORD_ACTION_T pRecAction,
|
|
BOOL fStatic
|
|
)
|
|
{
|
|
SPITFSNode spNode;
|
|
pNode->GetParent(&spNode);
|
|
|
|
CWinsServerHandler *pServer = GETHANDLER(CWinsServerHandler, spNode);
|
|
|
|
HRESULT hr = hrOK;
|
|
|
|
pRecAction->pAdd = NULL;
|
|
pRecAction->NoOfAdds = 0;
|
|
|
|
pRecAction->fStatic = fStatic;
|
|
pRecAction->Cmd_e = WINSINTF_E_QUERY;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
DWORD dwStatus = WinsRecordAction(pServer->GetBinding(), &pRecAction);
|
|
#else
|
|
DWORD dwStatus = WinsRecordAction(&pRecAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
// when we query for a record, the string length must not include the null terminator.
|
|
// in the normal case using GetDbRecs, wins returns the name length as length + 1
|
|
// for the null terminator. Since all of the code expects any WINSINTFS_RECORD_ACTION_T
|
|
// struct to be in that format, let's touch things up a bit and make a copy.
|
|
if (dwStatus == 0)
|
|
{
|
|
pRecAction->NameLen++;
|
|
LPBYTE pNew = (LPBYTE) malloc(pRecAction->NameLen);
|
|
if (pNew)
|
|
{
|
|
ZeroMemory(pNew, pRecAction->NameLen);
|
|
|
|
memcpy(pNew, pRecAction->pName, pRecAction->NameLen - 1);
|
|
|
|
pRecAction->pName = pNew;
|
|
}
|
|
|
|
return pRecAction;
|
|
}
|
|
else
|
|
{
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::ToString(DWORD dwParam, CString& strParam)
|
|
converts DWORD to CString
|
|
Author v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::ToString(DWORD dwParam, CString& strParam)
|
|
{
|
|
TCHAR szStr[20];
|
|
_ltot((LONG)dwParam, szStr, 10);
|
|
CString str(szStr);
|
|
strParam = str;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnExportEntries()
|
|
Command Handler for Export Database
|
|
Author v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnExportEntries()
|
|
{
|
|
HRESULT hr = hrOK;
|
|
WinsRecord ws;
|
|
HROW hrow;
|
|
|
|
if (!m_pCurrentDatabase)
|
|
{
|
|
return NULL;
|
|
}
|
|
|
|
// Bring up the Save Dialog
|
|
|
|
CString strType;
|
|
strType.LoadString(IDS_FILE_EXTENSION);
|
|
|
|
CString strDefFileName;
|
|
strDefFileName.LoadString(IDS_FILE_DEFNAME);
|
|
|
|
CString strFilter;
|
|
strFilter.LoadString(IDS_STR_EXPORTFILE_FILTER);
|
|
|
|
// put up the dlg to get the file name
|
|
CFileDialog cFileDlg(FALSE,
|
|
strType,
|
|
strDefFileName,
|
|
OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
|
|
strFilter);
|
|
|
|
CString strTitle;
|
|
strTitle.LoadString(IDS_EXPFILE_TITLE);
|
|
|
|
cFileDlg.m_ofn.lpstrTitle = strTitle;
|
|
|
|
if ( cFileDlg.DoModal() != IDOK )
|
|
{
|
|
return hrFalse;
|
|
}
|
|
|
|
// getthe entire path
|
|
CString strFileName = cFileDlg.GetPathName();
|
|
|
|
COM_PROTECT_TRY
|
|
{
|
|
int nCount;
|
|
m_pCurrentDatabase->GetCurrentCount(&nCount);
|
|
|
|
CString strContent;
|
|
strContent.Empty();
|
|
|
|
CString strTemp;
|
|
strTemp.Empty();
|
|
|
|
CString strLine;
|
|
strLine.Empty();
|
|
|
|
CString strDelim = _T(',');
|
|
CString strNewLine = _T("\r\n");
|
|
|
|
// create a file named "WinsExp.txt" in the current directory
|
|
CFile cFileExp(strFileName,
|
|
CFile::modeCreate | CFile::modeRead | CFile::modeWrite);
|
|
|
|
// this is a unicode file, write the unicde lead bytes (2)
|
|
cFileExp.Write(&gwUnicodeHeader, sizeof(WORD));
|
|
|
|
CString strHead;
|
|
strHead.LoadString(IDS_STRING_HEAD);
|
|
|
|
strHead += strNewLine;
|
|
|
|
cFileExp.Write(strHead, strHead.GetLength()*sizeof(TCHAR));
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
#ifdef DEBUG
|
|
CTime timeStart, timeFinish;
|
|
timeStart = CTime::GetCurrentTime();
|
|
#endif
|
|
|
|
for (int i = 0; i < nCount; i++)
|
|
{
|
|
strLine.Empty();
|
|
strTemp.Empty();
|
|
|
|
hr = m_pCurrentDatabase->GetHRow(i, &hrow);
|
|
hr = m_pCurrentDatabase->GetData(hrow, &ws);
|
|
|
|
// build the name string
|
|
CleanNetBIOSName(ws.szRecordName, // input char *
|
|
strTemp, // output LPTSTR
|
|
TRUE, // Expand
|
|
TRUE, // Truncate
|
|
IsLanManCompatible(),
|
|
TRUE, // name is OEM
|
|
FALSE, // No double backslash
|
|
ws.dwNameLen);
|
|
|
|
strLine += strTemp;
|
|
strLine += strDelim;
|
|
|
|
// now the type
|
|
m_NameTypeMap.TypeToCString((DWORD)ws.szRecordName[15], MAKELONG(HIWORD(ws.dwType), 0), strTemp);
|
|
strLine += strTemp;
|
|
strLine += strDelim;
|
|
|
|
// IP address
|
|
if ( (ws.dwState & WINSDB_REC_UNIQUE) ||
|
|
(ws.dwState & WINSDB_REC_NORM_GROUP) )
|
|
{
|
|
MakeIPAddress(ws.dwIpAdd[0], strTemp);
|
|
strLine += strTemp;
|
|
}
|
|
else
|
|
{
|
|
CString strTemp2;
|
|
|
|
// this record has multiple addresses. The addresses are in the form of:
|
|
// owner wins, then IP address
|
|
// out put will look like address - owner IP;address - owner ip
|
|
for (DWORD i = 0; i < ws.dwNoOfAddrs; i++)
|
|
{
|
|
if (i != 0)
|
|
strLine += _T(";");
|
|
|
|
// owner
|
|
::MakeIPAddress(ws.dwIpAdd[i++], strTemp);
|
|
// actual address
|
|
::MakeIPAddress(ws.dwIpAdd[i], strTemp2);
|
|
|
|
strTemp2 += _T(" - ");
|
|
strTemp2 += strTemp;
|
|
|
|
strLine += strTemp2;
|
|
}
|
|
}
|
|
|
|
strLine += strDelim;
|
|
|
|
// active status
|
|
GetStateString(ws.dwState, strTemp);
|
|
strLine += strTemp;
|
|
strLine += strDelim;
|
|
|
|
// static flag
|
|
if (ws.dwState & WINSDB_REC_STATIC)
|
|
strTemp.LoadString(IDS_ACTIVEREG_STATIC);
|
|
else
|
|
strTemp = _T("");
|
|
strLine += strTemp;
|
|
strLine += strDelim;
|
|
|
|
// version
|
|
GetVersionInfo(ws.liVersion.LowPart, ws.liVersion.HighPart, strTemp);
|
|
strLine += strTemp;
|
|
strLine += strDelim;
|
|
|
|
// expiration time
|
|
if (ws.dwExpiration == INFINITE_EXPIRATION)
|
|
{
|
|
Verify(strTemp.LoadString(IDS_INFINITE));
|
|
}
|
|
else
|
|
{
|
|
strTemp = TMST(ws.dwExpiration);
|
|
}
|
|
|
|
strLine += strTemp;
|
|
strLine += strNewLine;
|
|
|
|
strContent += strLine;
|
|
|
|
//optimize
|
|
// write to the file for every 1000 records converted
|
|
if ( i % 1000 == 0)
|
|
{
|
|
cFileExp.Write(strContent, strContent.GetLength() * (sizeof(TCHAR)) );
|
|
cFileExp.SeekToEnd();
|
|
|
|
// clear all the strings now
|
|
strContent.Empty();
|
|
}
|
|
}
|
|
|
|
// write to the file
|
|
|
|
cFileExp.Write(strContent, strContent.GetLength() * (sizeof(TCHAR)) );
|
|
cFileExp.Close();
|
|
|
|
#ifdef DEBUG
|
|
timeFinish = CTime::GetCurrentTime();
|
|
CTimeSpan timeDelta = timeFinish - timeStart;
|
|
CString strTempTime = timeDelta.Format(_T("%H:%M:%S"));
|
|
Trace2("WINS DB - Export Entries: %d records read, total time %s\n", i, strTempTime);
|
|
#endif
|
|
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
}
|
|
COM_PROTECT_CATCH
|
|
|
|
CString strDisp;
|
|
AfxFormatString1(strDisp, IDS_EXPORT_SUCCESS, strFileName);
|
|
|
|
AfxMessageBox(strDisp, MB_ICONINFORMATION );
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::BuildOwnerArray(ITFSNode *pNode)
|
|
Builds the list of owners in the server
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::BuildOwnerArray(handle_t hBinding)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
DWORD err = 0;
|
|
CWinsResults winsResults;
|
|
|
|
err = winsResults.Update(hBinding);
|
|
|
|
if (err == ERROR_SUCCESS)
|
|
{
|
|
m_pServerInfoArray->RemoveAll();
|
|
|
|
LARGE_INTEGER liVersion;
|
|
DWORD dwIP;
|
|
CString strName;
|
|
BOOL fGetHostName = TRUE;
|
|
|
|
for (int i = 0; i < winsResults.AddVersMaps.GetSize(); i++)
|
|
{
|
|
liVersion = winsResults.AddVersMaps[i].VersNo;
|
|
dwIP = winsResults.AddVersMaps[i].Add.IPAdd;
|
|
|
|
CServerInfo serverInfo(dwIP, strName, liVersion);
|
|
|
|
int nIndex = (int)m_pServerInfoArray->Add(serverInfo);
|
|
}
|
|
}
|
|
|
|
return HRESULT_FROM_WIN32(err);
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnCheckRegNames(ITFSNode* pNode)
|
|
Command Handler for Check Registered names
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnCheckRegNames(ITFSNode* pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
CCheckRegNames dlgRegName;
|
|
|
|
if (IDOK != dlgRegName.DoModal())
|
|
{
|
|
return hr;
|
|
}
|
|
|
|
CCheckNamesProgress dlgCheckNames;
|
|
|
|
dlgCheckNames.m_strNameArray.Copy(dlgRegName.m_strNameArray);
|
|
dlgCheckNames.m_strServerArray.Copy(dlgRegName.m_strServerArray);
|
|
dlgCheckNames.m_fVerifyWithPartners = dlgRegName.m_fVerifyWithPartners;
|
|
|
|
dlgCheckNames.DoModal();
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::OnDeleteOwner(ITFSNode* pNode)
|
|
Command Handler for Tombstone all records
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::OnDeleteOwner(ITFSNode* pNode)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
|
|
CDeleteOwner dlgDeleteOwner(pNode);
|
|
|
|
DWORD dwErr, dwIp;
|
|
CString strText, strIp;
|
|
|
|
if (dlgDeleteOwner.DoModal() == IDOK)
|
|
{
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
if (dlgDeleteOwner.m_fDeleteRecords)
|
|
{
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
dwErr = pServer->DeleteWinsServer(dlgDeleteOwner.m_dwSelectedOwner);
|
|
|
|
if (dwErr == ERROR_SUCCESS)
|
|
{
|
|
// remove from list
|
|
for (int i = 0; i < m_pServerInfoArray->GetSize(); i++)
|
|
{
|
|
if (m_pServerInfoArray->GetAt(i).m_dwIp == dlgDeleteOwner.m_dwSelectedOwner)
|
|
{
|
|
m_pServerInfoArray->RemoveAt(i);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
dwErr = TombstoneAllRecords(dlgDeleteOwner.m_dwSelectedOwner, pNode);
|
|
}
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
if (dwErr != ERROR_SUCCESS)
|
|
{
|
|
WinsMessageBox(dwErr);
|
|
}
|
|
|
|
// TODO trigger an update of whatever is in the active registrations result pane
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::AppendScopeName(char* lpName,
|
|
char* lpScopeAppended)
|
|
|
|
Appends the scope name to the record name, when there isa scope name
|
|
attached to the record
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::AppendScopeName(char* lpName, char* lpScopeAppended)
|
|
{
|
|
|
|
strcpy(lpScopeAppended, lpName);
|
|
char szTemp[MAX_PATH];
|
|
|
|
CString strScope = _T(".") + m_strStaticMappingScope;
|
|
|
|
// INTL$ Should the scope name be OEM as well?
|
|
WideToMBCS(strScope, szTemp, WINS_NAME_CODE_PAGE, WC_COMPOSITECHECK);
|
|
|
|
strcat(lpScopeAppended, szTemp);
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::TombstoneRecords()
|
|
Handles Tomsstoning of records
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
DWORD
|
|
CActiveRegistrationsHandler::TombstoneRecords
|
|
(
|
|
ITFSComponent * pComponent,
|
|
WinsRecord * pws
|
|
)
|
|
{
|
|
DWORD err = ERROR_SUCCESS;
|
|
|
|
// get the server node to retrive the handle for the WINS api
|
|
SPITFSNode spNode;
|
|
pComponent->GetSelectedNode(&spNode);
|
|
|
|
SPITFSNode spParentNode;
|
|
spNode->GetParent(&spParentNode);
|
|
|
|
CWinsServerHandler* pServer = GETHANDLER(CWinsServerHandler, spParentNode);
|
|
|
|
WINSINTF_VERS_NO_T MinVersNo;
|
|
WINSINTF_VERS_NO_T MaxVersNo;
|
|
|
|
MinVersNo = pws->liVersion;
|
|
MaxVersNo = MinVersNo;
|
|
|
|
// gotta get the owner of this record
|
|
WINSINTF_RECORD_ACTION_T recAction;
|
|
WINSINTF_RECORD_ACTION_T * precAction = &recAction;
|
|
|
|
ZeroMemory(&recAction, sizeof(recAction));
|
|
|
|
BYTE * pName = (BYTE*) WinsAllocMem(pws->dwNameLen + 1);
|
|
if (pName == NULL)
|
|
{
|
|
return ERROR_OUTOFMEMORY;
|
|
}
|
|
|
|
memset(pName, 0, pws->dwNameLen + 1);
|
|
memcpy(pName, pws->szRecordName, pws->dwNameLen);
|
|
|
|
recAction.pName = pName;
|
|
recAction.Cmd_e = WINSINTF_E_QUERY;
|
|
recAction.TypOfRec_e = HIWORD(pws->dwType);
|
|
recAction.fStatic = (pws->dwState & WINSDB_REC_STATIC) ? TRUE : FALSE;
|
|
recAction.pAdd = NULL;
|
|
recAction.NoOfAdds = 0;
|
|
recAction.NameLen = pws->dwNameLen;
|
|
|
|
// get the OwnerId for the mapping
|
|
// have to do this because the OwnerId in the raw data is bogus
|
|
#ifdef WINS_CLIENT_APIS
|
|
err = ::WinsRecordAction(pServer->GetBinding(), &precAction);
|
|
#else
|
|
err = ::WinsRecordAction(&precAction);
|
|
#endif WINS_CLIENT_APIS
|
|
|
|
WinsFreeMem(pName);
|
|
if (err != WINSINTF_SUCCESS )
|
|
{
|
|
return err;
|
|
}
|
|
|
|
WINSINTF_ADD_T WinsAdd;
|
|
|
|
WinsAdd.Len = 4;
|
|
WinsAdd.Type = 0;
|
|
//WinsAdd.IPAdd = m_dwArrayOwner[precAction->OwnerId];
|
|
WinsAdd.IPAdd = (*m_pServerInfoArray)[precAction->OwnerId].m_dwIp;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
err = ::WinsTombstoneDbRecs(pServer->GetBinding(),
|
|
&WinsAdd,
|
|
MinVersNo,
|
|
MaxVersNo);
|
|
#else
|
|
err = ::WinsTombstoneDbRecs(&WinsAdd,
|
|
MinVersNo,
|
|
MaxVersNo);
|
|
#endif
|
|
|
|
return err;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::TombstoneAllRecords()
|
|
Tombstones all records owned by this server
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
DWORD
|
|
CActiveRegistrationsHandler::TombstoneAllRecords(DWORD dwServerIpAddress, ITFSNode * pNode)
|
|
{
|
|
WINSINTF_VERS_NO_T MinVersNo;
|
|
WINSINTF_VERS_NO_T MaxVersNo;
|
|
WINSINTF_ADD_T WinsAdd;
|
|
|
|
SPITFSNode spParentNode;
|
|
pNode->GetParent(&spParentNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spParentNode);
|
|
|
|
DWORD err;
|
|
|
|
CWinsResults winsResults;
|
|
|
|
err = winsResults.Update(pServer->GetBinding());
|
|
if (err != ERROR_SUCCESS)
|
|
return err;
|
|
|
|
MinVersNo.QuadPart = 0;
|
|
|
|
for (UINT i = 0; i < winsResults.NoOfOwners; i++)
|
|
{
|
|
if (winsResults.AddVersMaps[i].Add.IPAdd == dwServerIpAddress)
|
|
{
|
|
MaxVersNo.QuadPart = winsResults.AddVersMaps[i].VersNo.QuadPart;
|
|
break;
|
|
}
|
|
}
|
|
|
|
// build the IP address
|
|
WinsAdd.Len = 4;
|
|
WinsAdd.Type = 0;
|
|
WinsAdd.IPAdd = dwServerIpAddress;
|
|
|
|
#ifdef WINS_CLIENT_APIS
|
|
err = ::WinsTombstoneDbRecs(pServer->GetBinding(),
|
|
&WinsAdd,
|
|
MinVersNo,
|
|
MaxVersNo);
|
|
#else
|
|
err = ::WinsTombstoneDbRecs(&WinsAdd,
|
|
MinVersNo,
|
|
MaxVersNo);
|
|
#endif
|
|
|
|
return err;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::UpdateRecord(ITFSComponent *pComponent,
|
|
WinsRecord *pws,
|
|
int nDelIndex)
|
|
|
|
Called to update the record on the result pane when a records has been
|
|
tombstoned
|
|
Author: v-shubk
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::UpdateRecord(ITFSComponent *pComponent,
|
|
WinsRecord *pws,
|
|
int nDelIndex)
|
|
{
|
|
HRESULT hr = hrOK;
|
|
WINSINTF_RECORD_ACTION_T RecAction;
|
|
PWINSINTF_RECORD_ACTION_T pRecAction;
|
|
PWINSINTF_RECORD_ACTION_T pRecActionRet;
|
|
DWORD dwStatus = ERROR_SUCCESS;
|
|
int nLen;
|
|
BYTE bLast;
|
|
SPITFSNode spNode;
|
|
SPITFSNode spParentNode;
|
|
WinsRecord wsNew;
|
|
HROW hrowDel;
|
|
|
|
pComponent->GetSelectedNode(&spNode);
|
|
|
|
// get it's parent, which happens to be the server node
|
|
spNode->GetParent(&spParentNode);
|
|
|
|
// get the pointer to the server handler
|
|
CWinsServerHandler *pServer = GETHANDLER(CWinsServerHandler, spParentNode);
|
|
|
|
ZeroMemory(&RecAction, sizeof(RecAction));
|
|
|
|
// form the PWINSINTFrecord from the info in WinsRecord
|
|
//RecAction.TypOfRec_e = nType;
|
|
RecAction.Cmd_e = WINSINTF_E_QUERY;
|
|
RecAction.pAdd = NULL;
|
|
RecAction.pName = NULL;
|
|
RecAction.NoOfAdds = 0;
|
|
RecAction.NameLen = nLen = pws->dwNameLen;
|
|
bLast = LOBYTE(LOWORD(pws->dwType));
|
|
|
|
pRecAction = &RecAction;
|
|
|
|
RecAction.pName = (LPBYTE)::WinsAllocMem(nLen + 1);
|
|
if (RecAction.pName == NULL)
|
|
{
|
|
return ERROR_NOT_ENOUGH_MEMORY;
|
|
}
|
|
|
|
// copy the name
|
|
memset(pRecAction->pName, 0, nLen + 1);
|
|
(void)memcpy(pRecAction->pName, pws->szRecordName, nLen);
|
|
|
|
// now query for this particular record
|
|
pRecActionRet = QueryForName(spNode, pRecAction);
|
|
|
|
// if the function is successful, update the listbox
|
|
if (pRecActionRet != NULL)
|
|
{
|
|
// convert PWinsINTF record to WinsRecord so that it can be added to the local storage
|
|
WinsIntfToWinsRecord(pRecActionRet, wsNew);
|
|
if (pRecActionRet->OwnerId < (UINT) m_pServerInfoArray->GetSize())
|
|
wsNew.dwOwner = (*m_pServerInfoArray)[pRecActionRet->OwnerId].m_dwIp;
|
|
|
|
free(pRecActionRet->pName);
|
|
|
|
// delete this particular record and add it back again to the local storage
|
|
CORg(m_pCurrentDatabase->GetHRow(nDelIndex, &hrowDel));
|
|
CORg(m_pCurrentDatabase->DeleteRecord(hrowDel));
|
|
|
|
// add it to database
|
|
m_pCurrentDatabase->AddRecord(&wsNew);
|
|
}
|
|
|
|
Error:
|
|
if (RecAction.pName)
|
|
{
|
|
WinsFreeMem(RecAction.pName);
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::RefreshResults(ITFSNode *pNode)
|
|
Refreshes the result pane of the active registrations node
|
|
---------------------------------------------------------------------------*/
|
|
HRESULT
|
|
CActiveRegistrationsHandler::RefreshResults(ITFSNode *pNode)
|
|
{
|
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
|
|
|
HRESULT hr = hrOK;
|
|
SPITFSNode spNode;
|
|
SPITFSNodeHandler spHandler;
|
|
ITFSQueryObject * pQuery = NULL;
|
|
SPITFSNode spServerNode;
|
|
DWORD dwIP;
|
|
CString strIP ;
|
|
CWinsServerHandler* pServer = NULL;
|
|
CString strMachineName;
|
|
int nCount, pos;
|
|
|
|
// if being loaded
|
|
if (m_spWinsDatabase)
|
|
{
|
|
CORg (m_spWinsDatabase->Stop());
|
|
|
|
DatabaseLoadingCleanup();
|
|
UpdateListboxCount(pNode);
|
|
}
|
|
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
Lock();
|
|
|
|
strMachineName = _T("\\\\") + pServer->GetServerAddress();
|
|
|
|
dwIP = pServer->GetServerIP();
|
|
MakeIPAddress(dwIP, strIP);
|
|
|
|
if (!m_spWinsDatabase)
|
|
{
|
|
CORg(CreateWinsDatabase(strIP, strIP, &m_spWinsDatabase));
|
|
}
|
|
|
|
m_spWinsDatabase->SetApiInfo(
|
|
m_dlgLoadRecords.m_pageOwners.GetOwnerForApi(),
|
|
m_dlgLoadRecords.m_pageIpAddress.GetNameForApi(),
|
|
m_dlgLoadRecords.m_bEnableCache);
|
|
|
|
// start loading records
|
|
CORg (m_spWinsDatabase->Init());
|
|
|
|
UpdateCurrentView(pNode);
|
|
|
|
// update our internal state
|
|
m_winsdbState = WINSDB_LOADING;
|
|
|
|
// update the node's icon
|
|
OnChangeState(pNode);
|
|
|
|
// kick off the background thread to do the timer updates
|
|
pQuery = OnCreateQuery(pNode);
|
|
Assert(pQuery);
|
|
|
|
Verify(StartBackgroundThread(pNode,
|
|
m_spTFSCompData->GetHiddenWnd(),
|
|
pQuery));
|
|
|
|
pQuery->Release();
|
|
|
|
// fill in any record type filter information
|
|
nCount = (int)m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter.GetSize();
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_TYPE);
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_TYPE,
|
|
m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter[pos].dwType,
|
|
m_dlgLoadRecords.m_pageTypes.m_arrayTypeFilter[pos].fShow,
|
|
NULL);
|
|
}
|
|
|
|
// fill in any owner filter information
|
|
nCount = (int)m_dlgLoadRecords.m_pageOwners.m_dwaOwnerFilter.GetSize();
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_OWNER);
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_OWNER,
|
|
m_dlgLoadRecords.m_pageOwners.m_dwaOwnerFilter[pos],
|
|
0,
|
|
NULL);
|
|
}
|
|
|
|
// fill in any ip address filter information
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_IPADDR);
|
|
if (m_dlgLoadRecords.m_pageIpAddress.m_bFilterIpAddr)
|
|
{
|
|
nCount = (int)m_dlgLoadRecords.m_pageIpAddress.m_dwaIPAddrs.GetSize();
|
|
for (pos = 0; pos < nCount; pos++)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_IPADDR,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_dwaIPAddrs[pos],
|
|
m_dlgLoadRecords.m_pageIpAddress.GetIPMaskForFilter(pos),
|
|
NULL);
|
|
}
|
|
}
|
|
|
|
// fill in any name filter information
|
|
m_spWinsDatabase->ClearFilter(WINSDB_FILTER_BY_NAME);
|
|
if (m_dlgLoadRecords.m_pageIpAddress.m_bFilterName)
|
|
{
|
|
m_spWinsDatabase->AddFilter(WINSDB_FILTER_BY_NAME,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_bMatchCase,
|
|
0,
|
|
m_dlgLoadRecords.m_pageIpAddress.m_strName);
|
|
}
|
|
|
|
// start loading records
|
|
CORg (m_spWinsDatabase->Start());
|
|
|
|
BEGIN_WAIT_CURSOR
|
|
|
|
// filter any records that may have been downloaded before we set the
|
|
// filter information (in the case when we had to reload the database).
|
|
// any records that come in after we set the
|
|
// filter info will be filtered correctly.
|
|
m_spWinsDatabase->FilterRecords(WINSDB_FILTER_BY_TYPE, 0,0);
|
|
|
|
END_WAIT_CURSOR
|
|
|
|
// do the initial update of the virutal listbox
|
|
OnHaveData(pNode, 0, QDATA_TIMER);
|
|
|
|
COM_PROTECT_ERROR_LABEL;
|
|
|
|
return hr;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetRecordOwner()
|
|
Gets the owner IP Address for a given record
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
BOOL
|
|
CActiveRegistrationsHandler::GetRecordOwner(ITFSNode * pNode, WinsRecord * pWinsRecord)
|
|
{
|
|
BOOL fSuccess = TRUE;
|
|
SPITFSNode spServerNode;
|
|
pNode->GetParent(&spServerNode);
|
|
|
|
CWinsServerHandler * pServer = GETHANDLER(CWinsServerHandler, spServerNode);
|
|
|
|
CConfiguration config = pServer->GetConfig();
|
|
|
|
if (!config.FSupportsOwnerId())
|
|
{
|
|
// query the server for correct info
|
|
WINSINTF_RECORD_ACTION_T RecAction;
|
|
|
|
ZeroMemory(&RecAction, sizeof(RecAction));
|
|
|
|
//
|
|
// Must have at least enough room for 256 character string,
|
|
// includes the scope name too
|
|
//
|
|
RecAction.pName = (LPBYTE)::WinsAllocMem(257);
|
|
if (RecAction.pName == NULL)
|
|
{
|
|
//return ERROR_NOT_ENOUGH_MEMORY;
|
|
Trace0("GetRecordOwner - WinsAllocMemFailed!!\n");
|
|
return FALSE;
|
|
}
|
|
|
|
// fill in the record action struct
|
|
::memset(RecAction.pName, 0, 257);
|
|
|
|
::memcpy((char *)RecAction.pName,
|
|
(LPCSTR) pWinsRecord->szRecordName,
|
|
pWinsRecord->dwNameLen);
|
|
|
|
RecAction.NameLen = strlen((char *) RecAction.pName);
|
|
|
|
// for name records of type 0x00 or records that somehow have a NULL in the name
|
|
// strlen will return an invalid string length. So, if the length < 16 then set
|
|
// the length to 16.
|
|
// name lengths with scopes will calculate correctly.
|
|
if (RecAction.NameLen < 0x10)
|
|
{
|
|
RecAction.NameLen = 0x10;
|
|
}
|
|
|
|
BOOL fStatic = (pWinsRecord->dwState & WINSDB_REC_STATIC) ? TRUE : FALSE;
|
|
|
|
// now query for the name
|
|
PWINSINTF_RECORD_ACTION_T pRecActionResult = QueryForName(pNode, &RecAction, fStatic);
|
|
|
|
if (pRecActionResult)
|
|
{
|
|
free(pRecActionResult->pName);
|
|
}
|
|
else
|
|
{
|
|
pWinsRecord->dwOwner = INVALID_OWNER_ID;
|
|
}
|
|
}
|
|
|
|
return fSuccess;
|
|
}
|
|
|
|
/*---------------------------------------------------------------------------
|
|
CActiveRegistrationsHandler::GetOwnerInfo()
|
|
Gets the owner info array
|
|
Author: EricDav
|
|
---------------------------------------------------------------------------*/
|
|
void
|
|
CActiveRegistrationsHandler::GetOwnerInfo(CServerInfoArray & serverInfoArray)
|
|
{
|
|
serverInfoArray.RemoveAll();
|
|
|
|
serverInfoArray.Copy(*m_pServerInfoArray);
|
|
}
|
|
|
|
void CActiveRegistrationsHandler::SetLoadedOnce(ITFSNode * pNode)
|
|
{
|
|
if (m_fLoadedOnce)
|
|
return;
|
|
|
|
m_fLoadedOnce = TRUE;
|
|
|
|
// clear the result pane message
|
|
ClearMessage(pNode);
|
|
}
|