windows-nt/Source/XPSP1/NT/base/fs/hsm/cli/cliadmin.cpp
2020-09-26 16:20:57 +08:00

836 lines
29 KiB
C++

/*++
Copyright (c) 2000 Microsoft Corporation
Module Name:
cliadmin.cpp
Abstract:
Implements CLI ADMIN sub-interface
Author:
Ran Kalach [rankala] 3-March-2000
Revision History:
--*/
#include "stdafx.h"
#include "HsmConn.h"
#include "engine.h"
#include "rsstrdef.h"
#include "mstask.h"
static GUID g_nullGuid = GUID_NULL;
// Internal utilities and classes for VOLUME interface
HRESULT DisplayServiceStatus(void);
HRESULT IsHsmInitialized(IN IHsmServer *pHsm);
HRESULT
AdminSet(
IN DWORD RecallLimit,
IN DWORD AdminExempt,
IN DWORD MediaCopies,
IN DWORD Concurrency,
IN PVOID Schedule
)
/*++
Routine Description:
Sets Remote Storage general parameters
Arguments:
RecallLimit - The runaway recall limit to set
AdminExempt - Whether to set administrators exempt for the recall limit
MediaCopies - Number of media copy sets
Concurrency - How many migrate jobs/recalls can be executed concurrently
Schedule - The schedule for the global migration ("Manage") job of all managed volumes
Return Value:
S_OK - If all the parameters are set successfully
Notes:
The scheduling implementation of HSM (in the Engine) allows only one scheduling
for the global Manage job. The scheduling given here overrides any former scheduling.
However, the user can add another scheduling to the same task using the Task Scheduler UI.
Enabling that via HSM, requires changing the CHsmServer::CreateTaskEx implementation
--*/
{
HRESULT hr = S_OK;
WsbTraceIn(OLESTR("AdminSet"), OLESTR(""));
try {
CWsbStringPtr param;
// Verify that input parameters are valid
WsbAffirmHr(ValidateLimitsArg(RecallLimit, IDS_RECALL_LIMIT, HSMADMIN_MIN_RECALL_LIMIT, INVALID_DWORD_ARG));
WsbAffirmHr(ValidateLimitsArg(MediaCopies, IDS_MEDIA_COPIES_PRM, HSMADMIN_MIN_COPY_SETS, HSMADMIN_MAX_COPY_SETS));
WsbAffirmHr(ValidateLimitsArg(Concurrency, IDS_CONCURRENCY_PRM, HSMADMIN_MIN_CONCURRENT_TASKS, INVALID_DWORD_ARG));
// Set parameters, if an error occurs we abort
if ((INVALID_DWORD_ARG != RecallLimit) || (INVALID_DWORD_ARG != AdminExempt)) {
// Need Fsa server and Fsa filter here
CComPtr<IFsaServer> pFsa;
CComPtr<IFsaFilter> pFsaFilter;
WsbAffirmHr(HsmConnectFromId(HSMCONN_TYPE_FSA, g_nullGuid, IID_IFsaServer, (void**)&pFsa));
WsbAffirmHr(pFsa->GetFilter( &pFsaFilter));
// Recall limit
if (INVALID_DWORD_ARG != RecallLimit) {
WsbAffirmHr(pFsaFilter->SetMaxRecalls(RecallLimit));
}
// Admin exempt
if (INVALID_DWORD_ARG != AdminExempt) {
BOOL bAdminExempt = (0 == AdminExempt) ? FALSE : TRUE;
WsbAffirmHr(pFsaFilter->SetAdminExemption(bAdminExempt));
}
}
if ( (INVALID_DWORD_ARG != MediaCopies) || (INVALID_DWORD_ARG != Concurrency) ||
(INVALID_POINTER_ARG != Schedule) ) {
// Need Hsm server
CComPtr<IHsmServer> pHsm;
WsbAffirmHr(HsmConnectFromId(HSMCONN_TYPE_HSM, g_nullGuid, IID_IHsmServer, (void**)&pHsm));
// Concurrency
if (INVALID_DWORD_ARG != Concurrency) {
WsbAffirmHr(pHsm->SetCopyFilesUserLimit(Concurrency));
}
// Media copies
if (INVALID_DWORD_ARG != MediaCopies) {
CComPtr<IHsmStoragePool> pStoragePool;
CComPtr<IWsbIndexedCollection> pCollection;
ULONG count;
// Get the storage pools collection. There should only be one member.
WsbAffirmHr(pHsm->GetStoragePools(&pCollection));
WsbAffirmHr(pCollection->GetEntries(&count));
WsbAffirm(1 == count, E_FAIL);
WsbAffirmHr(pCollection->At(0, IID_IHsmStoragePool, (void **)&pStoragePool));
WsbAffirmHr(pStoragePool->SetNumMediaCopies((USHORT)MediaCopies));
}
// Scheduling
if (INVALID_POINTER_ARG != Schedule) {
CWsbStringPtr taskName, taskComment;
TASK_TRIGGER_TYPE taskType;
PHSM_JOB_SCHEDULE pSchedule = (PHSM_JOB_SCHEDULE)Schedule;
SYSTEMTIME runTime;
DWORD runOccurrence;
// Set default valuess
GetSystemTime(&runTime);
runOccurrence = 0;
// Set input
switch (pSchedule->Frequency) {
case Daily:
taskType = TASK_TIME_TRIGGER_DAILY;
runTime = pSchedule->Parameters.Daily.Time;
runOccurrence = pSchedule->Parameters.Daily.Occurrence;
break;
case Weekly:
taskType = TASK_TIME_TRIGGER_WEEKLY;
runTime = pSchedule->Parameters.Weekly.Time;
runOccurrence = pSchedule->Parameters.Weekly.Occurrence;
break;
case Monthly:
taskType = TASK_TIME_TRIGGER_MONTHLYDATE;
runTime = pSchedule->Parameters.Monthly.Time;
break;
case Once:
taskType = TASK_TIME_TRIGGER_ONCE;
runTime = pSchedule->Parameters.Once.Time;
break;
case WhenIdle:
taskType = TASK_EVENT_TRIGGER_ON_IDLE;
runOccurrence = pSchedule->Parameters.WhenIdle.Occurrence;
break;
case SystemStartup:
taskType = TASK_EVENT_TRIGGER_AT_SYSTEMSTART;
break;
case Login:
taskType = TASK_EVENT_TRIGGER_AT_LOGON;
break;
default:
WsbThrow(E_INVALIDARG);
}
// Create the task with the new scheduling
// Note: Task parameters should not be localized - this is a parameter for RsLaunch.exe
WsbAffirmHr(WsbGetResourceString(IDS_HSM_SCHED_TASK_TITLE, &taskName));
WsbAffirmHr(WsbGetResourceString(IDS_HSM_SCHED_COMMENT, &taskComment));
WsbAffirmHr(pHsm->CreateTaskEx(taskName, L"run manage", taskComment,
taskType, runTime, runOccurrence, TRUE));
}
}
} WsbCatch(hr);
WsbTraceOut(OLESTR("AdminSet"), OLESTR("hr = <%ls>"), WsbHrAsString(hr));
return hr;
}
// Local structure for AdminShow
typedef struct _FSA_VOLUME_DATA {
WCHAR *Name;
BOOL Managed;
} FSA_VOLUME_DATA, *PFSA_VOLUME_DATA;
#define DATA_ALLOC_SIZE 10
HRESULT
AdminShow(
IN BOOL RecallLimit,
IN BOOL AdminExempt,
IN BOOL MediaCopies,
IN BOOL Concurrency,
IN BOOL Schedule,
IN BOOL General,
IN BOOL Manageables,
IN BOOL Managed,
IN BOOL Media
)
/*++
Routine Description:
Shows (prints to stdout) Remote Storage general parameters
Arguments:
RecallLimit - The runaway recall limit
AdminExempt - Whether administrators are exempt from the recall limit
MediaCopies - Number of media copy sets
Concurrency - How many migrate jobs/recalls can be executed concurrently
Schedule - The schedule for the global migration ("Manage") job of all managed volumes
General - General information: version, status, number of volumes managed,
number of tape cartridges used, data in remote storage
Manageables - List of volumes that may be managed by HSM
Managed - List of volumes that are managed by HSM
Media - List of medias that are allocated to HSM
Return Value:
S_OK - If all the required parameters are printed successfully
Notes:
The schedule is printed in a form of a list (like the volume list), not like a single parameter.
The reason is that a user can specify several schedules for the global Manage job.
--*/
{
HRESULT hr = S_OK;
// Volume saved data
PFSA_VOLUME_DATA pVolumesData = NULL;
ULONG volDataSize = 0;
// Media save data
BSTR* pMediasData = NULL;
ULONG mediaDataSize = 0;
CComPtr<IWsbDb> pDb;
CComPtr<IWsbDbSession> pDbSession;
WsbTraceIn(OLESTR("AdminShow"), OLESTR(""));
try {
CComPtr<IFsaServer> pFsa;
CComPtr<IHsmServer> pHsm;
CWsbStringPtr param;
CWsbStringPtr data;
WCHAR longData[100];
LPVOID pTemp;
// Volume data
LONGLONG dataInStorage = 0;
ULONG manageableCount = 0;
ULONG managedCount = 0;
// Media data
ULONG mediaAllocated = 0;
// Get required HSM servers
if (RecallLimit || AdminExempt || Manageables || Managed || General) {
// Need Fsa server
hr = HsmConnectFromId(HSMCONN_TYPE_FSA, g_nullGuid, IID_IFsaServer, (void**)&pFsa);
if (S_OK != hr) {
// Just print status before aborting
if (General) {
DisplayServiceStatus();
}
}
WsbAffirmHr(hr);
}
if (MediaCopies || Concurrency || General || Media) {
// Need Hsm (Engine) server
hr = HsmConnectFromId(HSMCONN_TYPE_HSM, g_nullGuid, IID_IHsmServer, (void**)&pHsm);
if (S_OK != hr) {
// Just print status before aborting
if (General) {
DisplayServiceStatus();
}
}
WsbAffirmHr(hr);
}
//
// Get basic information required according to the input settings
//
// Volumes data
if (General || Manageables || Managed) {
// Need to collect volumes information
CComPtr<IWsbEnum> pEnum;
CComPtr<IFsaResource> pResource;
HRESULT hrEnum;
BOOL bManaged;
LONGLONG totalSpace = 0;
LONGLONG freeSpace = 0;
LONGLONG premigrated = 0;
LONGLONG truncated = 0;
LONGLONG totalPremigrated = 0;
LONGLONG totalTruncated = 0;
WsbAffirmHr(pFsa->EnumResources(&pEnum));
hrEnum = pEnum->First(IID_IFsaResource, (void**)&pResource);
WsbAffirm((S_OK == hrEnum) || (WSB_E_NOTFOUND == hrEnum), hrEnum);
if (Manageables || Managed) {
volDataSize = DATA_ALLOC_SIZE;
pVolumesData = (PFSA_VOLUME_DATA)WsbAlloc(volDataSize * sizeof(FSA_VOLUME_DATA));
WsbAffirm(0 != pVolumesData, E_OUTOFMEMORY);
}
while(S_OK == hrEnum) {
// Don't count or display unavailable volumes
if (S_OK != pResource->IsAvailable()) {
goto skip_volume;
}
bManaged = (pResource->IsManaged() == S_OK);
if (Manageables) {
if (volDataSize == manageableCount) {
volDataSize += DATA_ALLOC_SIZE;
pTemp = WsbRealloc(pVolumesData, volDataSize * sizeof(FSA_VOLUME_DATA));
WsbAffirm(0 != pTemp, E_OUTOFMEMORY);
pVolumesData = (PFSA_VOLUME_DATA)pTemp;
}
pVolumesData[manageableCount].Name = NULL;
WsbAffirmHr(CliGetVolumeDisplayName(pResource, &(pVolumesData[manageableCount].Name)));
pVolumesData[manageableCount].Managed = bManaged;
}
manageableCount++;
if(bManaged) {
if (General) {
WsbAffirmHr(pResource->GetSizes(&totalSpace, &freeSpace, &premigrated, &truncated));
totalPremigrated += premigrated;
totalTruncated += truncated;
}
if (Managed && (!Manageables)) {
// Collect data only for managed volumes
if (volDataSize == managedCount) {
volDataSize += DATA_ALLOC_SIZE;
pTemp = WsbRealloc(pVolumesData, volDataSize * sizeof(FSA_VOLUME_DATA));
WsbAffirm(0 != pTemp, E_OUTOFMEMORY);
pVolumesData = (PFSA_VOLUME_DATA)pTemp;
}
pVolumesData[managedCount].Name = NULL;
WsbAffirmHr(CliGetVolumeDisplayName(pResource, &(pVolumesData[managedCount].Name)));
pVolumesData[managedCount].Managed = TRUE;
}
managedCount++;
}
skip_volume:
// Prepare for next iteration
pResource = 0;
hrEnum = pEnum->Next( IID_IFsaResource, (void**)&pResource );
}
if (Manageables) {
volDataSize = manageableCount;
} else if (Managed) {
volDataSize = managedCount;
}
if (General) {
dataInStorage = totalPremigrated + totalTruncated;
}
}
// Medias data
if (General || Media) {
CComPtr<IMediaInfo> pMediaInfo;
GUID mediaSubsystemId;
CComPtr<IRmsServer> pRms;
CComPtr<IRmsCartridge> pRmsCart;
HRESULT hrFind;
WsbAffirmHr(pHsm->GetHsmMediaMgr(&pRms));
WsbAffirmHr(pHsm->GetSegmentDb(&pDb));
WsbAffirmHr(pDb->Open(&pDbSession));
WsbAffirmHr(pDb->GetEntity(pDbSession, HSM_MEDIA_INFO_REC_TYPE, IID_IMediaInfo, (void**)&pMediaInfo));
if (Media) {
mediaDataSize = DATA_ALLOC_SIZE;
pMediasData = (BSTR *)WsbAlloc(mediaDataSize * sizeof(BSTR));
WsbAffirm(0 != mediaDataSize, E_OUTOFMEMORY);
}
for (hr = pMediaInfo->First(); S_OK == hr; hr = pMediaInfo->Next()) {
WsbAffirmHr(pMediaInfo->GetMediaSubsystemId(&mediaSubsystemId));
hrFind = pRms->FindCartridgeById(mediaSubsystemId, &pRmsCart);
if (S_OK == hrFind) { // Otherwise, the media is not valid anymore, it could have been deallocated
if (Media) {
if (mediaDataSize == mediaAllocated) {
mediaDataSize += DATA_ALLOC_SIZE;
pTemp = WsbRealloc(pMediasData, mediaDataSize * sizeof(BSTR));
WsbAffirm(0 != pTemp, E_OUTOFMEMORY);
pMediasData = (BSTR *)pTemp;
}
pMediasData[mediaAllocated] = NULL;
WsbAffirmHr(pRmsCart->GetName(&(pMediasData[mediaAllocated])));
if ( (NULL == pMediasData[mediaAllocated]) ||
(0 == wcscmp(pMediasData[mediaAllocated], OLESTR(""))) ) {
// Try decsription
if (NULL != pMediasData[mediaAllocated]) {
WsbFreeString(pMediasData[mediaAllocated]);
}
WsbAffirmHr(pRmsCart->GetDescription(&(pMediasData[mediaAllocated])));
}
}
mediaAllocated++;
pRmsCart = 0;
}
}
if (Media) {
mediaDataSize = mediaAllocated;
}
hr = S_OK;
if(pDb) {
pDb->Close(pDbSession);
pDb = 0;
}
}
//
// Print parameters
//
// General parameters
if (General) {
WsbTraceAndPrint(CLI_MESSAGE_GENERAL_PARMS, NULL);
// Status
WsbAffirmHr(DisplayServiceStatus());
// Manageable && Managed
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_NOF_MANAGEABLES));
swprintf(longData, OLESTR("%lu"), manageableCount);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_NOF_MANAGED));
swprintf(longData, OLESTR("%lu"), managedCount);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
// Tapes
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_NOF_CARTRIDGES));
swprintf(longData, OLESTR("%lu"), mediaAllocated);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
// Data in RS
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_REMOTE_DATA));
WsbAffirmHr(ShortSizeFormat64(dataInStorage, longData));
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
// Version
{
CComPtr<IWsbServer> pWsbHsm;
CWsbStringPtr ntProductVersionHsm;
ULONG ntProductBuildHsm;
ULONG buildVersionHsm;
WsbAffirmHr(pHsm->QueryInterface(IID_IWsbServer, (void **)&pWsbHsm));
WsbAffirmHr(pWsbHsm->GetNtProductBuild(&ntProductBuildHsm));
WsbAffirmHr(pWsbHsm->GetNtProductVersion(&ntProductVersionHsm, 0));
WsbAffirmHr(pWsbHsm->GetBuildVersion(&buildVersionHsm));
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_HSM_VERSION));
WsbAffirmHr(data.Realloc(wcslen(ntProductVersionHsm) + 30));
swprintf(data, L"%ls.%d [%ls]", (WCHAR*)ntProductVersionHsm, ntProductBuildHsm, RsBuildVersionAsString(buildVersionHsm));
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, (WCHAR *)data, NULL);
}
}
// Manageable volumes
if (Manageables) {
WsbTraceAndPrint(CLI_MESSAGE_MANAGEABLE_VOLS, NULL);
for (ULONG i=0; i<volDataSize; i++) {
if (pVolumesData[i].Name) {
WsbTraceAndPrint(CLI_MESSAGE_VALUE_DISPLAY, pVolumesData[i].Name, NULL);
}
}
}
// Managed volumes
if (Managed) {
WsbTraceAndPrint(CLI_MESSAGE_MANAGED_VOLS, NULL);
for (ULONG i=0; i<volDataSize; i++) {
if (pVolumesData[i].Name && pVolumesData[i].Managed) {
WsbTraceAndPrint(CLI_MESSAGE_VALUE_DISPLAY, pVolumesData[i].Name, NULL);
}
}
}
// Allocated Medias
if (Media) {
WsbTraceAndPrint(CLI_MESSAGE_MEDIAS, NULL);
for (ULONG i=0; i<mediaDataSize; i++) {
if (NULL != pMediasData[i]) {
WsbTraceAndPrint(CLI_MESSAGE_VALUE_DISPLAY, (WCHAR *)pMediasData[i], NULL);
}
}
}
// Schedule
if (Schedule) {
// Use Task Scheduler objects to get the data
CComPtr<ISchedulingAgent> pSchedAgent;
CComPtr<ITask> pTask;
CWsbStringPtr manageJobName;
// Initialize scheduling agent
WsbAffirmHr(CoCreateInstance(CLSID_CSchedulingAgent, 0, CLSCTX_SERVER, IID_ISchedulingAgent, (void **)&pSchedAgent));
pSchedAgent->SetTargetComputer(NULL); // local machine
// Get the relevant task
WsbAffirmHr(WsbGetResourceString(IDS_HSM_SCHED_TASK_TITLE, &manageJobName));
hr = pSchedAgent->Activate(manageJobName, IID_ITask, (IUnknown**)&pTask);
if (E_INVALIDARG == hr) {
// Print no scheduling message (Manage job is not found as a scheduled task)
WsbTraceAndPrint(CLI_MESSAGE_NO_SCHEDULING, NULL);
hr = S_OK;
} else if (S_OK == hr) {
// Get scheduling strings and print
WORD wTriggerCount;
WsbAffirmHr(pTask->GetTriggerCount(&wTriggerCount));
if (wTriggerCount == 0) {
WsbTraceAndPrint(CLI_MESSAGE_NO_SCHEDULING, NULL);
} else {
WsbTraceAndPrint(CLI_MESSAGE_SCHEDULING_LIST, NULL);
}
for (WORD triggerIndex = 0; triggerIndex < wTriggerCount; triggerIndex++) {
WCHAR *pTriggerString = NULL;
WsbAffirmHr(pTask->GetTriggerString(triggerIndex, &pTriggerString));
// Print
WsbTraceAndPrint(CLI_MESSAGE_VALUE_DISPLAY, pTriggerString, NULL);
CoTaskMemFree(pTriggerString);
}
} else {
WsbAffirmHr(hr);
}
}
// Limits and Media Copies
if (RecallLimit || AdminExempt) {
// Need Fsa filter here
CComPtr<IFsaFilter> pFsaFilter;
WsbAffirmHr(pFsa->GetFilter(&pFsaFilter));
if (RecallLimit) {
ULONG maxRecalls;
WsbAffirmHr(pFsaFilter->GetMaxRecalls(&maxRecalls));
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_RECALL_LIMIT));
swprintf(longData, OLESTR("%lu"), maxRecalls);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
}
if (AdminExempt) {
BOOL adminExempt;
WsbAffirmHr(pFsaFilter->GetAdminExemption(&adminExempt));
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_ADMIN_EXEMPT));
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, WsbBoolAsString(adminExempt), NULL);
}
}
if (Concurrency) {
ULONG concurrentTasks;
WsbAffirmHr(pHsm->GetCopyFilesUserLimit(&concurrentTasks));
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_CONCURRENCY));
swprintf(longData, OLESTR("%lu"), concurrentTasks);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
}
if (MediaCopies) {
CComPtr<IHsmStoragePool> pStoragePool;
CComPtr<IWsbIndexedCollection> pCollection;
ULONG count;
USHORT numCopies;
// Get the storage pools collection. There should only be one member.
WsbAffirmHr(pHsm->GetStoragePools(&pCollection));
WsbAffirmHr(pCollection->GetEntries(&count));
WsbAffirm(1 == count, E_FAIL);
WsbAffirmHr(pCollection->At(0, IID_IHsmStoragePool, (void **)&pStoragePool));
WsbAffirmHr(pStoragePool->GetNumMediaCopies(&numCopies));
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_MEDIA_COPIES));
swprintf(longData, OLESTR("%ld"), (int)numCopies);
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, longData, NULL);
}
} WsbCatchAndDo(hr,
if(pDb) {
pDb->Close(pDbSession);
pDb = 0;
}
);
// Free stored data
if (pVolumesData) {
for (ULONG i=0; i<volDataSize; i++) {
if (pVolumesData[i].Name) {
WsbFree(pVolumesData[i].Name);
}
}
WsbFree(pVolumesData);
pVolumesData = NULL;
}
if (pMediasData) {
for (ULONG i=0; i<mediaDataSize; i++) {
if (NULL != pMediasData[i]) {
WsbFreeString(pMediasData[i]);
}
}
WsbFree(pMediasData);
pMediasData = NULL;
}
WsbTraceOut(OLESTR("AdminShow"), OLESTR("hr = <%ls>"), WsbHrAsString(hr));
return hr;
}
//
// Internal utilities
//
HRESULT DisplayServiceStatus(void)
/*++
Routine Description:
Displays HSM service status.
Arguments:
None
Return Value:
S_OK - If status is retrieved and displayed succeessfully
Notes:
The function handle cases such as the service not runnig, pending, not initialized, etc.
--*/
{
HRESULT hr = S_OK;
WsbTraceIn(OLESTR("DisplayServiceStatus"), OLESTR(""));
try {
CWsbStringPtr param, data;
ULONG statusId = INVALID_DWORD_ARG;
DWORD serviceStatus;
HRESULT hrService;
hrService = WsbGetServiceStatus(NULL, APPID_RemoteStorageEngine, &serviceStatus);
if (S_OK != hrService) {
// HSM service not registered at all
WsbTrace(OLESTR("DisplayServiceStatus: Got hr = <%ls> from WsbGetServiceStatus\n"), WsbHrAsString(hrService));
statusId = IDS_SERVICE_STATUS_NOT_REGISTERED;
} else {
if (SERVICE_RUNNING == serviceStatus) {
CComPtr<IHsmServer> pHsm;
HRESULT hrSetup;
WsbAffirmHr(HsmConnectFromId(HSMCONN_TYPE_HSM, g_nullGuid, IID_IHsmServer, (void**)&pHsm));
hrSetup = IsHsmInitialized(pHsm);
if (S_FALSE == hrSetup) {
// HSM running but no initialized yet (Startup Wizard was not completed yet)
statusId = IDS_SERVICE_STATUS_NOT_SETUP;
} else if (S_OK == hrSetup) {
// Service is running, life is good
statusId = IDS_SERVICE_STATUS_RUNNING;
} else {
// Unexpected error
WsbAffirmHr(hrSetup);
}
} else {
// Service is not running, set exact string according to status
switch(serviceStatus) {
case SERVICE_STOPPED:
statusId = IDS_SERVICE_STATUS_STOPPED;
break;
case SERVICE_START_PENDING:
statusId = IDS_SERVICE_STATUS_START_PENDING;
break;
case SERVICE_STOP_PENDING:
statusId = IDS_SERVICE_STATUS_STOP_PENDING;
break;
case SERVICE_CONTINUE_PENDING:
statusId = IDS_SERVICE_STATUS_CONTINUE_PENDING;
break;
case SERVICE_PAUSE_PENDING:
statusId = IDS_SERVICE_STATUS_PAUSE_PENDING;
break;
case SERVICE_PAUSED:
statusId = IDS_SERVICE_STATUS_PAUSED;
break;
default:
WsbThrow(E_FAIL);
}
}
}
WsbAffirm(INVALID_DWORD_ARG != statusId, E_UNEXPECTED)
WsbAffirmHr(param.LoadFromRsc(g_hInstance, IDS_HSM_STATUS));
WsbAffirmHr(data.LoadFromRsc(g_hInstance, statusId));
WsbTraceAndPrint(CLI_MESSAGE_PARAM_DISPLAY, (WCHAR *)param, (WCHAR *)data, NULL);
} WsbCatch(hr);
WsbTraceOut(OLESTR("DisplayServiceStatus"), OLESTR("hr = <%ls>"), WsbHrAsString(hr));
return (hr);
}
HRESULT IsHsmInitialized(IN IHsmServer *pHsm)
/*++
Routine Description:
Check if HSM is initialized, i.e. if Startup wizard was completed successfully
Arguments:
pHsm - The HSM server to check with
Return Value:
S_OK - HSM initialized
S_FALSE - HSM not initialized
--*/
{
HRESULT hr = S_FALSE;
WsbTraceIn(OLESTR("IsHsmInitialized"), OLESTR(""));
try {
GUID guid;
CWsbBstrPtr poolName;
CComPtr<IWsbIndexedCollection> pCollection;
ULONG count;
CComPtr<IHsmStoragePool> pPool;
WsbAffirmHr(pHsm->GetStoragePools(&pCollection));
WsbAffirmHr(pCollection->GetEntries(&count));
WsbAffirm(1 == count, E_FAIL);
WsbAffirmHr(pCollection->At(0, IID_IHsmStoragePool, (void **)&pPool));
WsbAffirmHr(pPool->GetMediaSet(&guid, &poolName));
if(! IsEqualGUID(guid, GUID_NULL)) {
hr = S_OK;
}
} WsbCatch(hr);
WsbTraceOut(OLESTR("IsHsmInitialized"), OLESTR("hr = <%ls>"), WsbHrAsString(hr));
return (hr);
}
HRESULT AdminJob(IN BOOL Enable)
/*++
Routine Description:
Enable/Disable HSM jobs
Arguments:
None
Return Value:
S_OK - Success
HSM_E_DISABLE_RUNNING_JOBS - Returned by Engine when trying to disbale jobs
while jobs are running
Other - Other unexpected error
--*/
{
HRESULT hr = S_FALSE;
WsbTraceIn(OLESTR("AdminJob"), OLESTR(""));
try {
CComPtr<IHsmServer> pHsm;
WsbAffirmHr(HsmConnectFromId(HSMCONN_TYPE_HSM, g_nullGuid, IID_IHsmServer, (void**)&pHsm));
if (Enable) {
hr = pHsm->EnableAllJobs();
} else {
hr = pHsm->DisableAllJobs();
}
} WsbCatch(hr);
WsbTraceOut(OLESTR("AdminJob"), OLESTR("hr = <%ls>"), WsbHrAsString(hr));
return (hr);
}