How to Start the Microsoft System Information Dialog






4.11/5 (9 votes)
Jan 24, 2002
2 min read

187474

3651
Starting Microsoft System Information programmatically from application
Introduction
Everyone has seen the "System Info ..." button in the About box of Microsoft applications. It can be found in Microsoft Office apps, Visual Studio .NET and others. When clicked, it starts the Microsoft System Information utility. System Information displays a comprehensive view of your hardware, system components, and software environment. On earlier versions of Windows, namely Microsoft Office installed it (thanks to Matt Philmon for noticing that). I have once found out how to get its path in case the utility is installed developing MDB to SQLServer database converter with VB 6.0 - the function retrieving its path and starting it is added automatically to all VB projects about box. Look at the code below, it reads the registry for the first path and if not found, checks the second one for MSInfo32.exe. I think that in the newer versions of MS Windows, the MSInfo32.exe is left for backward compatibility just to start real program located somewhere else. For example, in Windows 2000, System Information is Microsoft Management Console (MMC) snap-in MSInfo32.msc located in the "C:\Program Files\Common Files\Microsoft Shared\MSInfo\" and MSInfo32.exe only seems to launch it.
Source Code
MFC Source Code
// Required for the path functions
#if ( _MFC_VER < 0x0700 && !defined _INC_SHLWAPI )
#include < Shlwapi.h >
#pragma comment( lib, "Shlwapi.lib" )
#endif
// Required for the CRegKey
#include <atlbase.h>
#define IDS_REG_KEY_MSINFO_PATH1 _T(
"Software\\Microsoft\\Shared Tools\\MSInfo" )
#define IDS_REG_KEY_MSINFO_PATH2 _T(
"Software\\Microsoft\\Shared Tools Location" )
#define IDS_REG_VAL_MSINFO_PATH1 _T( "Path" )
#define IDS_REG_VAL_MSINFO_PATH2 _T( "MSInfo" )
#define IDS_MSINFO_EXE_NAME _T( "MSInfo32.exe" )
//...
BOOL GetSysInfoPath( CString& strPath )
{
// Empty the string buffer and initialize variables.
strPath.Empty();
LPTSTR pszPath = strPath.GetBuffer( MAX_PATH );
CRegKey reg;
DWORD dwSize = MAX_PATH;
LONG nRet = reg.Open( HKEY_LOCAL_MACHINE, IDS_REG_KEY_MSINFO_PATH1,
KEY_READ );
// Try to find "MSInfo32.exe" at the first location:
if ( nRet == ERROR_SUCCESS )
{
#if ( _MFC_VER >= 0x0700 )
nRet = reg.QueryStringValue( IDS_REG_VAL_MSINFO_PATH1, pszPath,
&dwSize );
#else
nRet = reg.QueryValue(
pszPath, IDS_REG_VAL_MSINFO_PATH1, &dwSize );
#endif
reg.Close();
}
// If first attemp fails then try to find "MSInfo32.exe"
// at the second location:
if ( nRet != ERROR_SUCCESS )
{
nRet = reg.Open(
HKEY_LOCAL_MACHINE, IDS_REG_KEY_MSINFO_PATH2, KEY_READ );
if ( nRet == ERROR_SUCCESS )
{
#if ( _MFC_VER >= 0x0700 )
reg.QueryStringValue( IDS_REG_VAL_MSINFO_PATH2, pszPath,
&dwSize );
#else
reg.QueryValue( pszPath, IDS_REG_VAL_MSINFO_PATH2, &dwSize );
#endif
// The second location does not contain the full
// path (exe name is missing), complete it:
if ( nRet == ERROR_SUCCESS )
VERIFY( ::PathAppend( pszPath, IDS_MSINFO_EXE_NAME ) );
reg.Close();
}
}
strPath.ReleaseBuffer();
strPath.FreeExtra();
// Check for valid file.
return ::PathFileExists( strPath );
}
C# Source Code
//...
using Microsoft.Win32; // Required for the registry classes.
using System.IO; // Required for the Path class.
using System.Diagnostics; // Required for the process classes.
//...
public bool GetMsinfo32Path( ref string strPath )
{
strPath = string.Empty;
object objTmp = null;
RegistryKey regKey = Registry.LocalMachine;
if( regKey != null )
{
regKey = regKey.OpenSubKey(
"Software\\Microsoft\\Shared Tools\\MSInfo" );
if( regKey != null )
objTmp = regKey.GetValue( "Path" );
if( objTmp == null )
{
regKey = regKey.OpenSubKey(
"Software\\Microsoft\\Shared Tools Location" );
if( regKey != null )
{
objTmp = regKey.GetValue( "MSInfo" );
if( objTmp != null )
strPath = Path.Combine(
objTmp.ToString(), "MSInfo32.exe" );
}
}
else
strPath = objTmp.ToString();
try
{
FileInfo fi = new FileInfo( strPath );
return fi.Exists;
}
catch( ArgumentException )
{
strPath = string.Empty;
}
}
return false;
}
So we can get the full path to Msinfo32.exe and can run it:
MFC Sample
void CSomeDialog::StartSysInfo( void )
{
CString strMsinfo32( _T( "" ) );
if( GetSysInfoPath( strMsinfo32 ) )
{
// Disable type cast warning for cast from HINSTANCE to INT.
// Although ShellExecute returns HINSTANCE for compatibility
// with 16-bit Windows applications, it is not a true HINSTANCE.
// It can be cast only to an integer and compared to either 32
// or the SE_ERR_XXX error codes.
#if _MSC_VER >= 1300 //Represents Microsoft Visual C++ .NET
#pragma warning( disable : 4311 )
#endif
UINT uRet = (UINT)::ShellExecute( GetSafeHwnd(), _T( "open" ),
strMsinfo32, NULL, NULL, SW_SHOWNORMAL );
// Restore type cast warnings defaults
#if _MSC_VER >= 1300 //Represents Microsoft Visual C++ .NET
#pragma warning( default : 4311 )
#endif
if( uRet < = HINSTANCE_ERROR )
{
AfxMessageBox( _T( "Error Executing \"MsInfo32.exe\" !" ),
MB_OK | MB_ICONEXCLAMATION );
}
}
else
{
AfxMessageBox( _T( "\"MsInfo32.exe\" cannot be found !" ),
MB_OK | MB_ICONEXCLAMATION );
}
}
Using with Chris Maunder's Hyperlink control:
// In the header:
#include "HyperLink.h"
//...
public:
CHyperLink m_wndLinkSysInfo;
// In the cpp:
BOOL CSomeDialog::OnInitDialog( void )
{
// ...
CString strSysInfo( _T( "" ) );
if( GetSysInfoPath( strSysInfo ) )
m_wndLinkSysInfo.SetURL( strSysInfo );
else
m_wndLinkSysInfo.EnableWindow( FALSE );
//...
}
C# Sample
private void StartSysInfo( string strSysInfo )
{
try
{
Process.Start( strSysInfo );
}
catch ( Win32Exception ex )
{
MessageBox.Show ( this, ex.Message, Application.ProductName,
MessageBoxButtons.OK, MessageBoxIcon.Exclamation );
}
}
// Start using LinkLabel control:
private void lnkSysInfo_LinkClicked( object sender,
System.Windows.Forms.LinkLabelLinkClickedEventArgs e )
{
lnkSysInfo.Links[ lnkSysInfo.Links.IndexOf( e.Link ) ].Visited = true;
StartSysInfo( e.Link.LinkData.ToString() );
}
// Start on button click:
private void cmdSysInfo_Click( object sender, System.EventArgs e )
{
string strSysInfo = string.Empty;
if( GetMsinfo32Path( ref strSysInfo ) )
StartSysInfo( strSysInfo );
}
There is one more info tool on Windows NT 4.0 called WinMSD.exe - the descriptive name is Windows NT Diagnostics program. On Windows 2000 and XP platforms, the WinMSD tool has been replaced with MsInfo32.exe - so under Windows 2000/XP, WinMsd.exe is a stub executable file that starts Msinfo32.exe.
History
- 24th January, 2002: Posted article
- 5th February, 2002: Minor changes
- 28th July, 2002: Improved code for MFC 7.0, added C# code and download
- 4th August, 2002: Demo downloads fixed
- 5th October, 2002: New downloads
License
This article has no explicit license attached to it, but may contain usage terms in the article text or the download files themselves. If in doubt, please contact the author via the discussion board below.
A list of licenses authors might use can be found here.