// // PMMON.CPP // // Source file for ArchiveLib 2.0 // // Copyright (c) Greenleaf Software, Inc. 1994-1996 // All Rights Reserved // // CONTENTS // // ALOs2Message::operator new() // ALOs2Message::ALOs2Message() // ALOs2Message::Progress() // ALOs2Message::ArchiveOperation() // ALOs2Message::~ALOs2Message() // // DESCRIPTION // // This file contains all of the source to support the OS/2 // native monitor, ALOs2Message. // // REVISION HISTORY // // February 14, 1996 2.0A : New release // #include "arclib.h" #ifndef AL_IBM #pragma hdrstop #endif #include #include "pmmon.h" // // NAME // // ALOs2Message::operator new() // // PLATFORMS/ENVIRONMENTS // // PM // C++ // // SHORT DESCRIPTION // // Memory allocator used when ArchiveLib resides in a 16 bit DLL. // // C++ SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // void * ALOs2Message::operator new( size_t size ) // // C SYNOPSIS // // None. // // VB SYNOPSIS // // None. // // DELPHI SYNOPSIS // // None. // // ARGUMENTS // // size : The number of bytes that the compiler has decided will be // necessary to construct a new ALOs2Message object. // // DESCRIPTION // // When using a DLL, it is easy to get into a dangerous situation when // creating objects whose ctor and dtor are both in the DLL. The problem // arises because when you create an object using new, the memory for // the object will be allocated from the EXE. However, when you destroy // the object using delete, the memory is freed inside the DLL. Since // the DLL doesn't really own that memory, bad things can happen. // // But, you say, won't the space just go back to the Windows heap regardless // of who tries to free it? Maybe, but maybe not. If the DLL is using // a subsegment allocation scheme, it might do some sort of local free // before returning the space to the windows heap. That is the point where // you could conceivably cook your heap. // // By providing our own version of operator new inside this class, we // ensure that all memory allocation for the class will be done from // inside the DLL, not the EXE calling the DLL. // // RETURNS // // A pointer to some memory that should have been pulled out of the // heap for the DLL. // // EXAMPLE // // SEE ALSO // // REVISION HISTORY // // February 14, 1996 2.0A : New release // #if defined( AL_BUILDING_DLL ) void AL_DLL_FAR * AL_PROTO ALOs2Message::operator new( size_t size ) /* Tag protected function */ { return ::new char[ size ]; } #endif // // NAME // // ALOs2Message::ALOs2Message() // // PLATFORMS/ENVIRONMENTS // // Console Windows PM // C++ C VB Delphi // // SHORT DESCRIPTION // // Constructor for OS/2 PM monitor object. // // C++ SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // ALOs2Message::ALOs2Message( ALMonitorType monitor_type, // HWND progress_text_window, // ALWindowsMessageType message_type, // HWND progress_number_window, // UINT pm_message = 0 ); // // C SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // hALMonitor newALOs2Message( ALMonitorType monitor_type, // HWND progress_text_window, // ALWindowsMessageType message_type, // HWND progress_number_window, // UINT pm_message ); // // VB SYNOPSIS // // None, VB doesn't work under OS/2. // // DELPHI SYNOPSIS // // None, Delphi doesn't work with OS/2. // // ARGUMENTS // // monitor_type : AL_MONITOR_OBJECTS or AL_MONITOR_JOBS // // progress_text_window : The handle of the window that is going to // receive text messages during the archiving // process. // // message_type : AL_SEND_RATIO or AL_SEND_BYTE_COUNT // // progress_number_window : The window that is going to receive the // number, which will either be the byte // count or the percent complete ratio. // // windows_message : The message that will be sent to the // progress number window. When the message // is sent, the number is sent in mp1 and mp2, // so take your pick. If this number is set // to 0, the message is instead // sent as text using the set text call. // // DESCRIPTION // // This constructor has an easy job. It accepts five parameters. // Four of them just get copied into data members, the fifth gets // passed up to the constructor for the base class. // // This type of monitor is used in PM programs. Our examples // make use of it frequently. It sends text messages to edit or static // text controls, and sends numbers to either text controls or custom // controls. // // This monitor has special handling if the message sent is // SLM_SETSLIDERINFO. When that is the case, we assume the control is // a slider, and calculate the length of the slider, so it can be // updated in an orderly fashion. Check some of the PM examples to // see this in action. // // RETURNS // // The C++ ctor returns nothing, the C version returns a pointer to a // newly constructed monitor object, although it is masquerading as a // handle. // // EXAMPLE // // SEE ALSO // // REVISION HISTORY // // February 14, 1996 2.0A : New release // AL_PROTO ALOs2Message::ALOs2Message( ALMonitorType monitor_type, /* Tag public function */ HWND progress_text_window, ALWindowsMessageType message_type, HWND progress_number_window, UINT pm_message /* = 0 */ ) : ALMonitor( monitor_type ) { mhMessageWindowHandle = progress_text_window; mhNumberWindowHandle = progress_number_window; miMessage = pm_message; mMessageType = message_type; // // If the message is going to a slider control, we pick up the // number of increments right now. That way, we can send the // correct numbers when showing ratios from 0 to 100%. // if ( miMessage == SLM_SETSLIDERINFO ) { WNDPARAMS wndp; SLDCDATA sldc; wndp.fsStatus = WPM_CTLDATA; wndp.pCtlData = (PVOID) &sldc; wndp.cbCtlData = sizeof( sldc ); WinSendMsg( mhNumberWindowHandle, WM_QUERYWINDOWPARAMS, MPFROMP( &wndp ), MPFROMSHORT( 0 ) ); miSliderLength = sldc.usScale1Increments - 1; } else { miSliderLength = -1; } } #if !defined( AL_NO_C ) extern "C" AL_LINKAGE hALMonitor AL_FUNCTION newALOs2Message( ALMonitorType monitor_type, /* Tag public function */ HWND progress_text_window, ALWindowsMessageType message_type, HWND progress_number_window, UINT windows_message ) { return (hALMonitor) new ALOs2Message( monitor_type, progress_text_window, message_type, progress_number_window, windows_message ); } #endif // // NAME // // ALOs2Message::Progress() // // PLATFORMS/ENVIRONMENTS // // PM // C++ // // SHORT DESCRIPTION // // The progress routine for the PM message monitor. // // C++ SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // void ALOs2Message::Progress( long object_tell, // ALStorage &object ); // // C SYNOPSIS // // None, this is a protected member function for internal use. // // VB SYNOPSIS // // None, this is a protected member function for internal use. // // DELPHI SYNOPSIS // // None, this is a protected member function for internal use. // // ARGUMENTS // // object_tell : The current offset within the object being processed. // Since this function is always called from inside // ALStorage::Yield(), the location will always be known. // // object : The object being compressed, extracted, copied, or // whatever. // // // DESCRIPTION // // This function gets called a lot while an object is being processed. // All we do in here is send the ratio/position information to the // window that was specified in the constructor, using the message that // was specified in the ctor. // // You might notice here that we don't check on whether we are monitoring // Objects or Jobs, we just go with the value found in miRatio. There // is a simple reason for that. At the start of the function, we call // ALMonitor::Progress(). The base class function checks to see which // mode we are in, and calculates the miRatio value according to whatever // mode we are in. // // Also note that there is some special processing done for a slider. // // RETURNS // // Nothing. // // EXAMPLE // // SEE ALSO // // REVISION HISTORY // // February 14, 1996 2.0A : New release // void AL_PROTO ALOs2Message::Progress( long object_tell, /* Tag protected function */ ALStorage AL_DLL_FAR &object ) { char buf[ 18 ]; // // This guy figures out what the current byte count and ratio are // ALMonitor::Progress( object_tell, object ); int position = ( miRatio * miSliderLength ) / 100; if ( mhNumberWindowHandle == 0 ) return; switch ( mMessageType ) { case AL_SEND_BYTE_COUNT : // // Send the byte count using either SendMessage() or SetWindowText() // if ( miMessage == 0 ) { sprintf( buf, "%ld", mlByteCount ); WinSetWindowText( mhNumberWindowHandle, (PSZ) buf ); } else if ( miMessage != SLM_SETSLIDERINFO ) { WinSendMsg( mhNumberWindowHandle, miMessage, MPFROMSHORT( position ), MPFROMSHORT( position ) ); } else WinSendMsg( mhNumberWindowHandle, SLM_SETSLIDERINFO, MPFROM2SHORT( SMA_SLIDERARMPOSITION, SMA_INCREMENTVALUE ), MPFROMSHORT( position ) ); break; case AL_SEND_RATIO : // // Send the progress ratio using SendMessage() or SetWindowText() // if ( miMessage == 0 ) { sprintf( buf, "%d%%", miRatio ); WinSetWindowText( mhNumberWindowHandle, (PSZ) buf ); } else if ( miMessage != SLM_SETSLIDERINFO ) { WinSendMsg( mhNumberWindowHandle, miMessage, MPFROMSHORT( position ), MPFROMSHORT( position ) ); } else WinSendMsg( mhNumberWindowHandle, SLM_SETSLIDERINFO, MPFROM2SHORT( SMA_SLIDERARMPOSITION, SMA_INCREMENTVALUE ), MPFROMSHORT( position ) ); break; default : break; } } // // NAME // // ALOs2Message::ArchiveOperation() // // PLATFORMS/ENVIRONMENTS // // PM // C++ // // SHORT DESCRIPTION // // Update user interface elements after an archiving operation. // // C++ SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // void ALOs2Message::ArchiveOperation( ALArchiveOperation operation, // ALArchive *archive, // ALEntry *job ); // // C SYNOPSIS // // None, this is a protected member function for internal use. // // VB SYNOPSIS // // None, this is a protected member function for internal use. // // DELPHI SYNOPSIS // // None, this is a protected member function for internal use. // // ARGUMENTS // // operation : One of the values from the enumerated type ALArchiveOperation. // It is simply a list of possible operations that the archive // operation might take, such as opening a file, closing a // file, etc. // // archive : A pointer to the archive object currently being worked on. // // job : A pointer to an ALEntry object that defines the ALStorage // object presently being worked on. // // DESCRIPTION // // During the course of an Archiving operation, the functions in // ALArchive will get the urge to spit out a message. They do // so by calling this member function. All of the messages should // be self-explanatory. // // It would make a lot of sense to move the message formatting up into // the base class so I didn't have to duplicate this effort in every // derived class. // // RETURNS // // Nothing. // // EXAMPLE // // SEE ALSO // // REVISION HISTORY // // February 14, 1996 2.0A : New release // void AL_PROTO ALOs2Message::ArchiveOperation( ALArchiveOperation operation, /* Tag protected function */ ALArchive AL_DLL_FAR *archive, ALEntry AL_DLL_FAR *job ) { if ( mhMessageWindowHandle == 0 ) return; char buf[ 81 ]; switch ( operation ) { case AL_ARCHIVE_OPEN : sprintf( buf, "Opening %s", archive->GetStorageObject()->mName.GetSafeName() ); break; case AL_ARCHIVE_CLOSE : sprintf( buf, "Closing %s", archive->GetStorageObject()->mName.GetSafeName() ); break; case AL_EXTRACTION_OPEN : sprintf( buf, "Extracting %s", job->mpStorageObject->mName.GetSafeName() ); break; case AL_INSERTION_OPEN : sprintf( buf, "Inserting %s", job->mpStorageObject->mName.GetSafeName() ); break; case AL_COPY_OPEN : sprintf( buf, "Copying %s", job->mpStorageObject->mName.GetSafeName() ); break; case AL_EXTRACTION_CLOSE : case AL_INSERTION_CLOSE : case AL_COPY_CLOSE : case AL_END_DIRECTORY_WRITE : case AL_END_DIRECTORY_READ : strcpy( buf, "Done" ); break; case AL_START_DIRECTORY_WRITE : strcpy( buf, "Writing directory" ); break; case AL_START_DIRECTORY_READ : strcpy( buf, "Reading directory" ); break; } WinSetWindowText( mhMessageWindowHandle, (PSZ) buf ); } // // NAME // // ALOs2Message::~ALOs2Message() // // PLATFORMS/ENVIRONMENTS // // PM // C++ // // SHORT DESCRIPTION // // The PM monitor object destructor. // // C++ SYNOPSIS // // #include "arclib.h" // #include "pmmon.h" // // ALOs2Message::~ALOs2Message(); // // C SYNOPSIS // // None, C programmers should call the base class dtor, deleteALMonitor(). // // VB SYNOPSIS // // None, VB not supported under OS/2 PM. // // DELPHI SYNOPSIS // // None, Delphi not supported under OS/2 PM. // // ARGUMENTS // // None. // // DESCRIPTION // // An examination of the code shown here should satisfy you that this // destructor has nothing to do. // // RETURNS // // Nothing. // // EXAMPLE // // SEE ALSO // // REVISION HISTORY // // February 14, 1996 2.0A : New release // AL_PROTO ALOs2Message::~ALOs2Message() { AL_ASSERT( GoodTag(), "~ALOs2Message: attempt to delete invalid object" ); }