mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
990 lines
26 KiB
990 lines
26 KiB
/**********************************************************************/
|
|
/** Microsoft Windows NT **/
|
|
/** Copyright(c) Microsoft Corp., 1991 **/
|
|
/**********************************************************************/
|
|
|
|
/*
|
|
srvmcpl.cxx
|
|
This is the main module for the Server Manager Control Panel Applet.
|
|
It contains the "LibMain" and "CplApplet" functions.
|
|
|
|
|
|
FILE HISTORY:
|
|
KeithMo 22-Apr-1992 Templated from DavidHov's NCPACPL.CXX.
|
|
KeithMo 02-Jun-1992 Added "Start the Server?" option.
|
|
KeithMo 10-Jun-1992 Allow other process to start the server
|
|
"behind our back".
|
|
KeithMo 03-Aug-1992 Folded in the Service Manager (SVCMGR.CPL).
|
|
|
|
*/
|
|
|
|
|
|
#include <ntincl.hxx>
|
|
|
|
extern "C"
|
|
{
|
|
#include <ntlsa.h>
|
|
#include <ntsam.h>
|
|
}
|
|
|
|
//
|
|
// #defining this macro enables certain "unique" behaviour in the
|
|
// SVCCNTL_DIALOG dialog. The "standard" dialog will bail-out when
|
|
// the user stops the server service. If this macro is #defined,
|
|
// then the dialog won't bail out (SVCCNTL_DIALOG does not require
|
|
// that the server service be running).
|
|
//
|
|
|
|
#define MINI_SERVER_MANAGER_APPLET
|
|
|
|
#define INCL_NET
|
|
#define INCL_NETLIB
|
|
#define INCL_NETSERVICE
|
|
#define INCL_WINDOWS
|
|
#define INCL_WINDOWS_GDI
|
|
#define INCL_NETERRORS
|
|
#define INCL_DOSERRORS
|
|
#include <lmui.hxx>
|
|
|
|
#if defined(DEBUG)
|
|
static const CHAR szFileName[] = __FILE__;
|
|
#define _FILENAME_DEFINED_ONCE szFileName
|
|
#endif
|
|
|
|
#include <uiassert.hxx>
|
|
#include <uitrace.hxx>
|
|
|
|
#define INCL_BLT_WINDOW
|
|
#define INCL_BLT_DIALOG
|
|
#define INCL_BLT_CONTROL
|
|
#define INCL_BLT_CLIENT
|
|
#define INCL_BLT_MSGPOPUP
|
|
#define INCL_BLT_EVENT
|
|
#define INCL_BLT_MISC
|
|
#define INCL_BLT_TIMER
|
|
#define INCL_BLT_CC
|
|
#include <blt.hxx>
|
|
|
|
#include <dbgstr.hxx>
|
|
#include <lmosrv.hxx>
|
|
#include <lmoloc.hxx>
|
|
|
|
extern "C"
|
|
{
|
|
#include <cpl.h> // Multimedia CPL defs
|
|
#include <srvmgr.h>
|
|
#include <mnet.h>
|
|
|
|
#include <uimsg.h>
|
|
#include <uirsrc.h>
|
|
}
|
|
|
|
#include <srvprop.hxx>
|
|
#include <srvsvc.hxx>
|
|
#include <security.hxx>
|
|
#include <ntacutil.hxx>
|
|
#include <lsaaccnt.hxx>
|
|
#include <svccntl.hxx>
|
|
#include <devcntl.hxx>
|
|
|
|
|
|
extern "C"
|
|
{
|
|
//
|
|
// Control Panel Applet entry point.
|
|
//
|
|
|
|
LONG FAR PASCAL CPlApplet( HWND hwndCPl,
|
|
WORD nMsg,
|
|
LONG lParam1,
|
|
LONG lparam2 );
|
|
|
|
//
|
|
// DLL load/unload entry point.
|
|
//
|
|
|
|
BOOL DllMain( HINSTANCE hInstance, DWORD nReason, LPVOID pReserved );
|
|
|
|
//
|
|
// Globals.
|
|
//
|
|
|
|
HINSTANCE _hCplInstance = NULL;
|
|
|
|
} // extern "C"
|
|
|
|
|
|
//
|
|
// This is the "type" for an applet startup function.
|
|
//
|
|
|
|
typedef APIERR (* PCPL_APPLET_FUNC)( HWND hWnd );
|
|
|
|
|
|
//
|
|
// We'll keep one of these structures for each applet in this DLL.
|
|
//
|
|
|
|
typedef struct _CPL_APPLET
|
|
{
|
|
int idIcon;
|
|
int idName;
|
|
int idInfo;
|
|
int idHelpFile;
|
|
DWORD dwHelpContext;
|
|
LONG lData;
|
|
PCPL_APPLET_FUNC pfnApplet;
|
|
|
|
} CPL_APPLET;
|
|
|
|
|
|
//
|
|
// Forward reference prototypes.
|
|
//
|
|
|
|
APIERR RunSrvMgr( HWND hWnd );
|
|
APIERR RunSvcMgr( HWND hWnd );
|
|
APIERR RunDevMgr( HWND hWnd );
|
|
|
|
|
|
//
|
|
// Our applet descriptors.
|
|
//
|
|
|
|
CPL_APPLET CplApplets[] = {
|
|
{ // Server applet
|
|
IDI_SMCPA_ICON,
|
|
IDS_SMCPA_NAME_STRING,
|
|
IDS_SMCPA_INFO_STRING,
|
|
IDS_SMCPA_HELPFILENAME,
|
|
HC_SERVER_PROPERTIES,
|
|
0L,
|
|
&RunSrvMgr
|
|
},
|
|
|
|
{ // Services applet
|
|
IDI_SVCCPA_ICON,
|
|
IDS_SVCCPA_NAME_STRING,
|
|
IDS_SVCCPA_INFO_STRING,
|
|
IDS_SMCPA_HELPFILENAME,
|
|
HC_SVCCNTL_DIALOG,
|
|
0L,
|
|
&RunSvcMgr
|
|
},
|
|
|
|
{ // Devices applet
|
|
IDI_DEVCPA_ICON,
|
|
IDS_DEVCPA_NAME_STRING,
|
|
IDS_DEVCPA_INFO_STRING,
|
|
IDS_SMCPA_HELPFILENAME,
|
|
HC_DEVCNTL_DIALOG,
|
|
0L,
|
|
&RunDevMgr
|
|
}
|
|
};
|
|
|
|
LONG cActiveApplets = sizeof(CplApplets) / sizeof(CplApplets[0]);
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: GetLocalServerName
|
|
|
|
SYNOPSIS: Returns the name of the current server (\\server).
|
|
|
|
ENTRY: nlsServerName - Will receive the server name.
|
|
|
|
RETURNS: APIERR - Any error encountered.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
|
|
********************************************************************/
|
|
APIERR GetLocalServerName( NLS_STR & nlsServerName )
|
|
{
|
|
APIERR err = nlsServerName.QueryError();
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = nlsServerName.CopyFrom( SZ("\\\\") );
|
|
}
|
|
|
|
SERVER_INFO_100 * psrvi100;
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = ::MNetServerGetInfo( NULL,
|
|
100,
|
|
(BYTE **)&psrvi100 );
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
ALIAS_STR nlsRawName( (const TCHAR *)psrvi100->sv100_name );
|
|
err = nlsServerName.Append( nlsRawName );
|
|
|
|
::MNetApiBufferFree( (BYTE **)&psrvi100 );
|
|
}
|
|
|
|
return err;
|
|
|
|
} // GetLocalServerName
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: StartServer
|
|
|
|
SYNOPSIS: Starts the server on the local machine.
|
|
|
|
ENTRY: hWnd - "Owning" window handle.
|
|
|
|
RETURNS: APIERR - Any error encountered.
|
|
|
|
HISTORY:
|
|
KeithMo 02-Jun-1992 Created.
|
|
|
|
********************************************************************/
|
|
APIERR StartServer( HWND hWnd )
|
|
{
|
|
LOCATION loc( LOC_TYPE_LOCAL );
|
|
NLS_STR nlsDisplayName;
|
|
|
|
APIERR err = loc.QueryError();
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = nlsDisplayName.QueryError();
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = loc.QueryDisplayName( &nlsDisplayName );
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
GENERIC_SERVICE * psvc = new GENERIC_SERVICE( hWnd,
|
|
NULL,
|
|
nlsDisplayName,
|
|
(const TCHAR *)SERVICE_SERVER );
|
|
|
|
err = ( psvc == NULL ) ? ERROR_NOT_ENOUGH_MEMORY
|
|
: psvc->QueryError();
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = psvc->Start();
|
|
}
|
|
|
|
delete psvc;
|
|
}
|
|
|
|
return err;
|
|
|
|
} // StartServer
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: InitializeDll
|
|
|
|
SYNOPSIS: Perform DLL initialiazation functions on a
|
|
once-per-process basis.
|
|
|
|
ENTRY: hInstance - Program instance of the caller.
|
|
|
|
EXIT: If this is the first initialization request for this
|
|
process, then all necessary BLT initializers have
|
|
been invoked.
|
|
|
|
RETURNS: BOOL - TRUE = Initialization OK.
|
|
FALSE = Initialization failed.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
beng 04-Aug-1992 Changes to BLT::Init
|
|
|
|
********************************************************************/
|
|
BOOL InitializeDll( HINSTANCE hInstance )
|
|
{
|
|
//
|
|
// Save the instance handle.
|
|
//
|
|
|
|
_hCplInstance = hInstance;
|
|
|
|
return TRUE;
|
|
|
|
} // InitializeDll
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: TerminateDll
|
|
|
|
SYNOPSIS: Perform DLL termination functions on a
|
|
once-per-process basis.
|
|
|
|
EXIT: All necessary BLT terminators have been invoked.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
beng 04-Aug-1992 Changes to BLT::Term
|
|
|
|
********************************************************************/
|
|
VOID TerminateDll( VOID )
|
|
{
|
|
//
|
|
// Just in case we try to do anything goofy.
|
|
//
|
|
|
|
_hCplInstance = NULL;
|
|
|
|
} // TerminateDll
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: InitializeAllApplets
|
|
|
|
SYNOPSIS: Called before applet runs.
|
|
|
|
ENTRY: hWnd - Window handle of parent window.
|
|
|
|
RETURNS: BOOL - TRUE = Applet should be installed.
|
|
FALSE = Applet cannot be installed.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
KeithMo 10-Jun-1992 Moved "guts" to RunSrvMgr.
|
|
JonN 30-Aug-1994 Added lParam parameters to CPL_INIT, CPL_TERM
|
|
JonN 22-Sep-1995 Only called when applet runs
|
|
|
|
********************************************************************/
|
|
BOOL InitializeAllApplets( HWND hWnd, LONG lParam1, LONG lParam2 )
|
|
{
|
|
TRACEEOL( "SRVMGR.CPL: InitializeAllApplets enter" );
|
|
//
|
|
// Initialize all of the NetUI goodies.
|
|
//
|
|
|
|
APIERR err = BLT::Init( _hCplInstance,
|
|
IDRSRC_APP_BASE, IDRSRC_APP_LAST,
|
|
IDS_UI_APP_BASE, IDS_UI_SRVMGR_LAST );
|
|
|
|
TRACEEOL( "SRVMGR.CPL: InitializeAllApplets BLT::Init returns " << err );
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
TRACEEOL( "SRVMGR.CPL: InitializeAllApplets BLT::_MASTER_TIMER::Init next" );
|
|
|
|
err = BLT_MASTER_TIMER::Init();
|
|
|
|
TRACEEOL( "SRVMGR.CPL: InitializeAllApplets BLT::_MASTER_TIMER::Init returns " << err );
|
|
|
|
if( err != NERR_Success )
|
|
{
|
|
//
|
|
// BLT initialized OK, but BLT_MASTER_TIMER
|
|
// failed. So, before we bag-out, we must
|
|
// deinitialize BLT.
|
|
//
|
|
|
|
BLT::Term( _hCplInstance );
|
|
}
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = BLT::RegisterHelpFile( _hCplInstance,
|
|
IDS_SMCPA_HELPFILENAME,
|
|
HC_UI_SRVMGR_BASE,
|
|
HC_UI_SRVMGR_LAST );
|
|
|
|
if( err != NERR_Success )
|
|
{
|
|
//
|
|
// This is the only place where we can safely
|
|
// invoke MsgPopup, since we *know* that all of
|
|
// the BLT goodies were initialized properly.
|
|
//
|
|
|
|
::MsgPopup( hWnd, err );
|
|
}
|
|
}
|
|
|
|
TRACEEOL( "SRVMGR.CPL: InitializeAllApplets exit" );
|
|
|
|
return err == NERR_Success;
|
|
|
|
} // InitializeAllApplets
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: TerminateAllApplets
|
|
|
|
SYNOPSIS: Called after applet runs.
|
|
|
|
ENTRY: hWnd - Window handle of parent window.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
JonN 30-Aug-1994 Added lParam parameters to CPL_INIT, CPL_TERM
|
|
JonN 22-Sep-1995 Only called when applet runs
|
|
|
|
********************************************************************/
|
|
VOID TerminateAllApplets( HWND hWnd, LONG lParam1, LONG lParam2 )
|
|
{
|
|
UNREFERENCED(hWnd);
|
|
|
|
TRACEEOL( "SRVMGR.CPL: TerminateAllApplets enter" );
|
|
//
|
|
// Kill the NetUI goodies.
|
|
//
|
|
|
|
TRACEEOL( "SRVMGR.CPL: TerminateAllApplets BLT::_MASTER_TIMER::Term next" );
|
|
BLT_MASTER_TIMER::Term();
|
|
TRACEEOL( "SRVMGR.CPL: TerminateAllApplets BLT::_MASTER_TIMER::Term complete" );
|
|
|
|
BLT::Term( _hCplInstance );
|
|
|
|
TRACEEOL( "SRVMGR.CPL: TerminateAllApplets exit" );
|
|
|
|
} // TerminateAllApplets
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: RunSrvMgr
|
|
|
|
SYNOPSIS: Invoke the main dialog of the Server Manager Control
|
|
Panel Applet.
|
|
|
|
ENTRY: hWnd - Window handle of parent window.
|
|
|
|
RETURNS: APIERR
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
KeithMo 10-Jun-1992 Robustified server startup code.
|
|
|
|
********************************************************************/
|
|
APIERR RunSrvMgr( HWND hWnd )
|
|
{
|
|
#ifdef DEBUG_SMCPA
|
|
DebugBreak();
|
|
#endif // DEBUG_SMCPA
|
|
|
|
POPUP::SetCaption( IDS_CAPTION_PROPERTIES );
|
|
|
|
//
|
|
// Let's see if the server is running.
|
|
//
|
|
|
|
NLS_STR nlsServerName;
|
|
BOOL fServerRunning = FALSE; // until proven otherwise
|
|
APIERR err = GetLocalServerName( nlsServerName );
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
fServerRunning = TRUE;
|
|
}
|
|
else
|
|
if( err == NERR_ServerNotStarted )
|
|
{
|
|
//
|
|
// The server is not started. Let's see if the user
|
|
// wants us to start it.
|
|
//
|
|
|
|
if( MsgPopup( hWnd,
|
|
IDS_START_SERVER_NOW,
|
|
MPSEV_WARNING,
|
|
MP_YESNO,
|
|
MP_YES ) != IDYES )
|
|
{
|
|
//
|
|
// The user doesn't want to play right now.
|
|
//
|
|
|
|
err = NERR_Success;
|
|
}
|
|
else
|
|
{
|
|
//
|
|
// Start the server & re-retrieve the server name.
|
|
//
|
|
|
|
err = StartServer( hWnd );
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = GetLocalServerName( nlsServerName );
|
|
}
|
|
|
|
fServerRunning = ( err == NERR_Success );
|
|
}
|
|
}
|
|
|
|
if( ( err == NERR_Success ) && fServerRunning )
|
|
{
|
|
//
|
|
// Invoke the Main Property Sheet.
|
|
//
|
|
|
|
BOOL fDummy;
|
|
|
|
SERVER_PROPERTIES * pDlg = new SERVER_PROPERTIES( hWnd,
|
|
nlsServerName,
|
|
&fDummy );
|
|
|
|
if (pDlg == NULL)
|
|
{
|
|
err = ERROR_NOT_ENOUGH_MEMORY;
|
|
}
|
|
else if ( (err = pDlg->QueryError()) == NERR_Success)
|
|
{
|
|
err = pDlg->Process();
|
|
}
|
|
|
|
delete pDlg;
|
|
}
|
|
|
|
if( err != NERR_Success )
|
|
{
|
|
::MsgPopup( hWnd, err );
|
|
}
|
|
|
|
POPUP::ResetCaption();
|
|
|
|
return err;
|
|
|
|
} // RunSrvMgr
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: RunSvcMgr
|
|
|
|
SYNOPSIS: Invoke the main dialog of the Service Manager Control
|
|
Panel Applet.
|
|
|
|
ENTRY: hWnd - Window handle of parent window.
|
|
|
|
RETURNS: APIERR
|
|
|
|
HISTORY:
|
|
KeithMo 06-Jul-1992 Created.
|
|
|
|
********************************************************************/
|
|
APIERR RunSvcMgr( HWND hWnd )
|
|
{
|
|
POPUP::SetCaption( IDS_CAPTION_SVCCNTL );
|
|
|
|
LOCATION loc( LOC_TYPE_LOCAL );
|
|
NLS_STR nlsDisplayName;
|
|
|
|
APIERR err = loc.QueryError();
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = nlsDisplayName.QueryError();
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = loc.QueryDisplayName( &nlsDisplayName );
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
SVCCNTL_DIALOG * pDlg = new SVCCNTL_DIALOG( hWnd,
|
|
NULL,
|
|
nlsDisplayName,
|
|
SV_TYPE_NT );
|
|
|
|
err = ( pDlg == NULL ) ? ERROR_NOT_ENOUGH_MEMORY
|
|
: pDlg->Process();
|
|
delete pDlg;
|
|
}
|
|
|
|
if( err != NERR_Success )
|
|
{
|
|
::MsgPopup( hWnd, err );
|
|
}
|
|
|
|
POPUP::ResetCaption();
|
|
|
|
return err;
|
|
|
|
} // RunSvcMgr
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: RunDevMgr
|
|
|
|
SYNOPSIS: Invoke the main dialog of the Device Manager Control
|
|
Panel Applet.
|
|
|
|
ENTRY: hWnd - Window handle of parent window.
|
|
|
|
RETURNS: APIERR
|
|
|
|
HISTORY:
|
|
KeithMo 22-Dec-1992 Created.
|
|
|
|
********************************************************************/
|
|
APIERR RunDevMgr( HWND hWnd )
|
|
{
|
|
POPUP::SetCaption( IDS_CAPTION_DEVCNTL );
|
|
|
|
LOCATION loc( LOC_TYPE_LOCAL );
|
|
NLS_STR nlsDisplayName;
|
|
|
|
APIERR err = loc.QueryError();
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = nlsDisplayName.QueryError();
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
err = loc.QueryDisplayName( &nlsDisplayName );
|
|
}
|
|
|
|
if( err == NERR_Success )
|
|
{
|
|
DEVCNTL_DIALOG * pDlg = new DEVCNTL_DIALOG( hWnd,
|
|
NULL,
|
|
nlsDisplayName,
|
|
SV_TYPE_NT );
|
|
|
|
err = ( pDlg == NULL ) ? ERROR_NOT_ENOUGH_MEMORY
|
|
: pDlg->Process();
|
|
delete pDlg;
|
|
}
|
|
|
|
if( err != NERR_Success )
|
|
{
|
|
::MsgPopup( hWnd, err );
|
|
}
|
|
|
|
POPUP::ResetCaption();
|
|
|
|
return err;
|
|
|
|
} // RunDevMgr
|
|
|
|
|
|
BOOL strLoad( INT idString, WCHAR * pszBuffer, INT cchBuffer )
|
|
{
|
|
int result = ::LoadString( ::_hCplInstance,
|
|
idString,
|
|
pszBuffer,
|
|
cchBuffer );
|
|
|
|
return ( result > 0 ) && ( result < cchBuffer );
|
|
|
|
} // strLoad
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: CPlApplet
|
|
|
|
SYNOPSIS: Exported function to start the Server Manager Control
|
|
Panel Applet.
|
|
|
|
ENTRY: hwndCPl - Window handle of parent.
|
|
|
|
nMsg - CPL user message (see CPL.H
|
|
in WINDOWS\SHELL\CONTROL\H).
|
|
|
|
lParam1 - Message-specific pointer.
|
|
|
|
lParam2 - Message-specific pointer.
|
|
|
|
RETURNS: LONG
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
JonN 30-Aug-1994 Added lParam parameters to CPL_INIT, CPL_TERM
|
|
|
|
********************************************************************/
|
|
LONG FAR PASCAL CPlApplet( HWND hwndCPl,
|
|
WORD nMsg,
|
|
LONG lParam1,
|
|
LONG lParam2 )
|
|
{
|
|
LPCPLINFO pCplInfo;
|
|
LPNEWCPLINFO pNewInfo;
|
|
LONG nResult = 0;
|
|
|
|
switch( nMsg )
|
|
{
|
|
case CPL_INIT:
|
|
//
|
|
// This message is sent to indicate that CPlApplet() was found.
|
|
//
|
|
// lParam1 is not used, but we pass it anyway.
|
|
//
|
|
// lParam2 is -1 iff the DLL will be used only to confirm the
|
|
// number of applets.
|
|
//
|
|
//
|
|
// Return TRUE if applet should be installed, FALSE otherwise.
|
|
//
|
|
|
|
return TRUE;
|
|
|
|
case CPL_GETCOUNT:
|
|
//
|
|
// This message is set to determine the number of applets contained
|
|
// in this DLL.
|
|
//
|
|
// lParam1 and lParam2 are not used.
|
|
//
|
|
// Return the number of applets contained in this DLL.
|
|
//
|
|
|
|
return cActiveApplets;
|
|
|
|
case CPL_INQUIRE:
|
|
//
|
|
// This message is sent once per applet to retrieve information
|
|
// about each applet.
|
|
//
|
|
// lParam1 is the applet number to register.
|
|
//
|
|
// lParam2 is a pointer to a CPLINFO structure. The CPLINFO
|
|
// structure's idIcon, idName, idInfo, and lData fields should
|
|
// be initialized as appropriate for the applet.
|
|
//
|
|
// There is no return value.
|
|
//
|
|
|
|
pCplInfo = (LPCPLINFO)lParam2;
|
|
|
|
if( lParam1 < cActiveApplets )
|
|
{
|
|
CPL_APPLET * pApplet = &CplApplets[lParam1];
|
|
|
|
pCplInfo->idIcon = pApplet->idIcon;
|
|
pCplInfo->idName = pApplet->idName;
|
|
pCplInfo->idInfo = pApplet->idInfo;
|
|
pCplInfo->lData = pApplet->lData;
|
|
}
|
|
break;
|
|
|
|
case CPL_SELECT:
|
|
//
|
|
// This message is sent when the applet's icon has been
|
|
// selected.
|
|
//
|
|
// lParam1 is the applet number that was selected.
|
|
//
|
|
// lParam2 is the applet's lData value.
|
|
//
|
|
// There is no return value.
|
|
//
|
|
|
|
break;
|
|
|
|
case CPL_DBLCLK:
|
|
//
|
|
// This message is sent when the applet's icon has been
|
|
// double-clicked. This message should initiate the
|
|
// applet's dialog box.
|
|
//
|
|
// lParam1 is the applet number that was selected.
|
|
//
|
|
// lParam2 is the applet's lData value.
|
|
//
|
|
// There is no return value.
|
|
//
|
|
|
|
if( lParam1 < cActiveApplets )
|
|
{
|
|
if ( (LONG)InitializeAllApplets( hwndCPl, lParam1, lParam2 ) )
|
|
{
|
|
(CplApplets[lParam1].pfnApplet)( hwndCPl );
|
|
TerminateAllApplets( hwndCPl, lParam1, lParam2 );
|
|
}
|
|
else
|
|
{
|
|
ASSERT( FALSE );
|
|
}
|
|
}
|
|
break;
|
|
|
|
case CPL_STOP:
|
|
//
|
|
// This message is sent once for each applet when the
|
|
// control panel is shutting down. This message should
|
|
// initiate applet specific cleanup.
|
|
//
|
|
// lParam1 is the applet number being stopped.
|
|
//
|
|
// lParam2 is the applet's lData value.
|
|
//
|
|
// There is no return value.
|
|
//
|
|
|
|
break;
|
|
|
|
case CPL_EXIT:
|
|
//
|
|
// This message is sent just before the control panel calls
|
|
// FreeLibrary. This message should initiate non applet
|
|
// specific cleanup.
|
|
//
|
|
// lParam1 is not used, but we pass it anyway.
|
|
//
|
|
// lParam2 is -1 iff the DLL was used only to confirm the
|
|
// number of applets.
|
|
//
|
|
// There is no return value.
|
|
//
|
|
|
|
break;
|
|
|
|
case CPL_NEWINQUIRE:
|
|
//
|
|
// This message is basically the same as CPL_INQUIRE, except
|
|
// lParam2 points to a NEWCPLINFO structure. This message will
|
|
// be sent *before* CPL_INQUIRE. If the applet returns a non
|
|
// zero value, then CPL_INQUIRE will not be sent.
|
|
//
|
|
// lParam1 is the applet number to register.
|
|
//
|
|
// lParam2 is a pointer to a NEWCPLINFO structure.
|
|
//
|
|
// Return TRUE this message was handled, otherwise return FALSE.
|
|
//
|
|
|
|
pNewInfo = (LPNEWCPLINFO)lParam2;
|
|
|
|
if( lParam1 < cActiveApplets )
|
|
{
|
|
CPL_APPLET * pApplet = &CplApplets[lParam1];
|
|
|
|
pNewInfo->dwSize = sizeof(*pNewInfo);
|
|
pNewInfo->dwFlags = 0;
|
|
pNewInfo->dwHelpContext = pApplet->dwHelpContext;
|
|
pNewInfo->lData = pApplet->lData;
|
|
|
|
pNewInfo->hIcon = ::LoadIcon( ::_hCplInstance,
|
|
MAKEINTRESOURCE( pApplet->idIcon ) );
|
|
|
|
if( ( pNewInfo->hIcon != NULL ) &&
|
|
strLoad( pApplet->idName,
|
|
pNewInfo->szName,
|
|
sizeof(pNewInfo->szName) ) &&
|
|
strLoad( pApplet->idInfo,
|
|
pNewInfo->szInfo,
|
|
sizeof(pNewInfo->szInfo) ) &&
|
|
strLoad( pApplet->idHelpFile,
|
|
pNewInfo->szHelpFile,
|
|
sizeof(pNewInfo->szHelpFile) ) )
|
|
{
|
|
nResult = TRUE;
|
|
}
|
|
}
|
|
break;
|
|
|
|
default:
|
|
//
|
|
// Who knows. Ignore it.
|
|
//
|
|
|
|
break;
|
|
}
|
|
|
|
return nResult;
|
|
|
|
} // CPlApplet
|
|
|
|
|
|
|
|
/*******************************************************************
|
|
|
|
NAME: DllMain
|
|
|
|
SYNOPSIS: This DLL entry point is called when processes & threads
|
|
are initialized and terminated, or upon calls to
|
|
LoadLibrary() and FreeLibrary().
|
|
|
|
ENTRY: hInstance - A handle to the DLL.
|
|
|
|
nReason - Indicates why the DLL entry
|
|
point is being called.
|
|
|
|
pReserved - Reserved.
|
|
|
|
RETURNS: BOOL - TRUE = DLL init was successful.
|
|
FALSE = DLL init failed.
|
|
|
|
NOTES: The return value is only relevant during processing of
|
|
DLL_PROCESS_ATTACH notifications.
|
|
|
|
HISTORY:
|
|
KeithMo 22-Apr-1992 Created.
|
|
|
|
********************************************************************/
|
|
|
|
BOOL DllMain( HINSTANCE hInstance, DWORD nReason, LPVOID pReserved )
|
|
{
|
|
BOOL fResult = TRUE;
|
|
|
|
UNREFERENCED(pReserved);
|
|
|
|
switch( nReason )
|
|
{
|
|
case DLL_PROCESS_ATTACH:
|
|
//
|
|
// This notification indicates that the DLL is attaching to
|
|
// the address space of the current process. This is either
|
|
// the result of the process starting up, or after a call to
|
|
// LoadLibrary(). The DLL should us this as a hook to
|
|
// initialize any instance data or to allocate a TLS index.
|
|
//
|
|
// This call is made in the context of the thread that
|
|
// caused the process address space to change.
|
|
//
|
|
|
|
DisableThreadLibraryCalls(hInstance);
|
|
fResult = InitializeDll( hInstance );
|
|
break;
|
|
|
|
case DLL_PROCESS_DETACH:
|
|
//
|
|
// This notification indicates that the calling process is
|
|
// detaching the DLL from its address space. This is either
|
|
// due to a clean process exit or from a FreeLibrary() call.
|
|
// The DLL should use this opportunity to return any TLS
|
|
// indexes allocated and to free any thread local data.
|
|
//
|
|
// Note that this notification is posted only once per
|
|
// process. Individual threads do not invoke the
|
|
// DLL_THREAD_DETACH notification.
|
|
//
|
|
|
|
TerminateDll();
|
|
break;
|
|
|
|
default:
|
|
//
|
|
// Who knows? Just ignore it.
|
|
//
|
|
|
|
break;
|
|
}
|
|
|
|
return fResult;
|
|
|
|
} // DllMain
|
|
|