home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 10 Tools
/
10-Tools.zip
/
MONTE.ZIP
/
PMTHREAD
/
README
< prev
next >
Wrap
Text File
|
1993-03-05
|
7KB
|
185 lines
TWO-THREADED PM APPLICATION ARCHITECTURE -- Monte Copeland
The Presentation Manager has been part of OS/2 versions since 1.1. It is the
part of OS/2 that provides the graphical, message-based, windowing
environment known as the desktop. OS/2 applications that utilize the
windowing features of OS/2 are called Presentation Manager applications or PM
apps.
PM apps, like all OS/2 applications, may call into the operating system for
services via the OS/2 API's. However, PM apps are required to provide some
services to the Presentation Manager which makes the relationship between
application and operating system a two-way street -- very cooperative.
PM sends messages to an application by calling window procedures in the
application. The window procedure will process messages like menu
selections, client window painting, window resizing, mouse clicks, mouse
movements, and termination.
In order for the Presentation Manager to stay in synch with all the
applications on the desktop, it delivers messages one at a time. These are
"sent" messages. Stated differently, when the Presentation Manager sends a
message to your window procedure, it stops sending messages elsewhere until
your procedure returns.
Therefore, PM apps must return from their window procedures in a timely
manner; one-tenth second is recommended. It is known as the one-tenth-second
rule. When an application takes too long, the symptoms include:
■ user unable to minimize the application
■ user unable to switch to another application
■ hourglass pointer over entire desktop
■ the system dialog: "Application is not responding to system requests.
Press Enter to end it."
Use a second thread in PM apps to bust the 1/10th second rule and perform
tasks that take time: diskcopy, upload/download, file input/output, SQL
queries. This article describes a robust two-threaded PM application
architechure. Applications coded in this style obey the 1/10th second rule,
and they can perform lengthy tasks.
THREAD DUTIES
Thread one is responsible for presentation. Thread one will execute the
normal window procedures of the application. Its duty is to present the
client window, dialogs and message boxes. It reacts to command messages from
its menus. It processes messages generated by the frame window controls.
Thread one is devoted to the operation of all the application's visible
windows on the desktop.
Thread two will execute an object window procedure. Object windows do not
appear on the desktop; they are not bound by the 1/10th-of-a-second rule; PM
sends them very few messages. When object windows procedures execute on
Page 1
thread two, they are perfect for doing time-consuming tasks required by the
application.
For the application to perform a task on thread two, the client window
procedure calls WinPostMsg to post user-defined messages to the object
window. The object window procedure gets the message and performs the
lengthy task on thread two.
client/dialog object window
window on thread 1 on thread 2
--------------- ---------------
|-------------| | waiting in |
| user | WinPostMsg( | WinGetMsg |
| requests | hwndObject, | |
| a lengthy | WM_USER_WORKITEM, | |
| workitem | hwndToAck, | |
| | null ) | |
| | --------------------> | |
| window | | perform |
| disabled | | lengthy |
| while | | task |
| busy | | |
| | WinPostMsg( | |
| | hwndToAck, | |
| | WM_USER_ACK, | |
| | WM_USER_WORKITEM, | task |
| | result code ) | complete |
| | <-------------------- | |
| enable | | |
| again | | |
--------------- ---------------
CLIENT DISABLED WHILE OBJECT BUSY
In the sample code below, the application disables its client and menu
windows then posts a message to the object window to perform the lengthy
task. Disabling the menu and client windows permits only one outstanding
task at a time. Disabling these windows prevents the user from originating
more tasks. Even though they are disabled from the user's point of view, they
will continue to get and dispatch messages sent by PM.
The frame window is not disabled; therefore, the user can minimize the frame
window and/or switch to another application while your application is busy.
OBJECT ACKS WHEN FINISHED
Upon completion of the lengthy task, the object window posts a user
acknowledgement message to the client window. This informs the client that
the task is complete. The client window procedure can re-enable the menu bar
and the client window, or chain to other tasks as required.
Page 2
COMMON DATA
Both threads share a common data space. This space is defined by the GLOBALS
structure in app.h. WM_CREATE processing allocates this space and passes the
pointer to thread two on the call to _beginthread.
The client and object window procedures keep a pointer to this memory in
their window words. The number of extra words per window is set by the
WinRegisterClass calls. Both the client and object windows have four extra
bytes of window words.
Dialog box procedures must obtain the pointer to shared memory and store it
in their window words when they initialize. By default, dialog boxes have
enough window words to hold a 32-bits-long pointer.
PMASSERT
The pmassert macro is a debugging tool. It works much like the C language
assert macro. Anywhere in the source code, the programmer can assert that a
Boolean expression is true. At runtime, nothing happens if the expression is
true. If false, the macro displays the failed assertion in a message box
along with the line number and the C source file name where the assertion
failed.
Because pmassert is a macro, it is easy to redefine the macro to be a "no
operation" once the application is debugged. In the C language tradition,
this is accomplished by defining the symbol NDEBUG. This approach to program
building yields "debug" and "retail" versions of your program. See
pmassert.h below.
Page 3