home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
DP Tool Club 15
/
CD_ASCQ_15_070894.iso
/
vrac
/
memsz231.zip
/
MEMSIZE.CPP
< prev
next >
Wrap
C/C++ Source or Header
|
1994-06-08
|
123KB
|
3,115 lines
/**************************************************************** MEMSIZE.CPP
* *
* System Resources Monitor *
* *
* (C) Copyright 1991-1994 by Richard W. Papo. *
* *
* This is 'FreeWare'. As such, it may be copied and distributed *
* freely. If you want to use part of it in your own program, please *
* give credit where credit is due. If you want to change the *
* program, please refer the change request to me or send me the *
* modified source code. I can be reached at CompuServe 72607,3111 *
* and on Internet at RPapo@Msen.com. *
* *
****************************************************************************/
// Bugs to Fix:
//
// (1) When Float To Top is active, then the E editor dies upon displaying
// its file-type-set dialog. CLOCK has the same problem. IBM is helping.
//
// Things to do:
//
// (1) Provide an item to serve as a button to cause a secondary
// drive status window to be displayed (requested by Leland Sheppard).
//
// (2) Provide colored highlights for different levels, configurable
// by item.
//
#define INCL_BASE
#define INCL_PM
#include <os2.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "debug.h"
#include "helpwin.h"
#include "module.h"
#include "process.h"
#include "profile.h"
#include "restring.h"
#include "support.h"
#include "window.h"
#include "about.h"
#include "config.h"
#include "items.h"
#include "memsize.h"
#define STATIC
/****************************************************************************
* *
* Definitions & Declarations *
* *
****************************************************************************/
// Constants
#define WM_REFRESH (WM_USER)
#define MAX_DRIVES (26)
#define DRIVE_ERROR (0xFFFFFFFFL)
enum
{
ITEM_CLOCK,
ITEM_ELAPSEDTIME,
ITEM_MEMORYFREE,
ITEM_SWAPFILESIZE,
ITEM_SWAPDISKFREE,
ITEM_SPOOLFILESIZE,
ITEM_CPULOAD,
ITEM_TASKCOUNT,
ITEM_TOTALFREE,
ITEM_BASE_COUNT
} ;
// Data Types
typedef struct {
BOOL Active ;
PULONG Counter ;
PUSHORT Interval ;
PBYTE Priority ;
HWND Owner ;
} MONITOR_PARMS, *PMONITOR_PARMS ;
typedef struct {
BOOL Active ;
ULONG Counter ;
} COUNTER_PARMS, *PCOUNTER_PARMS ;
typedef struct { // Parameters saved to system.
// The Display Item List - - -
Item *Items [ ITEM_BASE_COUNT + MAX_DRIVES ] ;
int ItemCount ;
// Data required for the display item objects to function.
ULONG IdleCount ;
ULONG MaxCount ;
BYTE SwapPath [_MAX_PATH] ;
ULONG MinFree ;
PBYTE SpoolPath ;
COUNTRYINFO CountryInfo ;
ResourceString *Day ;
ResourceString *Days ;
ResourceString *DaysOfWeek ;
ResourceString *DriveError ;
// Window size and location
SWP Position ;
BOOL fPosition ;
// User Options
BOOL HideControls ;
BOOL fHideControls ;
BOOL Float ;
BOOL fFloat ;
BOOL Animate ;
BOOL fAnimate ;
BOOL ShowFileSystemNames ;
BOOL fShowFileSystemNames ;
BYTE MonitorPriority ;
BOOL fMonitorPriority ;
USHORT TimerInterval ;
BOOL fTimerInterval ;
// Presentation Parameters
BYTE FontNameSize [80] ;
BOOL fFontNameSize ;
COLOR BackColor ;
BOOL fBackColor ;
COLOR TextColor ;
BOOL fTextColor ;
} INIDATA, *PINIDATA ;
typedef struct { // Data structure for window.
Process *Proc ;
Module *Library ;
Profile *IniFile ;
INIDATA IniData ;
TID IdleLoopTID ;
COUNTER_PARMS IdleLoopParms ;
TID MonitorTID ;
MONITOR_PARMS MonitorParms ;
HWND hwndTitleBar ;
HWND hwndSysMenu ;
HWND hwndMinMax ;
ULONG Drives ;
long Width ;
long Height ;
} DATA, *PDATA ;
typedef struct {
short Filler ;
Process *Proc ;
Module *Library ;
Profile *IniFile ;
} PARMS, *PPARMS ;
// Function Prototypes
extern int main ( int argc, char *argv[] ) ;
STATIC FNWP MessageProcessor ;
STATIC METHODFUNCTION Create ;
STATIC METHODFUNCTION Destroy ;
STATIC METHODFUNCTION Size ;
STATIC METHODFUNCTION SaveApplication ;
STATIC METHODFUNCTION Paint ;
STATIC METHODFUNCTION Command ;
STATIC METHODFUNCTION ResetDefaults ;
STATIC METHODFUNCTION HideControlsCmd ;
STATIC METHODFUNCTION Configure ;
STATIC METHODFUNCTION About ;
STATIC METHODFUNCTION ButtonDown ;
STATIC METHODFUNCTION ButtonDblClick ;
STATIC METHODFUNCTION PresParamChanged ;
STATIC METHODFUNCTION SysColorChange ;
STATIC METHODFUNCTION QueryKeysHelp ;
STATIC METHODFUNCTION HelpError ;
STATIC METHODFUNCTION ExtHelpUndefined ;
STATIC METHODFUNCTION HelpSubitemNotFound ;
STATIC METHODFUNCTION Refresh ;
STATIC int GetIniData ( HAB Anchor, HMODULE Library, HINI IniHandle, PINIDATA IniData ) ;
STATIC VOID PutIniData ( HINI IniHandle, PINIDATA IniData ) ;
STATIC PSZ ScanSystemConfig ( HAB Anchor, PSZ Keyword ) ;
STATIC void ResizeWindow ( HWND hwnd, PINIDATA IniData ) ;
STATIC void HideControls
(
BOOL fHide,
HWND hwndFrame,
HWND hwndSysMenu,
HWND hwndTitleBar,
HWND hwndMinMax
) ;
STATIC void UpdateWindow ( HWND hwnd, PDATA Data, BOOL All ) ;
STATIC VOID _Optlink MonitorLoopThread ( PVOID Parameter ) ;
STATIC VOID UpdateDriveList
(
HAB Anchor,
HMODULE Library,
HINI IniHandle,
PINIDATA IniData,
ULONG OldDrives,
ULONG NewDrives
) ;
STATIC int CheckDrive ( USHORT Drive, PBYTE FileSystem ) ;
STATIC ULONG CalibrateLoadMeter ( PCOUNTER_PARMS Parms ) ;
STATIC VOID _Optlink CounterThread ( PVOID Parameter ) ;
// Global Data
HMODULE LibraryHandle ;
/****************************************************************************
* *
* Program Mainline *
* *
****************************************************************************/
extern int main ( int argc, char *argv[] ) {
/***************************************************************************
* Initialize the process. *
***************************************************************************/
Process Proc ;
/***************************************************************************
* Open the resource library. *
***************************************************************************/
Module Library ( PSZ(PROGRAM_NAME) ) ;
LibraryHandle = Library.QueryHandle() ;
/***************************************************************************
* Get the program title. *
***************************************************************************/
ResourceString Title ( Library.QueryHandle(), IDS_TITLE ) ;
/***************************************************************************
* Decipher command-line parameters. *
***************************************************************************/
BOOL Reset = FALSE ;
ResourceString ResetCommand ( Library.QueryHandle(), IDS_PARMS_RESET ) ;
while ( --argc ) {
argv ++ ;
if ( *argv[0] == '?' ) {
ResourceString Message ( Library.QueryHandle(), IDS_PARAMETERLIST ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_NOICON ) ;
return ( 0 ) ;
}
if ( !stricmp ( *argv, PCHAR(ResetCommand) ) ) {
Reset = TRUE ;
continue ;
}
{
ResourceString Format ( Library.QueryHandle(), IDS_ERROR_INVALIDPARM ) ;
BYTE Message [200] ;
sprintf ( PCHAR(Message), PCHAR(Format), *argv ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, Message,
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
abort ( ) ;
}
}
/***************************************************************************
* Create the help instance. *
***************************************************************************/
ResourceString HelpTitle ( Library.QueryHandle(), IDS_HELPTITLE ) ;
HelpWindow Help ( Proc.QueryAnchor(), 0,
ID_MAIN, PSZ(PROGRAM_NAME ".hlp"), PSZ(HelpTitle) ) ;
if ( Help.QueryHandle() == 0 ) {
ERRORID Error = WinGetLastError ( Proc.QueryAnchor() ) ;
ResourceString Format ( Library.QueryHandle(), IDS_ERROR_CREATEHELP ) ;
CHAR Message [200] ;
sprintf ( Message, PCHAR(Format), Error ) ;
Log ( "%s", Message ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
}
/***************************************************************************
* Open/create the profile file. Reset if requested. *
***************************************************************************/
Profile IniFile ( PSZ(PROGRAM_NAME),
Proc.QueryAnchor(), Library.QueryHandle(),
IDD_PROFILE_PATH, Help.QueryHandle(), Reset ) ;
if ( IniFile.QueryHandle() == 0 ) {
ResourceString Message ( Library.QueryHandle(), IDS_ERROR_PRFOPENPROFILE ) ;
Log ( "%s", PSZ(Message) ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
abort ( ) ;
}
/***************************************************************************
* Read the profile to find out if we're to animate the frame window. *
***************************************************************************/
BOOL Animate = FALSE ;
ULONG Size ;
if
(
PrfQueryProfileSize ( IniFile.QueryHandle(), PSZ(PROGRAM_NAME), PSZ("Animate"), &Size )
AND
( ( Size == sizeof(Animate) ) OR ( Size == sizeof(short) ) )
AND
PrfQueryProfileData ( IniFile.QueryHandle(), PSZ(PROGRAM_NAME), PSZ("Animate"), &Animate, &Size )
)
{
;
}
/***************************************************************************
* Create the frame window. *
***************************************************************************/
FRAMECDATA FrameControlData ;
FrameControlData.cb = sizeof(FrameControlData) ;
FrameControlData.flCreateFlags =
FCF_TITLEBAR | FCF_SYSMENU | FCF_BORDER |
FCF_ICON | FCF_MINBUTTON | FCF_NOBYTEALIGN | FCF_ACCELTABLE ;
FrameControlData.hmodResources = 0 ;
FrameControlData.idResources = ID_MAIN ;
Window Frame ( HWND_DESKTOP, WC_FRAME, PSZ(Title),
Animate ? WS_ANIMATE : 0,
0, 0, 0, 0, HWND_DESKTOP, HWND_TOP, ID_MAIN,
&FrameControlData, NULL ) ;
if ( Frame.QueryHandle() == 0 ) {
ERRORID Error = WinGetLastError ( Proc.QueryAnchor() ) ;
ResourceString Format ( Library.QueryHandle(), IDS_ERROR_CREATEFRAME ) ;
CHAR Message [200] ;
sprintf ( Message, PCHAR(Format), Error ) ;
Log ( "%s", Message ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
abort ( ) ;
}
/***************************************************************************
* Associate the help instance with the frame window. *
***************************************************************************/
if ( Help.QueryHandle() ) {
WinAssociateHelpInstance ( Help.QueryHandle(), Frame.QueryHandle() ) ;
}
/***************************************************************************
* Register the client window class. *
***************************************************************************/
if
(
!WinRegisterClass
(
Proc.QueryAnchor(),
PSZ(CLASS_NAME),
MessageProcessor,
CS_MOVENOTIFY,
sizeof(PVOID)
)
)
{
ERRORID Error = WinGetLastError ( Proc.QueryAnchor() ) ;
ResourceString Format ( Library.QueryHandle(), IDS_ERROR_WINREGISTERCLASS ) ;
CHAR Message [200] ;
sprintf ( Message, PCHAR(Format), CLASS_NAME, Error ) ;
Log ( "%s", Message ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
abort ( ) ;
}
/***************************************************************************
* Create the client window. *
***************************************************************************/
PARMS Parms ;
Parms.Filler = 0 ;
Parms.Proc = & Proc ;
Parms.Library = & Library ;
Parms.IniFile = & IniFile ;
Window Client ( Frame.QueryHandle(), PSZ(CLASS_NAME), PSZ(""), 0, 0, 0, 0, 0,
Frame.QueryHandle(), HWND_BOTTOM, FID_CLIENT, &Parms, NULL ) ;
if ( Client.QueryHandle() == 0 ) {
ERRORID Error = WinGetLastError ( Proc.QueryAnchor() ) ;
ResourceString Format ( Library.QueryHandle(), IDS_ERROR_CREATECLIENT ) ;
CHAR Message [200] ;
sprintf ( Message, PCHAR(Format), Error ) ;
Log ( "%s", Message ) ;
WinMessageBox ( HWND_DESKTOP, HWND_DESKTOP, PSZ(Message),
PSZ(Title), 0, MB_ENTER | MB_ICONEXCLAMATION ) ;
abort ( ) ;
}
/***************************************************************************
* Wait for and process messages to the window's queue. Terminate *
* when the WM_QUIT message is received. *
***************************************************************************/
QMSG QueueMessage ;
while ( WinGetMsg ( Proc.QueryAnchor(), &QueueMessage, 0, 0, 0 ) ) {
WinDispatchMsg ( Proc.QueryAnchor(), &QueueMessage ) ;
}
/***************************************************************************
* Discard all that was requested of the system and terminate. *
***************************************************************************/
return ( 0 ) ;
}
/****************************************************************************
* *
* Window Message Processor *
* *
****************************************************************************/
STATIC MRESULT EXPENTRY MessageProcessor ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Dispatch the message according to the method table and return the *
* result. Any messages not defined above get handled by the system *
* default window processor. *
***************************************************************************/
static METHOD Methods [] =
{
{ WM_CREATE, Create },
{ WM_DESTROY, Destroy },
{ WM_SIZE, Size },
{ WM_MOVE, Size },
{ WM_SAVEAPPLICATION, SaveApplication },
{ WM_PAINT, Paint },
{ WM_BUTTON1DOWN, ButtonDown },
{ WM_BUTTON2DOWN, ButtonDown },
{ WM_BUTTON1DBLCLK, ButtonDblClick },
{ WM_BUTTON2DBLCLK, ButtonDblClick },
{ WM_PRESPARAMCHANGED, PresParamChanged },
{ WM_SYSCOLORCHANGE, SysColorChange },
{ WM_COMMAND, Command },
{ HM_QUERY_KEYS_HELP, QueryKeysHelp },
{ HM_ERROR, HelpError },
{ HM_EXT_HELP_UNDEFINED, ExtHelpUndefined },
{ HM_HELPSUBITEM_NOT_FOUND, HelpSubitemNotFound },
{ WM_REFRESH, Refresh }
} ;
return ( DispatchMessage ( hwnd, msg, mp1, mp2, Methods, sizeof(Methods)/sizeof(Methods[0]), WinDefWindowProc ) ) ;
}
/****************************************************************************
* *
* Create the main window. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Create ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Allocate instance data. *
***************************************************************************/
PDATA Data = PDATA ( malloc ( sizeof(DATA) ) ) ;
memset ( Data, 0, sizeof(DATA) ) ;
WinSetWindowPtr ( hwnd, QWL_USER, Data ) ;
/***************************************************************************
* Grab any parameters from the WM_CREATE message. *
***************************************************************************/
PPARMS Parms = (PPARMS) PVOIDFROMMP ( mp1 ) ;
Data->Proc = Parms->Proc ;
Data->Library = Parms->Library ;
Data->IniFile = Parms->IniFile ;
/***************************************************************************
* Get the current drive mask. *
***************************************************************************/
ULONG Drive ;
DosQueryCurrentDisk ( &Drive, &Data->Drives ) ;
/***************************************************************************
* Calibrate the old-style load meter, if the high resolution timer's *
* available. *
***************************************************************************/
Data->IniData.MaxCount = CalibrateLoadMeter ( &Data->IdleLoopParms ) ;
Data->IniData.MaxCount = (ULONG) max ( 1, Data->IniData.MaxCount ) ;
/***************************************************************************
* Get profile data. Try the OS2.INI first, then try for private INI. *
* If obtained from OS2.INI, erase it afterwards. *
***************************************************************************/
if ( GetIniData ( Data->Proc->QueryAnchor(), Data->Library->QueryHandle(), HINI_USERPROFILE, &Data->IniData ) ) {
GetIniData ( Data->Proc->QueryAnchor(), Data->Library->QueryHandle(), Data->IniFile->QueryHandle(), &Data->IniData ) ;
} else {
PrfWriteProfileData ( HINI_USERPROFILE, PSZ(PROGRAM_NAME), 0, 0, 0 ) ;
}
/***************************************************************************
* Get the frame handle. *
***************************************************************************/
HWND hwndFrame = WinQueryWindow ( hwnd, QW_PARENT ) ;
/***************************************************************************
* Get the control window handles. *
***************************************************************************/
Data->hwndSysMenu = WinWindowFromID ( hwndFrame, FID_SYSMENU ) ;
Data->hwndTitleBar = WinWindowFromID ( hwndFrame, FID_TITLEBAR ) ;
Data->hwndMinMax = WinWindowFromID ( hwndFrame, FID_MINMAX ) ;
/***************************************************************************
* Add basic extensions to the system menu. *
***************************************************************************/
static MENUITEM MenuSeparator =
{ MIT_END, MIS_SEPARATOR, 0, 0, 0, 0 } ;
AddSysMenuItem ( hwndFrame, &MenuSeparator, 0 ) ;
static MENUITEM MenuItems [] =
{
{ MIT_END, MIS_TEXT, 0, IDM_SAVE_APPLICATION, 0, 0 },
{ MIT_END, MIS_TEXT, 0, IDM_RESET_DEFAULTS, 0, 0 },
{ MIT_END, MIS_TEXT, 0, IDM_HIDE_CONTROLS, 0, 0 },
{ MIT_END, MIS_TEXT, 0, IDM_CONFIGURE, 0, 0 },
} ;
for ( int i=0; i<sizeof(MenuItems)/sizeof(MenuItems[0]); i++ ) {
ResourceString MenuText ( Data->Library->QueryHandle(), i+IDS_SAVE_APPLICATION ) ;
AddSysMenuItem ( hwndFrame, MenuItems+i, PSZ(MenuText) ) ;
}
AddSysMenuItem ( hwndFrame, &MenuSeparator, 0 ) ;
/***************************************************************************
* Add 'About' to the system menu. *
***************************************************************************/
static MENUITEM MenuAbout =
{ MIT_END, MIS_TEXT, 0, IDM_ABOUT, 0, 0 } ;
ResourceString AboutText ( Data->Library->QueryHandle(), IDS_ABOUT ) ;
AddSysMenuItem ( hwndFrame, &MenuAbout, PSZ(AboutText) ) ;
/***************************************************************************
* Add 'Help' to the system menu. *
***************************************************************************/
static MENUITEM MenuHelp =
{ MIT_END, MIS_HELP, 0, 0, 0, 0 } ;
ResourceString HelpText ( Data->Library->QueryHandle(), IDS_HELP ) ;
AddSysMenuItem ( hwndFrame, &MenuHelp, PSZ(HelpText) ) ;
/***************************************************************************
* Start the new load meter. *
***************************************************************************/
Data->IdleLoopParms.Active = TRUE ;
Data->IdleLoopTID = _beginthread ( CounterThread, NULL, 0x3000, &Data->IdleLoopParms ) ;
DosSuspendThread ( Data->IdleLoopTID ) ;
DosSetPriority ( PRTYS_THREAD, PRTYC_IDLETIME, PRTYD_MINIMUM, Data->IdleLoopTID ) ;
Data->IniData.IdleCount = 0 ;
Data->IdleLoopParms.Counter = 0 ;
if ( Data->IniData.Items[ITEM_CPULOAD]->QueryFlag() ) {
DosResumeThread ( Data->IdleLoopTID ) ;
}
Data->MonitorParms.Active = TRUE ;
Data->MonitorParms.Counter = & Data->IdleLoopParms.Counter ;
Data->MonitorParms.Interval = & Data->IniData.TimerInterval ;
Data->MonitorParms.Priority = & Data->IniData.MonitorPriority ;
Data->MonitorParms.Owner = hwnd ;
Data->MonitorTID = _beginthread ( MonitorLoopThread, NULL, 0x3000, &Data->MonitorParms ) ;
/***************************************************************************
* Add the program to the system task list. *
***************************************************************************/
ResourceString Title ( Data->Library->QueryHandle(), IDS_TITLE ) ;
Add2TaskList ( hwndFrame, PSZ(Title) ) ;
/***************************************************************************
* Position & size the window. For some reason, we must move and size *
* the window to the saved position before applying the resizing *
* function as fine-tuning. Maybe the positioning request fails if *
* the window has no size? *
***************************************************************************/
WinSetWindowPos ( hwndFrame, HWND_BOTTOM,
Data->IniData.Position.x, Data->IniData.Position.y,
Data->IniData.Position.cx, Data->IniData.Position.cy,
SWP_SIZE | SWP_MOVE | SWP_ZORDER |
( Data->IniData.Position.fl & SWP_MINIMIZE ) |
( Data->IniData.Position.fl & SWP_RESTORE ) ) ;
ResizeWindow ( hwnd, &Data->IniData ) ;
/***************************************************************************
* Hide the controls if so configured. *
***************************************************************************/
if ( Data->IniData.HideControls
AND NOT ( Data->IniData.Position.fl & SWP_MINIMIZE ) ) {
CheckMenuItem ( hwndFrame, FID_SYSMENU, IDM_HIDE_CONTROLS, Data->IniData.HideControls ) ;
HideControls
(
TRUE,
hwndFrame,
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
}
/***************************************************************************
* Get the saved presentation parameters and reinstate them. *
***************************************************************************/
if ( Data->IniData.fFontNameSize ) {
WinSetPresParam ( hwnd, PP_FONTNAMESIZE,
strlen(PCHAR(Data->IniData.FontNameSize))+1, Data->IniData.FontNameSize ) ;
}
if ( Data->IniData.fBackColor ) {
WinSetPresParam ( hwnd, PP_BACKGROUNDCOLOR,
sizeof(Data->IniData.BackColor), &Data->IniData.BackColor ) ;
}
if ( Data->IniData.fTextColor ) {
WinSetPresParam ( hwnd, PP_FOREGROUNDCOLOR,
sizeof(Data->IniData.TextColor), &Data->IniData.TextColor ) ;
}
/***************************************************************************
* Determine our font size. *
***************************************************************************/
HPS hPS = WinGetPS ( hwnd ) ;
RECTL Rectangle ;
WinQueryWindowRect ( HWND_DESKTOP, &Rectangle ) ;
WinDrawText ( hPS, 1, PSZ(" "), &Rectangle, 0L, 0L, DT_LEFT | DT_BOTTOM | DT_QUERYEXTENT ) ;
Data->Width = Rectangle.xRight - Rectangle.xLeft ;
Data->Height = Rectangle.yTop - Rectangle.yBottom ;
WinReleasePS ( hPS ) ;
/***************************************************************************
* Now that the window's in order, make it visible. *
***************************************************************************/
WinShowWindow ( hwndFrame, TRUE ) ;
/***************************************************************************
* Success? Return no error. *
***************************************************************************/
return ( 0 ) ;
}
/****************************************************************************
* *
* Destroy main window. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Destroy ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Kill the extra threads. *
***************************************************************************/
DosResumeThread ( Data->MonitorTID ) ;
Data->MonitorParms.Active = FALSE ;
DosWaitThread ( &Data->MonitorTID, DCWW_WAIT ) ;
DosResumeThread ( Data->IdleLoopTID ) ;
Data->IdleLoopParms.Active = FALSE ;
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MAXIMUM, Data->IdleLoopTID ) ;
DosWaitThread ( &Data->IdleLoopTID, DCWW_WAIT ) ;
/***************************************************************************
* Release the instance memory. *
***************************************************************************/
free ( Data ) ;
/***************************************************************************
* We're done. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process window resize message. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Size ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Find out the window's new position and size. *
***************************************************************************/
HWND hwndFrame = WinQueryWindow ( hwnd, QW_PARENT ) ;
SWP Position ;
WinQueryWindowPos ( hwndFrame, &Position ) ;
if ( NOT ( Position.fl & SWP_MINIMIZE )
AND NOT ( Position.fl & SWP_MAXIMIZE ) ) {
Data->IniData.Position.x = Position.x ;
Data->IniData.Position.y = Position.y ;
Data->IniData.Position.cx = Position.cx ;
Data->IniData.Position.cy = Position.cy ;
}
/***************************************************************************
* If hiding the controls . . . *
***************************************************************************/
if ( Data->IniData.HideControls ) {
/*************************************************************************
* If changing to or from minimized state . . . *
*************************************************************************/
if ( ( Position.fl & SWP_MINIMIZE ) != ( Data->IniData.Position.fl & SWP_MINIMIZE ) )
{
/***********************************************************************
* Hide the controls if no longer minimized. *
***********************************************************************/
HideControls
(
NOT ( Position.fl & SWP_MINIMIZE ),
hwndFrame,
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
}
}
Data->IniData.Position.fl = Position.fl ;
/***************************************************************************
* We're done. *
***************************************************************************/
return ( 0 ) ;
}
/****************************************************************************
* *
* Process SAVE APPLICATION message. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY SaveApplication ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Call function to put all profile data out to the system. *
***************************************************************************/
PutIniData ( Data->IniFile->QueryHandle(), &Data->IniData ) ;
/***************************************************************************
* We're done. Let the system complete default processing. *
***************************************************************************/
return ( WinDefWindowProc ( hwnd, WM_SAVEAPPLICATION, 0, 0 ) ) ;
}
/****************************************************************************
* *
* Repaint entire window. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Paint ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Get presentation space and make it use RGB colors. *
***************************************************************************/
HPS hPS = WinBeginPaint ( hwnd, HPS(NULL), PRECTL(NULL) ) ;
GpiCreateLogColorTable ( hPS, LCOL_RESET, LCOLF_RGB, 0L, 0L, PLONG(NULL) ) ;
/***************************************************************************
* Clear the window. *
***************************************************************************/
RECTL Rectangle ;
WinQueryWindowRect ( hwnd, &Rectangle ) ;
GpiMove ( hPS, (PPOINTL) &Rectangle.xLeft ) ;
GpiSetColor ( hPS, Data->IniData.BackColor ) ;
GpiBox ( hPS, DRO_FILL, (PPOINTL) &Rectangle.xRight, 0L, 0L ) ;
/***************************************************************************
* Release presentation space. *
***************************************************************************/
WinEndPaint ( hPS ) ;
/***************************************************************************
* Update the window and return. *
***************************************************************************/
UpdateWindow ( hwnd, Data, TRUE ) ;
return ( 0 ) ;
}
/****************************************************************************
* *
* Process commands received by Main Window *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Command ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Dispatch all other commands through the method table. *
***************************************************************************/
static METHOD Methods [] =
{
{ IDM_SAVE_APPLICATION, SaveApplication },
{ IDM_RESET_DEFAULTS, ResetDefaults },
{ IDM_HIDE_CONTROLS, HideControlsCmd },
{ IDM_CONFIGURE, Configure },
{ IDM_EXIT, Exit },
{ IDM_ABOUT, About },
} ;
return ( DispatchMessage ( hwnd, SHORT1FROMMP(mp1), mp1, mp2, Methods, sizeof(Methods)/sizeof(Methods[0]), PFNWP(NULL) ) ) ;
}
/****************************************************************************
* *
* Process Reset Defaults menu command. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY ResetDefaults ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Reset all profile data for this program. *
***************************************************************************/
PrfWriteProfileData ( Data->IniFile->QueryHandle(), PSZ(PROGRAM_NAME), 0, 0, 0 ) ;
/***************************************************************************
* Reset the program's presentation parameters. *
***************************************************************************/
WinRemovePresParam ( hwnd, PP_FONTNAMESIZE ) ;
WinRemovePresParam ( hwnd, PP_FOREGROUNDCOLOR ) ;
WinRemovePresParam ( hwnd, PP_BACKGROUNDCOLOR ) ;
/***************************************************************************
* Done. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process Hide Controls menu command. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY HideControlsCmd ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Toggle the Hide Controls setting. *
***************************************************************************/
Data->IniData.HideControls = Data->IniData.HideControls ? FALSE : TRUE ;
Data->IniData.fHideControls = TRUE ;
/***************************************************************************
* Get the frame handle. *
***************************************************************************/
HWND hwndFrame = WinQueryWindow ( hwnd, QW_PARENT ) ;
/***************************************************************************
* If controls aren't hidden yet, update the menu check-mark. *
***************************************************************************/
if ( Data->IniData.HideControls )
CheckMenuItem ( hwndFrame, FID_SYSMENU, IDM_HIDE_CONTROLS, Data->IniData.HideControls ) ;
/***************************************************************************
* If not minimized right now, hide or reveal the controls. *
***************************************************************************/
if ( NOT ( Data->IniData.Position.fl & SWP_MINIMIZE ) )
{
HideControls
(
Data->IniData.HideControls,
hwndFrame,
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
}
/***************************************************************************
* If controls are no longer hidden, update the menu check-mark. *
***************************************************************************/
if ( NOT Data->IniData.HideControls )
CheckMenuItem ( hwndFrame, FID_SYSMENU, IDM_HIDE_CONTROLS, Data->IniData.HideControls ) ;
/***************************************************************************
* Done. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process Configure command. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Configure ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Invoke the Configure dialog. If cancelled, just return. *
***************************************************************************/
CONFIG_PARMS Parms ;
Parms.id = IDD_CONFIGURE ;
Parms.hwndHelp = WinQueryHelpInstance ( hwnd ) ;
Parms.HideControls = Data->IniData.HideControls ;
Parms.Float = Data->IniData.Float ;
Parms.Animate = Data->IniData.Animate ;
Parms.ShowFileSystemNames = Data->IniData.ShowFileSystemNames ;
Parms.MonitorPriority = Data->IniData.MonitorPriority ;
Parms.TimerInterval = Data->IniData.TimerInterval ;
Parms.ItemCount = Data->IniData.ItemCount ;
PSZ ItemNames [ ITEM_BASE_COUNT + MAX_DRIVES ] ;
BOOL ItemFlags [ ITEM_BASE_COUNT + MAX_DRIVES ] ;
for ( int i=0; i<Data->IniData.ItemCount; i++ )
{
ItemNames[i] = Data->IniData.Items[i]->QueryOption () ;
ItemFlags[i] = Data->IniData.Items[i]->QueryFlag () ;
}
Parms.ItemNames = ItemNames ;
Parms.ItemFlags = ItemFlags ;
if ( WinDlgBox ( HWND_DESKTOP, hwnd, PFNWP(ConfigureProcessor),
Data->Library->QueryHandle(), IDD_CONFIGURE, &Parms ) == FALSE )
{
return ( MRFROMSHORT ( 0 ) ) ;
}
/***************************************************************************
* Save the new monitor priority. *
***************************************************************************/
Data->IniData.fMonitorPriority = TRUE ;
Data->IniData.MonitorPriority = Parms.MonitorPriority ;
/***************************************************************************
* Save the new timer interval. *
***************************************************************************/
Data->IniData.fTimerInterval = TRUE ;
Data->IniData.TimerInterval = Parms.TimerInterval ;
/***************************************************************************
* Save the float-to-top flag. *
***************************************************************************/
Data->IniData.fFloat = TRUE ;
Data->IniData.Float = Parms.Float ;
/***************************************************************************
* Save the window animate flag. *
***************************************************************************/
Data->IniData.fAnimate = TRUE ;
Data->IniData.Animate = Parms.Animate ;
/***************************************************************************
* Save the hide controls flag, and adjust the window if it changed. *
***************************************************************************/
Data->IniData.fHideControls = TRUE ;
if ( Data->IniData.HideControls != Parms.HideControls ) {
HWND FrameWindow = WinQueryWindow ( hwnd, QW_PARENT ) ;
Data->IniData.HideControls = Parms.HideControls ;
if ( Data->IniData.HideControls )
CheckMenuItem ( FrameWindow, FID_SYSMENU, IDM_HIDE_CONTROLS, Data->IniData.HideControls ) ;
if ( NOT ( Data->IniData.Position.fl & SWP_MINIMIZE ) ) {
HideControls
(
Data->IniData.HideControls,
FrameWindow,
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
}
if ( NOT Data->IniData.HideControls )
CheckMenuItem ( FrameWindow, FID_SYSMENU, IDM_HIDE_CONTROLS, Data->IniData.HideControls ) ;
}
/***************************************************************************
* Determine if the display item list has changed. If not, return. *
***************************************************************************/
BOOL ItemsChanged = FALSE ;
for ( i=0; i<Data->IniData.ItemCount; i++ ) {
if ( ItemFlags[i] != Data->IniData.Items[i]->QueryFlag() ) {
ItemsChanged = TRUE ;
break ;
}
}
if ( NOT ItemsChanged AND ( Data->IniData.ShowFileSystemNames == Parms.ShowFileSystemNames ) ) {
return ( MRFROMSHORT ( 0 ) ) ;
}
/***************************************************************************
* Save the show file-system names flag. *
***************************************************************************/
Data->IniData.fShowFileSystemNames = TRUE ;
Data->IniData.ShowFileSystemNames = Parms.ShowFileSystemNames ;
for ( i=ITEM_BASE_COUNT; i<Data->IniData.ItemCount; i++ ) {
((DriveFree*)Data->IniData.Items[i])->SetShowFileSystemName ( Data->IniData.ShowFileSystemNames ) ;
} /* endfor */
/***************************************************************************
* If CPU load monitoring has changed, start/stop the monitoring thread. *
***************************************************************************/
if ( ItemFlags[ITEM_CPULOAD] != Data->IniData.Items[ITEM_CPULOAD]->QueryFlag() ) {
if ( ItemFlags[ITEM_CPULOAD] )
DosResumeThread ( Data->IdleLoopTID ) ;
else
DosSuspendThread ( Data->IdleLoopTID ) ;
}
/***************************************************************************
* Save the new item flags. *
***************************************************************************/
for ( i=0; i<Data->IniData.ItemCount; i++ ) {
if ( ItemFlags[i] )
Data->IniData.Items[i]->SetFlag ( ) ;
else
Data->IniData.Items[i]->ResetFlag ( ) ;
}
/***************************************************************************
* Resize the display window. *
***************************************************************************/
ResizeWindow ( hwnd, &Data->IniData ) ;
/***************************************************************************
* Done. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process About menu command. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY About ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Invoke the About dialog. *
***************************************************************************/
ABOUT_PARMS Parms ;
Parms.id = IDD_ABOUT ;
Parms.hwndHelp = WinQueryHelpInstance ( hwnd ) ;
WinDlgBox ( HWND_DESKTOP, hwnd, PFNWP(AboutProcessor),
Data->Library->QueryHandle(), IDD_ABOUT, &Parms ) ;
/***************************************************************************
* Done. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process Mouse Button being pressed. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY ButtonDown ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Determine the new window position. *
***************************************************************************/
TRACKINFO TrackInfo ;
memset ( &TrackInfo, 0, sizeof(TrackInfo) ) ;
TrackInfo.cxBorder = 1 ;
TrackInfo.cyBorder = 1 ;
TrackInfo.cxGrid = 1 ;
TrackInfo.cyGrid = 1 ;
TrackInfo.cxKeyboard = 8 ;
TrackInfo.cyKeyboard = 8 ;
HWND hwndFrame = WinQueryWindow ( hwnd, QW_PARENT ) ;
SWP Position ;
WinQueryWindowPos ( hwndFrame, &Position ) ;
TrackInfo.rclTrack.xLeft = Position.x ;
TrackInfo.rclTrack.xRight = Position.x + Position.cx ;
TrackInfo.rclTrack.yBottom = Position.y ;
TrackInfo.rclTrack.yTop = Position.y + Position.cy ;
WinQueryWindowPos ( HWND_DESKTOP, &Position ) ;
TrackInfo.rclBoundary.xLeft = Position.x ;
TrackInfo.rclBoundary.xRight = Position.x + Position.cx ;
TrackInfo.rclBoundary.yBottom = Position.y ;
TrackInfo.rclBoundary.yTop = Position.y + Position.cy ;
TrackInfo.ptlMinTrackSize.x = 0 ;
TrackInfo.ptlMinTrackSize.y = 0 ;
TrackInfo.ptlMaxTrackSize.x = Position.cx ;
TrackInfo.ptlMaxTrackSize.y = Position.cy ;
TrackInfo.fs = TF_MOVE | TF_STANDARD | TF_ALLINBOUNDARY ;
if ( WinTrackRect ( HWND_DESKTOP, HPS(NULL), &TrackInfo ) )
{
WinSetWindowPos ( hwndFrame, 0,
(SHORT) TrackInfo.rclTrack.xLeft,
(SHORT) TrackInfo.rclTrack.yBottom,
0, 0, SWP_MOVE ) ;
}
/***************************************************************************
* Return through the default processor, letting window activation *
* and other system functions occur. *
***************************************************************************/
return ( WinDefWindowProc ( hwnd, msg, mp1, mp2 ) ) ;
}
/****************************************************************************
* *
* Process Mouse Button having been double-clicked. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY ButtonDblClick ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Send message to self to stop hiding the controls. *
***************************************************************************/
WinPostMsg ( hwnd, WM_COMMAND,
MPFROM2SHORT ( IDM_HIDE_CONTROLS, 0 ),
MPFROM2SHORT ( CMDSRC_OTHER, TRUE ) ) ;
/***************************************************************************
* Return through the default processor, letting window activation *
* and other system functions occur. *
***************************************************************************/
return ( WinDefWindowProc ( hwnd, msg, mp1, mp2 ) ) ;
}
/****************************************************************************
* *
* Process Presentation Parameter Changed notification. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY PresParamChanged ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Get the presentation parameter that changed. *
***************************************************************************/
switch ( LONGFROMMP(mp1) )
{
/*************************************************************************
* If font, note the fact that we now have a font to be saved as *
* part of the configuration. Get the font metrics and resize *
* the window appropriately. *
*************************************************************************/
case PP_FONTNAMESIZE:
{
ULONG ppid ;
if ( WinQueryPresParam ( hwnd, PP_FONTNAMESIZE, 0, &ppid,
sizeof(Data->IniData.FontNameSize), &Data->IniData.FontNameSize,
0 ) )
{
Data->IniData.fFontNameSize = TRUE ;
}
else
{
strcpy ( PCHAR(Data->IniData.FontNameSize), "" ) ;
Data->IniData.fFontNameSize = FALSE ;
PrfWriteProfileData ( Data->IniFile->QueryHandle(), PSZ(PROGRAM_NAME), PSZ("FontNameSize"), NULL, 0 ) ;
}
HPS hPS = WinGetPS ( hwnd ) ;
RECTL Rectangle ;
WinQueryWindowRect ( HWND_DESKTOP, &Rectangle ) ;
WinDrawText ( hPS, 1, PSZ(" "), &Rectangle, 0L, 0L, DT_LEFT | DT_BOTTOM | DT_QUERYEXTENT ) ;
Data->Width = Rectangle.xRight - Rectangle.xLeft ;
Data->Height = Rectangle.yTop - Rectangle.yBottom ;
WinReleasePS ( hPS ) ;
ResizeWindow ( hwnd, &Data->IniData ) ;
break ;
}
/*************************************************************************
* If background color, note the fact and repaint the window. *
*************************************************************************/
case PP_BACKGROUNDCOLOR:
{
ULONG ppid ;
if ( WinQueryPresParam ( hwnd, PP_BACKGROUNDCOLOR, 0, &ppid,
sizeof(Data->IniData.BackColor), &Data->IniData.BackColor, 0 ) )
{
Data->IniData.fBackColor = TRUE ;
}
else
{
Data->IniData.BackColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_WINDOW, 0L ) ;
Data->IniData.fBackColor = FALSE ;
PrfWriteProfileData ( Data->IniFile->QueryHandle(), PSZ(PROGRAM_NAME), PSZ("BackgroundColor"), NULL, 0 ) ;
}
WinInvalidateRect ( hwnd, PRECTL(NULL), TRUE ) ;
break ;
}
/*************************************************************************
* If foreground color, note the fact and repaint the window. *
*************************************************************************/
case PP_FOREGROUNDCOLOR:
{
ULONG ppid ;
if ( WinQueryPresParam ( hwnd, PP_FOREGROUNDCOLOR, 0, &ppid,
sizeof(Data->IniData.TextColor), &Data->IniData.TextColor, 0 ) )
{
Data->IniData.fTextColor = TRUE ;
}
else
{
Data->IniData.TextColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_OUTPUTTEXT, 0L ) ;
Data->IniData.fTextColor = FALSE ;
PrfWriteProfileData ( Data->IniFile->QueryHandle(), PSZ(PROGRAM_NAME), PSZ("ForegroundColor"), NULL, 0 ) ;
}
WinInvalidateRect ( hwnd, PRECTL(NULL), TRUE ) ;
break ;
}
}
/***************************************************************************
* Return through the default processor, letting window activation *
* and other system functions occur. *
***************************************************************************/
return ( WinDefWindowProc ( hwnd, msg, mp1, mp2 ) ) ;
}
/****************************************************************************
* *
* Process System Color Change notification. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY SysColorChange ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* If we aren't using custom colors, then query for the new defaults. *
***************************************************************************/
if ( NOT Data->IniData.fBackColor )
{
Data->IniData.BackColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_WINDOW, 0L ) ;
}
if ( NOT Data->IniData.fTextColor )
{
Data->IniData.TextColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_OUTPUTTEXT, 0L ) ;
}
/***************************************************************************
* Return value must be NULL, according to the documentation. *
***************************************************************************/
return ( MRFROMP ( NULL ) ) ;
}
/****************************************************************************
* *
* Process Query for Keys Help resource id. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY QueryKeysHelp ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Simply return the ID of the Keys Help panel. *
***************************************************************************/
return ( (MRESULT) IDM_KEYS_HELP ) ;
}
/****************************************************************************
* *
* Process Help Manager Error *
* *
****************************************************************************/
STATIC MRESULT APIENTRY HelpError ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Local Declarations *
***************************************************************************/
static struct
{
ULONG Error ;
USHORT StringId ;
}
HelpErrors [] =
{
{ HMERR_NO_FRAME_WND_IN_CHAIN, IDS_HMERR_NO_FRAME_WND_IN_CHAIN },
{ HMERR_INVALID_ASSOC_APP_WND, IDS_HMERR_INVALID_ASSOC_APP_WND },
{ HMERR_INVALID_ASSOC_HELP_INST, IDS_HMERR_INVALID_ASSOC_HELP_IN },
{ HMERR_INVALID_DESTROY_HELP_INST, IDS_HMERR_INVALID_DESTROY_HELP_ },
{ HMERR_NO_HELP_INST_IN_CHAIN, IDS_HMERR_NO_HELP_INST_IN_CHAIN },
{ HMERR_INVALID_HELP_INSTANCE_HDL, IDS_HMERR_INVALID_HELP_INSTANCE },
{ HMERR_INVALID_QUERY_APP_WND, IDS_HMERR_INVALID_QUERY_APP_WND },
{ HMERR_HELP_INST_CALLED_INVALID, IDS_HMERR_HELP_INST_CALLED_INVA },
{ HMERR_HELPTABLE_UNDEFINE, IDS_HMERR_HELPTABLE_UNDEFINE },
{ HMERR_HELP_INSTANCE_UNDEFINE, IDS_HMERR_HELP_INSTANCE_UNDEFIN },
{ HMERR_HELPITEM_NOT_FOUND, IDS_HMERR_HELPITEM_NOT_FOUND },
{ HMERR_INVALID_HELPSUBITEM_SIZE, IDS_HMERR_INVALID_HELPSUBITEM_S },
{ HMERR_HELPSUBITEM_NOT_FOUND, IDS_HMERR_HELPSUBITEM_NOT_FOUND },
{ HMERR_INDEX_NOT_FOUND, IDS_HMERR_INDEX_NOT_FOUND },
{ HMERR_CONTENT_NOT_FOUND, IDS_HMERR_CONTENT_NOT_FOUND },
{ HMERR_OPEN_LIB_FILE, IDS_HMERR_OPEN_LIB_FILE },
{ HMERR_READ_LIB_FILE, IDS_HMERR_READ_LIB_FILE },
{ HMERR_CLOSE_LIB_FILE, IDS_HMERR_CLOSE_LIB_FILE },
{ HMERR_INVALID_LIB_FILE, IDS_HMERR_INVALID_LIB_FILE },
{ HMERR_NO_MEMORY, IDS_HMERR_NO_MEMORY },
{ HMERR_ALLOCATE_SEGMENT, IDS_HMERR_ALLOCATE_SEGMENT },
{ HMERR_FREE_MEMORY, IDS_HMERR_FREE_MEMORY },
{ HMERR_PANEL_NOT_FOUND, IDS_HMERR_PANEL_NOT_FOUND },
{ HMERR_DATABASE_NOT_OPEN, IDS_HMERR_DATABASE_NOT_OPEN },
{ 0, IDS_HMERR_UNKNOWN }
} ;
ULONG ErrorCode = (ULONG) LONGFROMMP ( mp1 ) ;
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Find the error code in the message table. *
***************************************************************************/
int Index = 0 ;
while ( HelpErrors[Index].Error
AND ( HelpErrors[Index].Error != ErrorCode ) )
{
Index ++ ;
}
/***************************************************************************
* Get the message texts. *
***************************************************************************/
ResourceString Title ( Data->Library->QueryHandle(), IDS_HMERR ) ;
ResourceString Message ( Data->Library->QueryHandle(), HelpErrors[Index].StringId ) ;
/***************************************************************************
* Display the error message. *
***************************************************************************/
WinMessageBox
(
HWND_DESKTOP,
hwnd,
PSZ(Message),
PSZ(Title),
0,
MB_OK | MB_WARNING
) ;
/***************************************************************************
* Return zero, indicating that the message was processed. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process "Extended Help Undefined" notification *
* *
****************************************************************************/
STATIC MRESULT APIENTRY ExtHelpUndefined ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Get the message texts. *
***************************************************************************/
ResourceString Title ( Data->Library->QueryHandle(), IDS_HMERR ) ;
ResourceString Message ( Data->Library->QueryHandle(), IDS_HMERR_EXTHELPUNDEFINED ) ;
/***************************************************************************
* Display the error message. *
***************************************************************************/
WinMessageBox
(
HWND_DESKTOP,
hwnd,
PSZ(Message),
PSZ(Title),
0,
MB_OK | MB_WARNING
) ;
/***************************************************************************
* Return zero, indicating that the message was processed. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process "Help Subitem Not Found" notification *
* *
****************************************************************************/
STATIC MRESULT APIENTRY HelpSubitemNotFound ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* Get the title text. *
***************************************************************************/
ResourceString Title ( Data->Library->QueryHandle(), IDS_HMERR ) ;
/***************************************************************************
* Format the error message. *
***************************************************************************/
USHORT Topic = (USHORT) SHORT1FROMMP ( mp2 ) ;
USHORT Subtopic = (USHORT) SHORT2FROMMP ( mp2 ) ;
ResourceString Frame ( Data->Library->QueryHandle(), IDS_HELPMODE_FRAME ) ;
ResourceString Menu ( Data->Library->QueryHandle(), IDS_HELPMODE_MENU ) ;
ResourceString Window ( Data->Library->QueryHandle(), IDS_HELPMODE_WINDOW ) ;
ResourceString Unknown ( Data->Library->QueryHandle(), IDS_HELPMODE_UNKNOWN ) ;
PBYTE Mode ;
switch ( SHORT1FROMMP ( mp1 ) )
{
case HLPM_FRAME:
Mode = PSZ(Frame) ;
break ;
case HLPM_MENU:
Mode = PSZ(Menu) ;
break ;
case HLPM_WINDOW:
Mode = PSZ(Window) ;
break ;
default:
Mode = PSZ(Unknown) ;
}
ResourceString Format ( Data->Library->QueryHandle(), IDS_HELPSUBITEMNOTFOUND ) ;
BYTE Message [200] ;
sprintf ( PCHAR(Message), PCHAR(Format), Mode, Topic, Subtopic ) ;
/***************************************************************************
* Display the error message. *
***************************************************************************/
WinMessageBox
(
HWND_DESKTOP,
hwnd,
Message,
PSZ(Title),
0,
MB_OK | MB_WARNING
) ;
/***************************************************************************
* Return zero, indicating that the message was processed. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Process Refresh message. *
* *
****************************************************************************/
STATIC MRESULT APIENTRY Refresh ( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 ) {
/***************************************************************************
* Find the instance data. *
***************************************************************************/
PDATA Data = PDATA ( WinQueryWindowPtr ( hwnd, QWL_USER ) ) ;
/***************************************************************************
* If we're supposed to float the window, do so here. *
***************************************************************************/
if ( Data->IniData.Float )
WinSetWindowPos ( WinQueryWindow(hwnd,QW_PARENT), HWND_TOP, 0, 0, 0, 0, SWP_ZORDER ) ;
/***************************************************************************
* Save the idle counter. *
***************************************************************************/
Data->IniData.IdleCount = LONGFROMMP ( mp1 ) ;
/***************************************************************************
* Determine if drive mask has changed. *
***************************************************************************/
ULONG Drive ;
ULONG Drives ;
DosQueryCurrentDisk ( &Drive, &Drives ) ;
if ( Drives != Data->Drives ) {
/*************************************************************************
* It has. First save the display options. *
*************************************************************************/
SaveApplication ( hwnd, WM_SAVEAPPLICATION, 0, 0 ) ;
/*************************************************************************
* Next, update the drive item list. *
*************************************************************************/
UpdateDriveList ( Data->Proc->QueryAnchor(), Data->Library->QueryHandle(), Data->IniFile->QueryHandle(),
&Data->IniData, Data->Drives, Drives ) ;
/*************************************************************************
* If the controls are hidden, hide the whole window and reveal the *
* controls. Otherwise the menu wouldn't get updated correctly. *
*************************************************************************/
if ( Data->IniData.HideControls ) {
WinShowWindow ( WinQueryWindow(hwnd,QW_PARENT), FALSE ) ;
HideControls
(
FALSE,
WinQueryWindow ( hwnd, QW_PARENT ),
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
}
/*************************************************************************
* If the controls were supposed to be hidden, hide them once more and *
* show the window to the world again. *
*************************************************************************/
if ( Data->IniData.HideControls ) {
HideControls
(
TRUE,
WinQueryWindow ( hwnd, QW_PARENT ),
Data->hwndSysMenu,
Data->hwndTitleBar,
Data->hwndMinMax
) ;
WinShowWindow ( WinQueryWindow(hwnd,QW_PARENT), TRUE ) ;
}
/*************************************************************************
* Save the updated drive mask. *
*************************************************************************/
Data->Drives = Drives ;
/*************************************************************************
* Resize the window to accommodate the new option list. *
*************************************************************************/
ResizeWindow ( hwnd, &Data->IniData ) ;
}
/***************************************************************************
* Update the statistics. *
***************************************************************************/
UpdateWindow ( hwnd, Data, FALSE ) ;
/***************************************************************************
* Return zero, indicating that the message was processed. *
***************************************************************************/
return ( MRFROMSHORT ( 0 ) ) ;
}
/****************************************************************************
* *
* Get IniData Data *
* *
****************************************************************************/
STATIC int GetIniData ( HAB Anchor, HMODULE Library, HINI IniHandle, PINIDATA IniData ) {
/***************************************************************************
* Get the window's current size and position. *
***************************************************************************/
#pragma pack(2)
typedef struct {
USHORT Filler ;
USHORT fs ;
USHORT cy, cx, y, x ;
HWND hwndInsertBehind ;
HWND hwnd ;
} OLDSWP ;
#pragma pack()
ULONG Size ;
memset ( &IniData->Position, 0, sizeof(IniData->Position) ) ;
IniData->fPosition = FALSE ;
if ( PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Position"), &Size ) )
{
if ( Size == sizeof(OLDSWP)-sizeof(USHORT) )
{
OLDSWP OldPosition ;
if ( PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Position"), &OldPosition.fs, &Size ) )
{
IniData->Position.fl = OldPosition.fs ;
IniData->Position.cy = OldPosition.cy ;
IniData->Position.cx = OldPosition.cx ;
IniData->Position.y = OldPosition.y ;
IniData->Position.x = OldPosition.x ;
IniData->Position.hwndInsertBehind = OldPosition.hwndInsertBehind ;
IniData->Position.hwnd = OldPosition.hwnd ;
IniData->fPosition = TRUE ;
}
}
else if ( Size == sizeof(IniData->Position) )
{
if ( PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Position"), &IniData->Position, &Size ) )
{
IniData->fPosition = TRUE ;
}
}
}
if ( NOT IniData->fPosition )
{
if ( IniHandle == HINI_USERPROFILE )
{
return ( 1 ) ;
}
}
/***************************************************************************
* Get the program options. *
***************************************************************************/
IniData->HideControls = FALSE ;
IniData->fHideControls = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("HideControls"), &Size )
AND
( ( Size == sizeof(IniData->HideControls) ) OR ( Size == sizeof(short) ) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("HideControls"), &IniData->HideControls, &Size )
)
{
IniData->fHideControls = TRUE ;
}
IniData->Float = FALSE ;
IniData->fFloat = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Float"), &Size )
AND
( Size == sizeof(IniData->Float) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Float"), &IniData->Float, &Size )
)
{
IniData->fFloat = TRUE ;
}
IniData->Animate = FALSE ;
IniData->fAnimate = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Animate"), &Size )
AND
( Size == sizeof(IniData->Animate) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("Animate"), &IniData->Animate, &Size )
)
{
IniData->fAnimate = TRUE ;
}
IniData->ShowFileSystemNames = TRUE ;
IniData->fShowFileSystemNames = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("ShowFileSystemNames"), &Size )
AND
( Size == sizeof(IniData->ShowFileSystemNames) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("ShowFileSystemNames"), &IniData->ShowFileSystemNames, &Size )
)
{
IniData->fShowFileSystemNames = TRUE ;
}
IniData->MonitorPriority = PRTYD_MAXIMUM ;
IniData->fMonitorPriority = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("MonitorPriority"), &Size )
AND
( Size == sizeof(IniData->MonitorPriority) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("MonitorPriority"), &IniData->MonitorPriority, &Size )
)
{
IniData->fMonitorPriority = TRUE ;
}
IniData->TimerInterval = 1000 ;
IniData->fTimerInterval = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("TimerInterval"), &Size )
AND
( ( Size == sizeof(IniData->TimerInterval) ) OR ( Size == sizeof(short) ) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("TimerInterval"), &IniData->TimerInterval, &Size )
)
{
IniData->fTimerInterval = TRUE ;
}
/***************************************************************************
* Get the presentation parameters. *
***************************************************************************/
strcpy ( PCHAR(IniData->FontNameSize), "" ) ;
IniData->fFontNameSize = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("FontNameSize"), &Size )
AND
( Size == sizeof(IniData->FontNameSize) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("FontNameSize"), &IniData->FontNameSize, &Size )
)
{
IniData->fFontNameSize = TRUE ;
}
IniData->BackColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_WINDOW, 0L ) ;
IniData->fBackColor = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("BackgroundColor"), &Size )
AND
( Size == sizeof(IniData->BackColor) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("BackgroundColor"), &IniData->BackColor, &Size )
)
{
IniData->fBackColor = TRUE ;
}
IniData->TextColor = WinQuerySysColor ( HWND_DESKTOP, SYSCLR_OUTPUTTEXT, 0L ) ;
IniData->fTextColor = FALSE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), PSZ("ForegroundColor"), &Size )
AND
( Size == sizeof(IniData->TextColor) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), PSZ("ForegroundColor"), &IniData->TextColor, &Size )
)
{
IniData->fTextColor = TRUE ;
}
/***************************************************************************
* Initialize the global resource strings. *
***************************************************************************/
IniData->Day = new ResourceString ( Library, IDS_DAY ) ;
IniData->Days = new ResourceString ( Library, IDS_DAYS ) ;
IniData->DaysOfWeek = new ResourceString ( Library, IDS_DAYSOFWEEK ) ;
IniData->DriveError = new ResourceString ( Library, IDS_DRIVEERROR ) ;
/***************************************************************************
* Get country information. *
***************************************************************************/
COUNTRYCODE CountryCode ;
ULONG Count ;
ULONG Status ;
CountryCode.country = 0 ;
CountryCode.codepage = 0 ;
Status = DosGetCtryInfo ( sizeof(IniData->CountryInfo), &CountryCode,
&IniData->CountryInfo, &Count ) ;
if ( Status )
{
IniData->CountryInfo.fsDateFmt = DATEFMT_MM_DD_YY ;
IniData->CountryInfo.fsTimeFmt = 0 ;
IniData->CountryInfo.szDateSeparator[0] = '/' ;
IniData->CountryInfo.szDateSeparator[1] = 0 ;
IniData->CountryInfo.szTimeSeparator[0] = ':' ;
IniData->CountryInfo.szTimeSeparator[1] = 0 ;
IniData->CountryInfo.szThousandsSeparator[0] = ',' ;
IniData->CountryInfo.szThousandsSeparator[1] = 0 ;
}
/***************************************************************************
* Get the SWAPPATH statement from CONFIG.SYS. *
***************************************************************************/
PSZ Swappath = ScanSystemConfig ( Anchor, PSZ("SWAPPATH") ) ;
if ( Swappath == NULL ) {
Swappath = PSZ("C:\\OS2\\SYSTEM 0") ;
}
sscanf ( PCHAR(Swappath), "%s %li",
IniData->SwapPath, &IniData->MinFree ) ;
/***************************************************************************
* Find out where the spool work directory is. *
***************************************************************************/
IniData->SpoolPath = 0 ;
if ( PrfQueryProfileSize ( HINI_PROFILE, PSZ("PM_SPOOLER"), PSZ("DIR"), &Size ) )
{
IniData->SpoolPath = PSZ ( malloc ( (int)Size ) ) ;
if ( IniData->SpoolPath )
{
if ( PrfQueryProfileData ( HINI_PROFILE, PSZ("PM_SPOOLER"), PSZ("DIR"), IniData->SpoolPath, &Size ) )
{
PBYTE p = PBYTE( strchr ( PCHAR(IniData->SpoolPath), ';' ) ) ;
if ( p )
{
*p = 0 ;
}
}
else
{
free ( IniData->SpoolPath ) ;
IniData->SpoolPath = 0 ;
}
}
}
if ( IniData->SpoolPath == 0 )
IniData->SpoolPath = PSZ ( "C:\\SPOOL" ) ;
/***************************************************************************
* Build the fixed portion of the item list. *
***************************************************************************/
ResourceString ClockLabel ( Library, IDS_SHOW_CLOCK_LABEL ) ;
ResourceString ClockOption ( Library, IDS_SHOW_CLOCK_OPTION ) ;
IniData->Items[ITEM_CLOCK] = new Clock ( ITEM_CLOCK,
PSZ("ShowClock"), PSZ(ClockLabel), PSZ(ClockOption),
IniData->CountryInfo, IniData->DaysOfWeek ) ;
ResourceString ElapsedLabel ( Library, IDS_SHOW_ELAPSED_LABEL ) ;
ResourceString ElapsedOption ( Library, IDS_SHOW_ELAPSED_OPTION ) ;
IniData->Items[ITEM_ELAPSEDTIME] = new ElapsedTime ( ITEM_ELAPSEDTIME,
PSZ("ShowElapsed"), PSZ(ElapsedLabel), PSZ(ElapsedOption),
IniData->CountryInfo,
IniData->Day,
IniData->Days ) ;
ResourceString SwapSizeLabel ( Library, IDS_SHOW_SWAPSIZE_LABEL ) ;
ResourceString SwapSizeOption ( Library, IDS_SHOW_SWAPSIZE_OPTION ) ;
IniData->Items[ITEM_SWAPFILESIZE] = new SwapSize ( ITEM_SWAPFILESIZE,
PSZ("ShowSwapsize"), PSZ(SwapSizeLabel), PSZ(SwapSizeOption),
IniData->CountryInfo,
IniData->SwapPath ) ;
ResourceString SwapFreeLabel ( Library, IDS_SHOW_SWAPFREE_LABEL ) ;
ResourceString SwapFreeOption ( Library, IDS_SHOW_SWAPFREE_OPTION ) ;
IniData->Items[ITEM_SWAPDISKFREE] = new SwapFree ( ITEM_SWAPDISKFREE,
PSZ("ShowSwapfree"), PSZ(SwapFreeLabel), PSZ(SwapFreeOption),
IniData->CountryInfo,
IniData->SwapPath,
IniData->MinFree ) ;
ResourceString MemoryLabel ( Library, IDS_SHOW_MEMORY_LABEL ) ;
ResourceString MemoryOption ( Library, IDS_SHOW_MEMORY_OPTION ) ;
IniData->Items[ITEM_MEMORYFREE] = new MemoryFree ( ITEM_MEMORYFREE,
PSZ("ShowMemory"), PSZ(MemoryLabel), PSZ(MemoryOption),
IniData->CountryInfo,
(SwapFree*)IniData->Items[ITEM_SWAPDISKFREE] ) ;
ResourceString SpoolSizeLabel ( Library, IDS_SHOW_SPOOLSIZE_LABEL ) ;
ResourceString SpoolSizeOption ( Library, IDS_SHOW_SPOOLSIZE_OPTION ) ;
IniData->Items[ITEM_SPOOLFILESIZE] = new SpoolSize ( ITEM_SPOOLFILESIZE,
PSZ("ShowSpoolSize"), PSZ(SpoolSizeLabel), PSZ(SpoolSizeOption),
IniData->CountryInfo,
IniData->SpoolPath ) ;
ResourceString CpuLoadLabel ( Library, IDS_SHOW_CPULOAD_LABEL ) ;
ResourceString CpuLoadOption ( Library, IDS_SHOW_CPULOAD_OPTION ) ;
IniData->Items[ITEM_CPULOAD] = new CpuLoad ( ITEM_CPULOAD,
PSZ("ShowCpuLoad"), PSZ(CpuLoadLabel), PSZ(CpuLoadOption),
IniData->MaxCount,
&IniData->IdleCount ) ;
ResourceString TaskCountLabel ( Library, IDS_SHOW_TASKCOUNT_LABEL ) ;
ResourceString TaskCountOption ( Library, IDS_SHOW_TASKCOUNT_OPTION ) ;
IniData->Items[ITEM_TASKCOUNT] = new TaskCount ( ITEM_TASKCOUNT,
PSZ("ShowTaskCount"), PSZ(TaskCountLabel), PSZ(TaskCountOption),
Anchor ) ;
ResourceString TotalFreeLabel ( Library, IDS_SHOW_TOTALFREE_LABEL ) ;
ResourceString TotalFreeOption ( Library, IDS_SHOW_TOTALFREE_OPTION ) ;
IniData->Items[ITEM_TOTALFREE] = new TotalFree ( ITEM_TOTALFREE,
PSZ("ShowTotalFree"), PSZ(TotalFreeLabel), PSZ(TotalFreeOption),
IniData->CountryInfo, 0 ) ;
for ( int i=0; i<ITEM_BASE_COUNT; i++ )
{
BOOL Flag = TRUE ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), IniData->Items[i]->QueryName(), &Size )
AND
( ( Size == sizeof(Flag) ) OR ( Size == sizeof(short) ) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), IniData->Items[i]->QueryName(), &Flag, &Size )
)
{
;
}
if ( Flag )
IniData->Items[i]->SetFlag() ;
else
IniData->Items[i]->ResetFlag() ;
}
/***************************************************************************
* Add items for each drive on the system. *
***************************************************************************/
ULONG Drive, Drives ;
DosQueryCurrentDisk ( &Drive, &Drives ) ;
UpdateDriveList ( Anchor, Library, IniHandle, IniData, 0, Drives ) ;
return ( 0 ) ;
}
/****************************************************************************
* *
* Put IniData Data *
* *
****************************************************************************/
STATIC void PutIniData ( HINI IniHandle, PINIDATA IniData )
{
/***************************************************************************
* Save the window's current size and position. *
***************************************************************************/
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("Position"),
&IniData->Position,
sizeof(IniData->Position)
) ;
/***************************************************************************
* Save the program options. *
***************************************************************************/
if ( IniData->fHideControls )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("HideControls"),
&IniData->HideControls,
sizeof(IniData->HideControls)
) ;
}
if ( IniData->fFloat )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("Float"),
&IniData->Float,
sizeof(IniData->Float)
) ;
}
if ( IniData->fAnimate )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("Animate"),
&IniData->Animate,
sizeof(IniData->Animate)
) ;
}
if ( IniData->fShowFileSystemNames )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("ShowFileSystemNames"),
&IniData->ShowFileSystemNames,
sizeof(IniData->ShowFileSystemNames)
) ;
}
if ( IniData->fMonitorPriority )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("MonitorPriority"),
&IniData->MonitorPriority,
sizeof(IniData->MonitorPriority)
) ;
}
if ( IniData->fTimerInterval )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("TimerInterval"),
&IniData->TimerInterval,
sizeof(IniData->TimerInterval)
) ;
}
/***************************************************************************
* Save the item options. *
***************************************************************************/
for ( int i=0; i<IniData->ItemCount; i++ )
{
Item *pItem = IniData->Items [i] ;
BOOL Flag = pItem->QueryFlag() ;
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
pItem->QueryName(),
&Flag,
sizeof(Flag)
) ;
}
/***************************************************************************
* Save the presentation parameters. *
***************************************************************************/
if ( IniData->fFontNameSize )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("FontNameSize"),
IniData->FontNameSize,
sizeof(IniData->FontNameSize)
) ;
}
if ( IniData->fBackColor )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("BackgroundColor"),
&IniData->BackColor,
sizeof(IniData->BackColor)
) ;
}
if ( IniData->fTextColor )
{
PrfWriteProfileData
(
IniHandle,
PSZ(PROGRAM_NAME),
PSZ("ForegroundColor"),
&IniData->TextColor,
sizeof(IniData->TextColor)
) ;
}
}
/****************************************************************************
* *
* Scan CONFIG.SYS for a keyword. Return the value. *
* *
****************************************************************************/
STATIC PSZ ScanSystemConfig ( HAB Anchor, PSZ Keyword )
{
/***************************************************************************
* Get the boot drive number from the global information segment. *
***************************************************************************/
ULONG BootDrive ;
DosQuerySysInfo ( QSV_BOOT_DRIVE, QSV_BOOT_DRIVE, &BootDrive, sizeof(BootDrive) ) ;
/***************************************************************************
* Convert the keyword to upper case. *
***************************************************************************/
WinUpper ( Anchor, 0, 0, Keyword ) ;
/***************************************************************************
* Build the CONFIG.SYS path. *
***************************************************************************/
char Path [_MAX_PATH] ;
Path[0] = (char) ( BootDrive + 'A' - 1 ) ;
Path[1] = 0 ;
strcat ( Path, ":\\CONFIG.SYS" ) ;
/***************************************************************************
* Open CONFIG.SYS for reading. *
***************************************************************************/
FILE *File = fopen ( Path, "r" ) ;
if ( NOT File )
{
return ( 0 ) ;
}
/***************************************************************************
* While there're more lines in CONFIG.SYS, read a line and check it. *
***************************************************************************/
static char Buffer [500] ;
while ( fgets ( Buffer, sizeof(Buffer), File ) )
{
/*************************************************************************
* Clean any trailing newline character from the input string. *
*************************************************************************/
if ( Buffer[strlen(Buffer)-1] == '\n' )
{
Buffer[strlen(Buffer)-1] = 0 ;
}
/*************************************************************************
* If keyword starts the line, we've found the line we want. Close *
* the file and return a pointer to the parameter text. *
*************************************************************************/
WinUpper ( Anchor, 0, 0, PSZ(Buffer) ) ;
if ( NOT strncmp ( Buffer, PCHAR(Keyword), strlen(PCHAR(Keyword)) )
AND ( Buffer[strlen(PCHAR(Keyword))] == '=' ) )
{
fclose ( File ) ;
return ( PSZ( Buffer + strlen(PCHAR(Keyword)) + 1 ) ) ;
}
}
/***************************************************************************
* Close the file. We haven't found the line we wanted. *
***************************************************************************/
fclose ( File ) ;
return ( 0 ) ;
}
/****************************************************************************
* *
* Resize Client Window *
* *
****************************************************************************/
STATIC void ResizeWindow ( HWND hwnd, PINIDATA IniData )
{
/***************************************************************************
* If the window is visible and minimized, restore it invisibly. *
***************************************************************************/
HWND hwndFrame = WinQueryWindow ( hwnd, QW_PARENT ) ;
SHORT fHadToHide = FALSE ;
SHORT fHadToRestore = FALSE ;
if ( IniData->Position.fl & SWP_MINIMIZE )
{
if ( WinIsWindowVisible ( hwndFrame ) )
{
WinShowWindow ( hwndFrame, FALSE ) ;
fHadToHide = TRUE ;
}
WinSetWindowPos ( hwndFrame, 0, 0, 0, 0, 0, SWP_RESTORE ) ;
fHadToRestore = TRUE ;
}
/***************************************************************************
* Determine how many items are to be displayed. *
***************************************************************************/
HPS hPS = WinGetPS ( hwnd ) ;
int Count = 0 ;
LONG Widest = 0 ;
LONG Height = 0 ;
for ( int i=0; i<IniData->ItemCount; i++ )
{
Item *pItem = IniData->Items [i] ;
if ( pItem->QueryFlag() )
{
Count ++ ;
RECTL Rectangle ;
pItem->Measure ( hPS, Rectangle ) ;
Widest = max ( Widest, (Rectangle.xRight-Rectangle.xLeft+1) ) ;
Height += Rectangle.yTop - Rectangle.yBottom ;
}
}
WinReleasePS ( hPS ) ;
/***************************************************************************
* Get the window's current size & position. *
***************************************************************************/
RECTL Rectangle ;
WinQueryWindowRect ( hwndFrame, &Rectangle ) ;
WinCalcFrameRect ( hwndFrame, &Rectangle, TRUE ) ;
/***************************************************************************
* Adjust the window's width & height. *
***************************************************************************/
Rectangle.xRight = Rectangle.xLeft + Widest ;
Rectangle.yTop = Rectangle.yBottom + Height ;
/***************************************************************************
* Compute new frame size and apply it. *
***************************************************************************/
WinCalcFrameRect ( hwndFrame, &Rectangle, FALSE ) ;
WinSetWindowPos ( hwndFrame, 0, 0, 0,
(SHORT) (Rectangle.xRight-Rectangle.xLeft),
(SHORT) (Rectangle.yTop-Rectangle.yBottom),
SWP_SIZE ) ;
/***************************************************************************
* Return the window to its original state. *
***************************************************************************/
if ( fHadToRestore )
{
WinSetWindowPos ( hwndFrame, 0,
IniData->Position.x, IniData->Position.y,
IniData->Position.cx, IniData->Position.cy,
SWP_MOVE | SWP_SIZE | SWP_MINIMIZE ) ;
}
if ( fHadToHide )
{
WinShowWindow ( hwndFrame, TRUE ) ;
}
/***************************************************************************
* Invalidate the window so that it gets repainted. *
***************************************************************************/
WinInvalidateRect ( hwnd, PRECTL(NULL), TRUE ) ;
}
/****************************************************************************
* *
* Hide Window Controls *
* *
****************************************************************************/
STATIC void HideControls
(
BOOL fHide,
HWND hwndFrame,
HWND hwndSysMenu,
HWND hwndTitleBar,
HWND hwndMinMax
)
{
/***************************************************************************
* Get original window position and state. *
***************************************************************************/
SWP OldPosition ;
WinQueryWindowPos ( hwndFrame, &OldPosition ) ;
BOOL WasVisible = WinIsWindowVisible ( hwndFrame ) ;
/***************************************************************************
* Restore and hide the window. *
***************************************************************************/
WinSetWindowPos ( hwndFrame, 0, 0, 0, 0, 0, SWP_RESTORE | SWP_HIDE ) ;
/***************************************************************************
* Determine client window and location. *
***************************************************************************/
SWP Position ;
WinQueryWindowPos ( hwndFrame, &Position ) ;
RECTL Rectangle ;
Rectangle.xLeft = Position.x ;
Rectangle.xRight = Position.x + Position.cx ;
Rectangle.yBottom = Position.y ;
Rectangle.yTop = Position.y + Position.cy ;
WinCalcFrameRect ( hwndFrame, &Rectangle, TRUE ) ;
/***************************************************************************
* Hide or reveal the controls windows by changing their parentage. *
***************************************************************************/
if ( fHide )
{
WinSetParent ( hwndSysMenu, HWND_OBJECT, FALSE ) ;
WinSetParent ( hwndTitleBar, HWND_OBJECT, FALSE ) ;
WinSetParent ( hwndMinMax, HWND_OBJECT, FALSE ) ;
}
else
{
WinSetParent ( hwndSysMenu, hwndFrame, TRUE ) ;
WinSetParent ( hwndTitleBar, hwndFrame, TRUE ) ;
WinSetParent ( hwndMinMax, hwndFrame, TRUE ) ;
}
/***************************************************************************
* Tell the frame that things have changed. Let it update the window. *
***************************************************************************/
WinSendMsg ( hwndFrame, WM_UPDATEFRAME,
MPFROMSHORT ( FCF_TITLEBAR | FCF_SYSMENU | FCF_MINBUTTON ), 0L ) ;
/***************************************************************************
* Reposition the frame around the client window, which is left be. *
***************************************************************************/
WinCalcFrameRect ( hwndFrame, &Rectangle, FALSE ) ;
WinSetWindowPos ( hwndFrame, 0,
(SHORT) Rectangle.xLeft, (SHORT) Rectangle.yBottom,
(SHORT) (Rectangle.xRight-Rectangle.xLeft),
(SHORT) (Rectangle.yTop-Rectangle.yBottom),
SWP_SIZE | SWP_MOVE ) ;
/***************************************************************************
* If window was maximized, put it back that way. *
***************************************************************************/
if ( OldPosition.fl & SWP_MAXIMIZE )
{
WinSetWindowPos ( hwndFrame, 0,
(SHORT) Rectangle.xLeft, (SHORT) Rectangle.yBottom,
(SHORT) (Rectangle.xRight-Rectangle.xLeft),
(SHORT) (Rectangle.yTop-Rectangle.yBottom),
SWP_SIZE | SWP_MOVE |
( OldPosition.fl & SWP_MAXIMIZE ) ) ;
}
/***************************************************************************
* If the window was visible in the first place, show it. *
***************************************************************************/
if ( WasVisible ) {
WinShowWindow ( hwndFrame, TRUE ) ;
}
}
/****************************************************************************
* *
* Update Window *
* *
****************************************************************************/
STATIC void UpdateWindow ( HWND hwnd, PDATA Data, BOOL All )
{
/***************************************************************************
* Determine how many items are to be displayed. *
***************************************************************************/
int Count = 0 ;
for ( int i=0; i<Data->IniData.ItemCount; i++ ) {
if ( Data->IniData.Items[i]->QueryFlag() ) {
Count ++ ;
}
}
/***************************************************************************
* Get presentation space and make it use RGB colors. *
***************************************************************************/
HPS hPS = WinGetPS ( hwnd ) ;
GpiCreateLogColorTable ( hPS, LCOL_RESET, LCOLF_RGB, 0L, 0L, PLONG(NULL) ) ;
/***************************************************************************
* Get the window's size and determine the initial position. *
***************************************************************************/
RECTL Rectangle ;
WinQueryWindowRect ( hwnd, &Rectangle ) ;
Rectangle.xLeft += Data->Width / 2 ;
Rectangle.xRight -= Data->Width / 2 ;
Rectangle.yBottom = Data->Height * ( Count - 1 ) ;
Rectangle.yTop = Rectangle.yBottom + Data->Height ;
/***************************************************************************
* Review all items. Display those changed, or all. *
***************************************************************************/
for ( i=0; i<Data->IniData.ItemCount; i++ ) {
Item *pItem = Data->IniData.Items [i] ;
if ( pItem->QueryFlag() ) {
pItem->Repaint ( hPS, Rectangle, Data->IniData.TextColor, Data->IniData.BackColor, All ) ;
Rectangle.yBottom -= Data->Height ;
Rectangle.yTop -= Data->Height ;
}
}
/***************************************************************************
* Release the presentation space and return. *
***************************************************************************/
WinReleasePS ( hPS ) ;
}
/****************************************************************************
* *
* Monitor Loop Thread *
* *
****************************************************************************/
STATIC VOID _Optlink MonitorLoopThread ( PVOID Parameter )
{
/***************************************************************************
* Get the thread parameter. *
***************************************************************************/
PMONITOR_PARMS Parms = PMONITOR_PARMS ( Parameter ) ;
/***************************************************************************
* Set this thread's priority. *
***************************************************************************/
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MAXIMUM, 0 ) ;
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MINIMUM+(*Parms->Priority), 0 ) ;
/***************************************************************************
* Start up the high resolution timer, if it is available. *
***************************************************************************/
BOOL HiResTimer = OpenTimer ( ) ;
/***************************************************************************
* Loop while active . . . *
***************************************************************************/
while ( Parms->Active ) {
/*************************************************************************
* Reset the last time and count seen. *
*************************************************************************/
ULONG LastMilliseconds ;
TIMESTAMP Time [2] ;
if ( HiResTimer )
GetTime ( &Time[0] ) ;
else
DosQuerySysInfo ( QSV_MS_COUNT, QSV_MS_COUNT, &LastMilliseconds, sizeof(LastMilliseconds) ) ;
ULONG LastCounter = *Parms->Counter ;
/*************************************************************************
* Adjust priority and sleep a bit. *
*************************************************************************/
// DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MAXIMUM, 0 ) ;
// DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MINIMUM+(*Parms->Priority), 0 ) ;
DosSleep ( *Parms->Interval ) ;
/*************************************************************************
* Find out how much time and counts went by. *
*************************************************************************/
ULONG CurrentCounter = *Parms->Counter ;
ULONG DeltaMilliseconds ;
if ( HiResTimer ) {
GetTime ( &Time[1] ) ;
ULONG Nanoseconds ;
DeltaMilliseconds = ComputeElapsedTime ( &Time[0], &Time[1], &Nanoseconds ) ;
if ( Nanoseconds >= 500000L )
DeltaMilliseconds ++ ;
} else {
ULONG Milliseconds ;
DosQuerySysInfo ( QSV_MS_COUNT, QSV_MS_COUNT, &Milliseconds, sizeof(Milliseconds) ) ;
DeltaMilliseconds = Milliseconds - LastMilliseconds ;
}
/*************************************************************************
* Find out how much idle time was counted. Adjust it to persecond. *
*************************************************************************/
ULONG Counter = (ULONG) ( ( (double)(CurrentCounter-LastCounter) * 1000L ) / (double)DeltaMilliseconds ) ;
/*************************************************************************
* Tell the owner window to refresh its statistics. *
*************************************************************************/
WinPostMsg ( Parms->Owner, WM_REFRESH, MPFROMLONG(Counter), 0L ) ;
}
}
/****************************************************************************
* *
* Update the Item List to reflect changes in the available drives. *
* *
****************************************************************************/
STATIC VOID UpdateDriveList
(
HAB Anchor,
HMODULE Library,
HINI IniHandle,
PINIDATA IniData,
ULONG OldDrives,
ULONG NewDrives
)
{
/***************************************************************************
* Get format strings. *
***************************************************************************/
ResourceString LabelFormat ( Library, IDS_SHOW_DRIVE_FREE_LABEL ) ;
ResourceString OptionFormat ( Library, IDS_SHOW_DRIVE_FREE_OPTION ) ;
/***************************************************************************
* Save the old item list for comparison. *
***************************************************************************/
Item *OldItems [ ITEM_BASE_COUNT + MAX_DRIVES ] ;
memset ( OldItems, 0, sizeof(OldItems) ) ;
USHORT OldCount = 0 ;
if ( OldDrives )
{
OldCount = IniData->ItemCount ;
memcpy ( OldItems, IniData->Items, sizeof(OldItems) ) ;
}
/***************************************************************************
* Add items for each drive on the system. *
***************************************************************************/
USHORT Count = ITEM_BASE_COUNT ;
USHORT OldIndex = ITEM_BASE_COUNT ;
ULONG Drives = 0 ;
NewDrives >>= 2 ;
OldDrives >>= 2 ;
for ( int Drive=3; Drive<=MAX_DRIVES; Drive++ )
{
while ( ( OldIndex < OldCount )
AND ( (SHORT)OldItems[OldIndex]->QueryId() < ITEM_BASE_COUNT + Drive ) )
{
OldIndex ++ ;
}
if ( NewDrives & 1 )
{
if ( OldDrives & 1 )
{
Drives |= ( 1 << (Drive-1) ) ;
if ( ( OldIndex < OldCount )
AND ( (SHORT)OldItems[OldIndex]->QueryId() == ITEM_BASE_COUNT + Drive ) )
{
IniData->Items[Count++] = OldItems[OldIndex++] ;
}
}
else
{
BYTE FileSystem [80] ;
int DriveType = CheckDrive ( Drive, FileSystem ) ;
if ( DriveType ) {
if ( DriveType > 0 )
Drives |= ( 1 << (Drive-1) ) ;
BYTE Name [80] ;
sprintf ( PCHAR(Name), "ShowDrive%c:", Drive+'A'-1 ) ;
BYTE Label [80] ;
sprintf ( PCHAR(Label), PCHAR(LabelFormat), Drive+'A'-1 ) ;
BYTE Option [80] ;
sprintf ( PCHAR(Option), PCHAR(OptionFormat), Drive+'A'-1 ) ;
IniData->Items[Count++] = new DriveFree ( ITEM_BASE_COUNT+Drive,
Name, Label, Option, IniData->CountryInfo,
Drive, IniData->DriveError, IniData->ShowFileSystemNames, FileSystem ) ;
}
}
}
else
{
if ( OldDrives & 1 )
{
delete OldItems[OldIndex++] ;
}
else
{
// Do nothing.
}
}
NewDrives >>= 1 ;
OldDrives >>= 1 ;
}
/***************************************************************************
* Save the new item count. *
***************************************************************************/
IniData->ItemCount = Count ;
/***************************************************************************
* Fetch the display flags for the drives. *
***************************************************************************/
for ( int i=ITEM_BASE_COUNT; i<IniData->ItemCount; i++ )
{
BOOL Flag = TRUE ;
Item *pItem = IniData->Items [i] ;
ULONG Size ;
if
(
PrfQueryProfileSize ( IniHandle, PSZ(PROGRAM_NAME), pItem->QueryName(), &Size )
AND
( ( Size == sizeof(Flag) ) OR ( Size == sizeof(short) ) )
AND
PrfQueryProfileData ( IniHandle, PSZ(PROGRAM_NAME), pItem->QueryName(), &Flag, &Size )
)
{
;
}
if ( Flag )
pItem->SetFlag () ;
else
pItem->ResetFlag () ;
}
/***************************************************************************
* Update the total free space object. *
***************************************************************************/
( (TotalFree*) IniData->Items [ ITEM_TOTALFREE ] ) -> ResetMask ( Drives ) ;
}
/****************************************************************************
* *
* Check to see if drive should be added to display list. *
* *
****************************************************************************/
STATIC int CheckDrive ( USHORT Drive, PBYTE FileSystem ) {
/***************************************************************************
* First, check to see if drive is local or remote. Remote drives are *
* always monitored. *
***************************************************************************/
BYTE Path [3] ;
Path[0] = (BYTE) ( Drive + 'A' - 1 ) ;
Path[1] = ':' ;
Path[2] = 0 ;
DosError ( FERR_DISABLEHARDERR ) ;
BYTE Buffer [1024] ;
ULONG Size = sizeof(Buffer) ;
ULONG Status = DosQueryFSAttach ( Path, 0, FSAIL_QUERYNAME, (PFSQBUFFER2)Buffer, &Size ) ;
DosError ( FERR_ENABLEHARDERR ) ;
if ( Status ) {
// Log ( "ERROR: Unable to query drive %s for file system. Status %04X.",
// Path, Status ) ;
return ( 0 ) ; // Don't monitor.
}
USHORT cbName = PFSQBUFFER2(Buffer)->cbName ;
strcpy ( PCHAR(FileSystem), PCHAR(PFSQBUFFER2(Buffer+cbName)->szFSDName) ) ;
if ( PFSQBUFFER2(Buffer)->iType == FSAT_REMOTEDRV ) {
return ( -1 ) ; // Monitor but don't include in the total over all drives.
}
/***************************************************************************
* Attempt to open the local drive as an entire device. If unable to do *
* so, we cannot monitor this drive. *
***************************************************************************/
ULONG Action ;
HFILE Handle ;
Status = DosOpen ( Path, &Handle, &Action, 0, 0, FILE_OPEN,
OPEN_ACCESS_READONLY | OPEN_SHARE_DENYNONE |
OPEN_FLAGS_DASD | OPEN_FLAGS_FAIL_ON_ERROR, 0 ) ;
if ( Status ) {
// Log ( "ERROR: Unable to open local drive %s. Status %04X.",
// Path, Status ) ;
return ( 0 ) ; // Don't monitor.
}
/***************************************************************************
* Check to see if the drive has removable media. We cannot monitor such. *
***************************************************************************/
BOOL Addit = FALSE ;
BYTE Command = 0 ;
BYTE NonRemovable ;
ULONG LengthIn = sizeof(Command) ;
ULONG LengthOut = sizeof(NonRemovable);
if (
NOT DosDevIOCtl
(
Handle, 8, 0x20,
&Command, sizeof(Command), &LengthIn,
&NonRemovable, sizeof(NonRemovable), &LengthOut
)
) {
Addit = NonRemovable ;
}
/***************************************************************************
* Close the drive. *
***************************************************************************/
DosClose ( Handle ) ;
/***************************************************************************
* Return the final verdict. *
***************************************************************************/
return ( Addit ) ; // Monitor and include in overall total if not removable.
}
/****************************************************************************
* *
* Calibrate the Load Meter *
* *
****************************************************************************/
STATIC ULONG CalibrateLoadMeter ( PCOUNTER_PARMS Parms ) {
/***************************************************************************
* Set result to zero as a default. *
***************************************************************************/
double AdjustedMaxLoad = 0.0 ;
/***************************************************************************
* If HRTIMER.SYS has been installed . . . *
***************************************************************************/
if ( OpenTimer ( ) ) {
/*************************************************************************
* Increase this thread's priority to the maximum. *
*************************************************************************/
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MAXIMUM, 0 ) ;
/*************************************************************************
* Create the calibration thread and set its priority next highest. *
*************************************************************************/
Parms->Active = TRUE ;
TID tidCalibrate = _beginthread ( CounterThread, NULL, 0x3000, Parms ) ;
DosSuspendThread ( tidCalibrate ) ;
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, PRTYD_MAXIMUM, tidCalibrate ) ;
DosSetPriority ( PRTYS_THREAD, PRTYC_TIMECRITICAL, -1, tidCalibrate ) ;
/*************************************************************************
* Reset the calibration count, get the time, and let the counter go. *
*************************************************************************/
Parms->Counter = 0 ;
TIMESTAMP Time[2] ;
GetTime ( &Time[0] ) ;
DosResumeThread ( tidCalibrate ) ;
/*************************************************************************
* Sleep for one second. *
*************************************************************************/
DosSleep ( 1000 ) ;
/*************************************************************************
* Suspend the calibration counter and get the time. *
*************************************************************************/
Parms->Active = FALSE ;
DosWaitThread ( &tidCalibrate, DCWW_WAIT ) ;
GetTime ( &Time[1] ) ;
/*************************************************************************
* Return priorities to normal. *
*************************************************************************/
DosSetPriority ( PRTYS_THREAD, PRTYC_REGULAR, 0, 0 ) ;
/*************************************************************************
* Get the elapsed time and adjust the calibration count. *
*************************************************************************/
ULONG Milliseconds ;
ULONG Nanoseconds ;
Milliseconds = ComputeElapsedTime ( &Time[0], &Time[1], &Nanoseconds ) ;
AdjustedMaxLoad = (double)Parms->Counter * 1.0E9 ;
AdjustedMaxLoad /= (double)Milliseconds*1.0E6L + (double)Nanoseconds ;
/*************************************************************************
* Close down the connection to HRTIMER.SYS. *
*************************************************************************/
CloseTimer ( ) ;
}
/***************************************************************************
* Return the adjusted calibration count. If HRTIMER was not there, it *
* will be zero. *
***************************************************************************/
return ( (ULONG)AdjustedMaxLoad ) ;
}
/****************************************************************************
* *
* General Purpose Counter Thread *
* *
****************************************************************************/
STATIC VOID _Optlink CounterThread ( PVOID Parameter ) {
PCOUNTER_PARMS Parms = PCOUNTER_PARMS ( Parameter ) ;
while ( Parms->Active ) {
Parms->Counter ++ ;
}
}