506 lines
14 KiB
C++
506 lines
14 KiB
C++
|
/****************************************************************************
|
||
|
Copyright information : Copyright (c) 1998-1999 Microsoft Corporation
|
||
|
File Name : wcmain.cpp
|
||
|
Project Name : WMI Command Line
|
||
|
Author Name : Ch. Sriramachandramurthy
|
||
|
Date of Creation (dd/mm/yy) : 27th-September-2000
|
||
|
Version Number : 1.0
|
||
|
Brief Description : The _tmain function is the entry point of the
|
||
|
WMICli program.
|
||
|
Revision History :
|
||
|
Last Modified by :Biplab Mistry
|
||
|
Last Modified date :4/11/00
|
||
|
****************************************************************************/
|
||
|
|
||
|
// wcmain.cpp :main function implementation file
|
||
|
#include "Precomp.h"
|
||
|
|
||
|
#include "CommandSwitches.h"
|
||
|
#include "GlobalSwitches.h"
|
||
|
#include "HelpInfo.h"
|
||
|
#include "ErrorLog.h"
|
||
|
#include "ParsedInfo.h"
|
||
|
#include "CmdTokenizer.h"
|
||
|
#include "CmdAlias.h"
|
||
|
#include "ParserEngine.h"
|
||
|
#include "ExecEngine.h"
|
||
|
#include "ErrorInfo.h"
|
||
|
#include "WmiCliXMLLog.h"
|
||
|
#include "FormatEngine.h"
|
||
|
#include "WmiCmdLn.h"
|
||
|
|
||
|
CWMICommandLine g_wmiCmd;
|
||
|
_TCHAR* g_pszBuffer = NULL;
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :_tmain
|
||
|
Synopsis :This function takes the error code as input and return
|
||
|
an error string
|
||
|
Type :Member Function
|
||
|
Input parameters :
|
||
|
argc :argument count
|
||
|
argv :Pointer to string array storing command line arguments
|
||
|
Output parameters :None
|
||
|
Return Type :Integer
|
||
|
Global Variables :None
|
||
|
Calling Syntax :
|
||
|
Calls :CWMICommandLine::Initialize,
|
||
|
CWMICommandLine::UnInitialize,
|
||
|
CFormatEngine::DisplayResults,
|
||
|
CWMICommandLine::ProcessCommandAndDisplayResults
|
||
|
|
||
|
Called by :None
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
__cdecl _tmain(WMICLIINT argc, _TCHAR **argv)
|
||
|
{
|
||
|
SESSIONRETCODE ssnRetCode = SESSION_SUCCESS;
|
||
|
BOOL bFileEmpty = FALSE;
|
||
|
BOOL bIndirectionInput = FALSE;
|
||
|
FILE *fpInputFile = NULL;
|
||
|
WMICLIUINT uErrLevel = 0;
|
||
|
|
||
|
try
|
||
|
{
|
||
|
_bstr_t bstrBuf;
|
||
|
|
||
|
// Initailize the CWMICommandLine object.
|
||
|
if (g_wmiCmd.Initialize())
|
||
|
{
|
||
|
HANDLE hStd=GetStdHandle(STD_INPUT_HANDLE);
|
||
|
|
||
|
if(hStd != (HANDLE)0x00000003 && hStd != INVALID_HANDLE_VALUE &&
|
||
|
hStd != (HANDLE)0x0000000f)
|
||
|
{
|
||
|
if (!(g_wmiCmd.ReadXMLOrBatchFile(hStd)) ||
|
||
|
(fpInputFile = _tfopen(TEMP_BATCH_FILE, _T("r"))) == NULL)
|
||
|
{
|
||
|
g_wmiCmd.SetSessionErrorLevel(SESSION_ERROR);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
return uErrLevel;
|
||
|
}
|
||
|
bIndirectionInput = TRUE;
|
||
|
}
|
||
|
// If no command line arguments are specified.
|
||
|
if (argc == 1)
|
||
|
{
|
||
|
// Allocate memory for the g_pszBuffer
|
||
|
g_pszBuffer = new _TCHAR[MAX_BUFFER];
|
||
|
|
||
|
// If memory allocation successfull
|
||
|
if (g_pszBuffer)
|
||
|
{
|
||
|
while (TRUE)
|
||
|
{
|
||
|
OUTPUTSPEC opsOutOpt = g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendOption(TRUE);
|
||
|
OUTPUTSPEC opsSavedOutOpt = opsOutOpt;
|
||
|
CHString chsSavedOutFileName;
|
||
|
if ( opsSavedOutOpt == FILEOUTPUT )
|
||
|
chsSavedOutFileName =
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendFileName(TRUE);
|
||
|
|
||
|
// Make propmt to be diplayed to stdout.
|
||
|
if ( opsOutOpt != STDOUT )
|
||
|
{
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendOption(STDOUT, TRUE);
|
||
|
}
|
||
|
|
||
|
// Preserve append file pointer.
|
||
|
FILE* fpAppend =
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendFilePointer(FALSE);
|
||
|
// Set append file pointer = null.
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFilePointer(NULL, FALSE);
|
||
|
|
||
|
// Display the prompt;
|
||
|
bstrBuf = _bstr_t(EXEC_NAME);
|
||
|
bstrBuf += _bstr_t(":");
|
||
|
bstrBuf += _bstr_t(g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().GetRole());
|
||
|
bstrBuf += _bstr_t(">");
|
||
|
DisplayMessage(bstrBuf, CP_OEMCP, FALSE, FALSE);
|
||
|
|
||
|
// To handle Ctrl+C at propmt, Start accepting command
|
||
|
g_wmiCmd.SetAcceptCommand(TRUE);
|
||
|
|
||
|
// To handle batch input from file.
|
||
|
_TCHAR *pBuf = NULL;
|
||
|
while(TRUE)
|
||
|
{
|
||
|
if ( bIndirectionInput == TRUE )
|
||
|
pBuf = _fgetts(g_pszBuffer, MAX_BUFFER-1,
|
||
|
fpInputFile);
|
||
|
else
|
||
|
pBuf = _fgetts(g_pszBuffer, MAX_BUFFER-1, stdin);
|
||
|
|
||
|
if(pBuf != NULL)
|
||
|
{
|
||
|
if ( bIndirectionInput == TRUE )
|
||
|
{
|
||
|
DisplayMessage(g_pszBuffer, CP_OEMCP,
|
||
|
FALSE, FALSE);
|
||
|
}
|
||
|
LONG lInStrLen = lstrlen(g_pszBuffer);
|
||
|
if(g_pszBuffer[lInStrLen - 1] == _T('\n'))
|
||
|
g_pszBuffer[lInStrLen - 1] = _T('\0');
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// Indicates end of file
|
||
|
if (pBuf == NULL)
|
||
|
{
|
||
|
// Set the bFileEmpty flag to TRUE
|
||
|
bFileEmpty = TRUE;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
// To handle Ctrl+C at propmt, End accepting command
|
||
|
// and start of executing command
|
||
|
g_wmiCmd.SetAcceptCommand(FALSE);
|
||
|
|
||
|
// Set append file pointer = saved.
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFilePointer(fpAppend, FALSE);
|
||
|
|
||
|
// Redirect the output back to file specified.
|
||
|
if ( opsOutOpt != STDOUT )
|
||
|
{
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendOption(opsOutOpt, TRUE);
|
||
|
}
|
||
|
|
||
|
// Set the error level to success.
|
||
|
g_wmiCmd.SetSessionErrorLevel(SESSION_SUCCESS);
|
||
|
|
||
|
// If all the commands in the batch file got executed.
|
||
|
if (bFileEmpty)
|
||
|
{
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// Set Break Event to False
|
||
|
g_wmiCmd.SetBreakEvent(FALSE);
|
||
|
|
||
|
// Clear the clipboard.
|
||
|
g_wmiCmd.EmptyClipBoardBuffer();
|
||
|
|
||
|
// Process the command and display results.
|
||
|
ssnRetCode = g_wmiCmd.ProcessCommandAndDisplayResults
|
||
|
(g_pszBuffer);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
|
||
|
// Break the loop if "QUIT" keyword is keyed-in.
|
||
|
if(ssnRetCode == SESSION_QUIT)
|
||
|
{
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
opsOutOpt = g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendOption(TRUE);
|
||
|
|
||
|
if ( opsOutOpt == CLIPBOARD )
|
||
|
CopyToClipBoard(g_wmiCmd.GetClipBoardBuffer());
|
||
|
|
||
|
if ( ( opsOutOpt != FILEOUTPUT &&
|
||
|
CloseOutputFile() == FALSE ) ||
|
||
|
CloseAppendFile() == FALSE )
|
||
|
{
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
if ( g_wmiCmd.GetParsedInfoObject().
|
||
|
GetCmdSwitchesObject().
|
||
|
GetOutputSwitchFlag() == TRUE )
|
||
|
{
|
||
|
if ( opsOutOpt == FILEOUTPUT &&
|
||
|
CloseOutputFile() == FALSE )
|
||
|
{
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetCmdSwitchesObject().
|
||
|
SetOutputSwitchFlag(FALSE);
|
||
|
|
||
|
if ( opsOutOpt == FILEOUTPUT )
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFileName(NULL, TRUE);
|
||
|
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendOption(opsSavedOutOpt
|
||
|
, TRUE);
|
||
|
|
||
|
if ( opsSavedOutOpt == FILEOUTPUT )
|
||
|
g_wmiCmd.GetParsedInfoObject().
|
||
|
GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFileName(
|
||
|
_bstr_t((LPCWSTR)chsSavedOutFileName),
|
||
|
TRUE);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
ssnRetCode = SESSION_ERROR;
|
||
|
g_wmiCmd.GetParsedInfoObject().GetCmdSwitchesObject().
|
||
|
SetErrataCode(OUT_OF_MEMORY);
|
||
|
g_wmiCmd.SetSessionErrorLevel(ssnRetCode);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
}
|
||
|
}
|
||
|
// If command line arguments are specified.
|
||
|
else
|
||
|
{
|
||
|
// Obtain the command line string
|
||
|
g_pszBuffer = GetCommandLine();
|
||
|
if (g_pszBuffer != NULL)
|
||
|
{
|
||
|
// Set the error level to success.
|
||
|
g_wmiCmd.SetSessionErrorLevel(SESSION_SUCCESS);
|
||
|
|
||
|
// Process the command and display results.
|
||
|
while( *(++g_pszBuffer) != _T(' '));
|
||
|
ssnRetCode = g_wmiCmd.ProcessCommandAndDisplayResults(g_pszBuffer);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// Call the uninitialize function of the CWMICommandLine object.
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
|
||
|
if ( bIndirectionInput == TRUE )
|
||
|
{
|
||
|
fclose(fpInputFile);
|
||
|
DeleteFile(TEMP_BATCH_FILE);
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
ssnRetCode = SESSION_ERROR;
|
||
|
|
||
|
// If COM error.
|
||
|
if (g_wmiCmd.GetParsedInfoObject().
|
||
|
GetCmdSwitchesObject().GetCOMError())
|
||
|
{
|
||
|
g_wmiCmd.GetFormatObject().
|
||
|
DisplayResults(g_wmiCmd.GetParsedInfoObject());
|
||
|
}
|
||
|
g_wmiCmd.SetSessionErrorLevel(ssnRetCode);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
}
|
||
|
}
|
||
|
catch(...)
|
||
|
{
|
||
|
ssnRetCode = SESSION_ERROR;
|
||
|
g_wmiCmd.GetParsedInfoObject().GetCmdSwitchesObject().
|
||
|
SetErrataCode(UNKNOWN_ERROR);
|
||
|
g_wmiCmd.SetSessionErrorLevel(ssnRetCode);
|
||
|
DisplayString(IDS_E_WMIC_UNKNOWN_ERROR, CP_OEMCP,
|
||
|
NULL, TRUE, TRUE);
|
||
|
uErrLevel = g_wmiCmd.GetSessionErrorLevel();
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
if ( bIndirectionInput == TRUE )
|
||
|
{
|
||
|
fclose(fpInputFile);
|
||
|
DeleteFile(TEMP_BATCH_FILE);
|
||
|
}
|
||
|
}
|
||
|
return uErrLevel;
|
||
|
}
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :CtrlHandler
|
||
|
Synopsis :Handler routine to handle CTRL + C so as free
|
||
|
the memory allocated during the program execution.
|
||
|
Type :Global Function
|
||
|
Input parameters :
|
||
|
fdwCtrlType - control handler type
|
||
|
Output parameters :None
|
||
|
Return Type :BOOL
|
||
|
Global Variables :
|
||
|
g_pszBuffer - command buffer
|
||
|
g_wmiCmd - wmi command line object
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
BOOL CtrlHandler(DWORD fdwCtrlType)
|
||
|
{
|
||
|
BOOL bRet = FALSE;
|
||
|
switch (fdwCtrlType)
|
||
|
{
|
||
|
case CTRL_C_EVENT:
|
||
|
// if at command propmt
|
||
|
if ( g_wmiCmd.GetAcceptCommand() == TRUE )
|
||
|
{
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
bRet = FALSE;
|
||
|
}
|
||
|
else // executing command
|
||
|
{
|
||
|
g_wmiCmd.SetBreakEvent(TRUE);
|
||
|
bRet = TRUE;
|
||
|
}
|
||
|
break;
|
||
|
case CTRL_CLOSE_EVENT:
|
||
|
default:
|
||
|
SAFEDELETE(g_pszBuffer);
|
||
|
g_wmiCmd.Uninitialize();
|
||
|
bRet = FALSE;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
return bRet;
|
||
|
}
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :CloseOutputFile
|
||
|
Synopsis :Close the output file.
|
||
|
Type :Global Function
|
||
|
Input parameters :None
|
||
|
Output parameters :None
|
||
|
Return Type :BOOL
|
||
|
Global Variables :
|
||
|
g_wmiCmd - wmi command line object
|
||
|
Calling Syntax :CloseOutputFile()
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
BOOL CloseOutputFile()
|
||
|
{
|
||
|
BOOL bRet = TRUE;
|
||
|
|
||
|
// TRUE for getting output file pointer.
|
||
|
FILE* fpOutputFile =
|
||
|
g_wmiCmd.GetParsedInfoObject().GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendFilePointer(TRUE);
|
||
|
|
||
|
// If currently output is going to file close the file.
|
||
|
if ( fpOutputFile != NULL )
|
||
|
{
|
||
|
if ( fclose(fpOutputFile) == EOF )
|
||
|
{
|
||
|
DisplayString(IDS_E_CLOSE_OUT_FILE_ERROR, CP_OEMCP,
|
||
|
NULL, TRUE, TRUE);
|
||
|
bRet = FALSE;
|
||
|
}
|
||
|
else // TRUE for setting output file pointer.
|
||
|
g_wmiCmd.GetParsedInfoObject().GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFilePointer(NULL, TRUE);
|
||
|
}
|
||
|
|
||
|
return bRet;
|
||
|
}
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :CloseAppendFile
|
||
|
Synopsis :Close the append file.
|
||
|
Type :Global Function
|
||
|
Input parameters :None
|
||
|
Output parameters :None
|
||
|
Return Type :BOOL
|
||
|
Global Variables :
|
||
|
g_wmiCmd - wmi command line object
|
||
|
Calling Syntax :CloseAppendFile()
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
BOOL CloseAppendFile()
|
||
|
{
|
||
|
BOOL bRet = TRUE;
|
||
|
|
||
|
// FALSE for getting append file pointer.
|
||
|
FILE* fpAppendFile =
|
||
|
g_wmiCmd.GetParsedInfoObject().GetGlblSwitchesObject().
|
||
|
GetOutputOrAppendFilePointer(FALSE);
|
||
|
|
||
|
if ( fpAppendFile != NULL )
|
||
|
{
|
||
|
if ( fclose(fpAppendFile) == EOF )
|
||
|
{
|
||
|
DisplayString(IDS_E_CLOSE_APPEND_FILE_ERROR, CP_OEMCP,
|
||
|
NULL, TRUE, TRUE);
|
||
|
bRet = FALSE;
|
||
|
}
|
||
|
else // FASLE for setting output file pointer.
|
||
|
g_wmiCmd.GetParsedInfoObject().GetGlblSwitchesObject().
|
||
|
SetOutputOrAppendFilePointer(NULL, FALSE);
|
||
|
}
|
||
|
|
||
|
return bRet;
|
||
|
}
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :CopyToClipBoard
|
||
|
Synopsis :Copy data to clip board.
|
||
|
Type :Global Function
|
||
|
Input parameters :
|
||
|
bstrClipBoardBuffer - reference to object of type _bstr_t.
|
||
|
Output parameters :None
|
||
|
Return Type :void
|
||
|
Global Variables :None
|
||
|
Calling Syntax :CopyToClipBoard(bstrClipBoardBuffer)
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
void CopyToClipBoard(_bstr_t& bstrClipBoardBuffer)
|
||
|
{
|
||
|
HGLOBAL hMem = CopyStringToHGlobal(bstrClipBoardBuffer);
|
||
|
if (hMem != NULL)
|
||
|
{
|
||
|
if (OpenClipboard(NULL))
|
||
|
{
|
||
|
EmptyClipboard();
|
||
|
SetClipboardData(CF_UNICODETEXT, hMem);
|
||
|
CloseClipboard();
|
||
|
}
|
||
|
else
|
||
|
GlobalFree(hMem); //We must clean up.
|
||
|
}
|
||
|
}
|
||
|
|
||
|
/*------------------------------------------------------------------------
|
||
|
Name :CopyStringToHGlobal
|
||
|
Synopsis :Copy string to global memory.
|
||
|
Type :Global Function
|
||
|
Input parameters :
|
||
|
psz - LPTSTR type, specifying string to get memory allocated.
|
||
|
Output parameters :None
|
||
|
Return Type :HGLOBAL
|
||
|
Global Variables :None
|
||
|
Calling Syntax :CopyStringToHGlobal(psz)
|
||
|
Notes :None
|
||
|
------------------------------------------------------------------------*/
|
||
|
HGLOBAL CopyStringToHGlobal(LPTSTR psz)
|
||
|
{
|
||
|
HGLOBAL hMem;
|
||
|
LPTSTR pszDst;
|
||
|
hMem = GlobalAlloc(GHND, (DWORD) (lstrlen(psz)+1) * sizeof(TCHAR));
|
||
|
|
||
|
if (hMem != NULL)
|
||
|
{
|
||
|
pszDst = (LPTSTR) GlobalLock(hMem);
|
||
|
lstrcpy(pszDst, psz);
|
||
|
GlobalUnlock(hMem);
|
||
|
}
|
||
|
|
||
|
return hMem;
|
||
|
}
|