1997-06-16 19:43:53 +02:00
|
|
|
KERNEL MODULE
|
|
|
|
=============
|
|
|
|
|
|
|
|
...
|
|
|
|
|
|
|
|
GDI MODULE
|
|
|
|
==========
|
|
|
|
|
|
|
|
...
|
|
|
|
|
1996-06-16 18:16:05 +02:00
|
|
|
USER MODULE
|
|
|
|
===========
|
|
|
|
|
|
|
|
USER implements windowing and messaging subsystems. It also
|
|
|
|
contains code for common controls and for other miscellaneous
|
|
|
|
stuff (rectangles, clipboard, WNet, etc). Wine USER code is
|
|
|
|
located in windows/, controls/, and misc/ directories.
|
|
|
|
|
|
|
|
1. Windowing subsystem
|
|
|
|
|
Release 971101
Thu Oct 30 21:52:23 1997 Martin Boehme <boehme@informatik.mu-luebeck.de>
* [windows/nonclient.c]
Changed NC_TrackSysMenu to give the same behaviour as MS-Windows,
i.e. system menu already appears when mouse button is depressed.
Changed NC_HandleNCLButtonDblClk so that double clicks on scroll
bar arrows are handled the same way as single clicks.
* [windows/winpos.c]
Fixed SetWindowPos32 to clear WIN_NO_REDRAW when SWP_SHOWWINDOW is
set; this is the way MS-Windows behaves.
Thu Oct 30 21:08:57 1997 Morten Welinder <terra@diku.dk>
* [controls/status.c]
In SW_SetText, fix condition, I hope.
* [controls/menu.c]
(GetMenuState32): Don't mask return value. Print more debug info.
(MENU_MenuBarCalcSize): Be more careful when printing debug
information.
(MENU_SetItemData): Empty strings are separators.
* [graphics/x11drv/text.c]
Don't prototype CLIPPING_IntersectClipRect.
* [include/dc.h]
Prototype CLIPPING_IntersectClipRect.
* [objects/font.c]
Remove non-portable (and faulty) smartness in FONT_TextMetric*to*.
In CreateFont32W and CreateFont16, handle null font name.
* [objects/text.c]
(TEXT_NextLine): Fix end-of-line bug.
* [if1632/shell32.spec]
Activate existing implementation of ExtractIconA.
* [misc/shell.c]
For Control_RunDLL, add types for parameters.
Thu Oct 30 14:54:11 1997 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de>
* [controls/static.c] [include/windows.h] [misc/spy.c]
Added some win32 defines to static controls, basic SS_BITMAP style
handling implemented. [please add more, I am lacking knowledge and
time]
* [controls/status.c]
part_num 255 seems to indicate whole statusline (win95 cdplayer.exe)
* [if1632/thunk.c] [tools/build.c]
Support lret and 0x66 lret calls for CallTo16_regs
(needed for KERNEL32_45)
Fixed KERNEL32_45, QT_Thunk (should work now).
* [if1632/relay.c][if1632/builtin.c][tools/build.c][if1632/*32.spec]
Added string dumping to relay debugging for win32 apifuncs.
* [misc/ver.c]
Fixed and cleaned up VerQueryValue*.
* [multimedia/*.c][include/mmsystem.h][if1632/mmsystem.spec]
[if1632/winmm.spec]
Win32 support for lowlevel multimedia functions.
Added some mixer* lowlevel functions.
Some small fixes in the audio lowlevel queue handling, code
reformatting/cleanups.
* [debugger/hash.c]
Don't show difference between 16bit symbols if they are in
different segments.
* [objects/cursoricon.c]
Added GetIconInfo (partial) and CreateIconIndirect.
* [windows/mdi.c]
Fixed some "bad class" problems and crashes in MDICreateChild,
which happen in Win32 (jwp32.exe).
Wed Oct 29 00:57:27 1997 Bruce Milner <Bruce.Milner@genetics.utah.edu>
* [if1632/winaspi.spec] [misc/aspi.c] [include/aspi.c]
[documentation/aspi] [include/callback.h]
Added support for 16 bit ASPI calls to linux generic SCSI.
The support is not complete, but appears to run my Mustek
scanner from within ipplus.exe.
Mon Oct 27 00:59:41 1997 Alex Korobka <alex@trantor.pharm.sunysb.edu>
* [windows/dce.c]
DC reuse framework.
Sun Oct 26 18:41:21 1997 Huw D M Davies <h.davies1@physics.oxford.ac.uk>
* [graphics/x11drv/xfont.c]
Substituted fonts are removed from the alias table. References to
the old name are also updated.
* [controls/combo.c]
LB_SELECTSTRING32 not CB_SELECTSTRING32 should be sent to
ComboLBox.
Sun Oct 26 14:25:00 1997 Nikita V. Youshchenko <yoush@cs.msu.su>
* [include/drive.h] [files/drive.c] [msdos/int21.c]
Partially implemented DOS drive mapping (int21 AX=440F).
Sat Oct 25 13:03:29 1997 Alexandre Julliard <julliard@lrc.epfl.ch>
* [debugger/debug.l]
Support '.' in identifiers. Use "x . y" to access structure
fields.
* [debugger/hash.c] [loader/pe_image.c]
Load entry points of Win32 modules only when entering the
debugger.
* [debugger/break.c]
New function DEBUG_AddModuleBreakpoint() to set a breakpoint at
the start of every module.
* [files/file.c]
FILE_mmap() can now fake mmap() for unaligned offsets or broken
filesystems.
* [include/callback.h] [misc/callback.c] [if1632/thunk.c]
Use a table of callbacks instead of macros to differentiate
between emulator and Winelib.
* [loader/task.c]
Initialize current directory from cwd, not from module path.
* [tools/build.c]
Read CallTo16 prototypes directly from thunk.c source file.
* [windows/winproc.c] [windows/mdi.c]
Added translation for WM_MDIACTIVATE and WM_MDIGETACTIVE.
Fri Oct 24 21:41:25 1997 Uwe Bonnes <bon@elektron.ikp.tu-darmstadt.de>
* [files/drive.c]
Allow arguments like "a" for the drive related apis.
* [memory/global.c]
Keep the calculation for dwMemoryLoad in range.
* [misc/crtdll.c]
Make CRTDLL_getcwd use GetCurrentDirectory32A and alloc
its memory if requested.
Implemented CRTDLL_rename and CRTDLL_stat needed for
lcc-win32:wedit.exe.
Implemented CRTDLL__fullpath.
* [misc/comm.c]
High speed modes for the 16-bit mode Comm functions.
* [misc/cpu.c]
As applications may treat lpMaximumApplicationAddress as long,
use a valid long number.
* [misc/main.c]
In SystemParametersInfo16 ignore SPI_GETHIGHCONTRAST too.
* [misc/ole2nls.c]
Implement LCMAP_UPPERCASE for LCMapString32.
* [misc/wsprintf]
Made WPRINTF_ParseFormatA understand %ws.
* [win32/file.c]
Ignore FILE_ATTRIBUTE_NORMAL.
Stub for ReadFileEx.
Fri Oct 24 15:36:02 1997 Doug Ridgway <ridgway@routh.ucsd.edu>
* [memory/local.c]
Local heap exhaustion message now prints which builtin heap filled.
Fri Oct 24 00:46:34 1997 Huw D M Davies <h.davies1@physics.oxford.ac.uk>
* [windows/dialog.c]
Reversed CreateFont16/32W typo.
Thu Oct 23 23:44:20 1997 Kristian Nielsen <kristian.nielsen@risoe.dk>
* [if1632/user.spec]
Fixed argument list for ChangeClipboardChain.
* [windows/mdi.c]
Pass correct hInstance to CreateWindow16() in MDICreateChild().
Mon Oct 20 11:51:24 1997 Carsten Fallesen <cf@it.dtu.dk>
* [objects/metafile.c]
Added support for META_SETTEXTCHAREXTRA.
* [objects/region.c]
Fixed crash in XPolygonRegion if there is only one point in
in the region.
* [if1632/gdi32.spec][include/gdi.h][include/windows.h]
[objects/gdiobj.c]
Completed OBJ_XXX defines in gdi.h, removed OBJ_XXX in gdiobj.c
and included gdi.h instead. Implemented GetObjectType32().
Thu Oct 16 17:21:32 1997 Philippe De Muyter <phdm@info.ucl.ac.be>
* [documentation/wine.texinfo]
Fixed WIN32 and Makefiles entries of Reference manual node, that
made makeinfo dump core.
Mon Oct 13 17:15:57 1997 Robert Wilhelm <robert@physiol.med.tu-muenchen.de>
* [if1632/crtdll.spec]
Added missing math functions y0(), y1(), y2(), floor(), frexp(),
ldexp(), modf().
1997-11-01 20:08:16 +01:00
|
|
|
windows/win.c
|
|
|
|
windows/winpos.c
|
|
|
|
|
1996-06-16 18:16:05 +02:00
|
|
|
Windows are arranged into parent/child hierarchy with one
|
|
|
|
common ancestor for all windows (desktop window). Each window
|
|
|
|
structure contains a pointer to the immediate ancestor (parent
|
|
|
|
window if WS_CHILD style bit is set), a pointer to the sibling
|
|
|
|
(returned by GetWindow(..., GW_NEXT)), a pointer to the owner
|
|
|
|
window (set only for popup window if it was created with valid
|
|
|
|
hwndParent parameter), and a pointer to the first child
|
|
|
|
window (GetWindow(.., GW_CHILD)). All popup and non-child windows
|
|
|
|
are therefore placed in the first level of this hierarchy and their
|
|
|
|
ancestor link (wnd->parent) points to the desktop window.
|
|
|
|
|
|
|
|
Desktop window - root window
|
1997-06-16 19:43:53 +02:00
|
|
|
| \ `-.
|
|
|
|
| \ `-.
|
1996-06-16 18:16:05 +02:00
|
|
|
popup -> wnd1 -> wnd2 - top level windows
|
1997-06-16 19:43:53 +02:00
|
|
|
| \ `-. `-.
|
|
|
|
| \ `-. `-.
|
1996-06-16 18:16:05 +02:00
|
|
|
child1 child2 -> child3 child4 - child windows
|
|
|
|
|
|
|
|
Horizontal arrows denote sibling relationship, vertical lines
|
|
|
|
- ancestor/child. To summarize, all windows with the same immediate
|
|
|
|
ancestor are sibling windows, all windows which do not have desktop
|
|
|
|
as their immediate ancestor are child windows. Popup windows behave
|
|
|
|
as topmost top-level windows unless they are owned. In this case the
|
|
|
|
only requirement is that they must precede their owners in the top-level
|
|
|
|
sibling list (they are not topmost). Child windows are confined to the
|
|
|
|
client area of their parent windows (client area is where window gets
|
|
|
|
to do its own drawing, non-client area consists of caption, menu, borders,
|
1997-06-16 19:43:53 +02:00
|
|
|
intrinsic scrollbars, and minimize/maximize/close/help buttons).
|
1996-06-16 18:16:05 +02:00
|
|
|
|
|
|
|
Another fairly important concept is "z-order". It is derived from
|
|
|
|
the ancestor/child hierarchy and is used to determine "above/below"
|
|
|
|
relationship. For instance, in the example above, z-order is
|
|
|
|
child1->popup->child2->child3->wnd1->child4->wnd2->desktop. Current
|
|
|
|
active window ("foreground window" in Win32) is moved to the front
|
|
|
|
of z-order unless its top-level ancestor owns popup windows.
|
|
|
|
|
|
|
|
All these issues are dealt with (or supposed to be) in
|
|
|
|
windows/winpos.c
|
|
|
|
|
|
|
|
Wine specifics: in default and managed mode each top-level window
|
|
|
|
gets its own X counterpart with desktop window being basically a
|
1997-06-16 19:43:53 +02:00
|
|
|
fake stub. In desktop mode, however, only desktop window has an X
|
1996-06-16 18:16:05 +02:00
|
|
|
window associated with it.
|
|
|
|
|
Release 971101
Thu Oct 30 21:52:23 1997 Martin Boehme <boehme@informatik.mu-luebeck.de>
* [windows/nonclient.c]
Changed NC_TrackSysMenu to give the same behaviour as MS-Windows,
i.e. system menu already appears when mouse button is depressed.
Changed NC_HandleNCLButtonDblClk so that double clicks on scroll
bar arrows are handled the same way as single clicks.
* [windows/winpos.c]
Fixed SetWindowPos32 to clear WIN_NO_REDRAW when SWP_SHOWWINDOW is
set; this is the way MS-Windows behaves.
Thu Oct 30 21:08:57 1997 Morten Welinder <terra@diku.dk>
* [controls/status.c]
In SW_SetText, fix condition, I hope.
* [controls/menu.c]
(GetMenuState32): Don't mask return value. Print more debug info.
(MENU_MenuBarCalcSize): Be more careful when printing debug
information.
(MENU_SetItemData): Empty strings are separators.
* [graphics/x11drv/text.c]
Don't prototype CLIPPING_IntersectClipRect.
* [include/dc.h]
Prototype CLIPPING_IntersectClipRect.
* [objects/font.c]
Remove non-portable (and faulty) smartness in FONT_TextMetric*to*.
In CreateFont32W and CreateFont16, handle null font name.
* [objects/text.c]
(TEXT_NextLine): Fix end-of-line bug.
* [if1632/shell32.spec]
Activate existing implementation of ExtractIconA.
* [misc/shell.c]
For Control_RunDLL, add types for parameters.
Thu Oct 30 14:54:11 1997 Marcus Meissner <msmeissn@cip.informatik.uni-erlangen.de>
* [controls/static.c] [include/windows.h] [misc/spy.c]
Added some win32 defines to static controls, basic SS_BITMAP style
handling implemented. [please add more, I am lacking knowledge and
time]
* [controls/status.c]
part_num 255 seems to indicate whole statusline (win95 cdplayer.exe)
* [if1632/thunk.c] [tools/build.c]
Support lret and 0x66 lret calls for CallTo16_regs
(needed for KERNEL32_45)
Fixed KERNEL32_45, QT_Thunk (should work now).
* [if1632/relay.c][if1632/builtin.c][tools/build.c][if1632/*32.spec]
Added string dumping to relay debugging for win32 apifuncs.
* [misc/ver.c]
Fixed and cleaned up VerQueryValue*.
* [multimedia/*.c][include/mmsystem.h][if1632/mmsystem.spec]
[if1632/winmm.spec]
Win32 support for lowlevel multimedia functions.
Added some mixer* lowlevel functions.
Some small fixes in the audio lowlevel queue handling, code
reformatting/cleanups.
* [debugger/hash.c]
Don't show difference between 16bit symbols if they are in
different segments.
* [objects/cursoricon.c]
Added GetIconInfo (partial) and CreateIconIndirect.
* [windows/mdi.c]
Fixed some "bad class" problems and crashes in MDICreateChild,
which happen in Win32 (jwp32.exe).
Wed Oct 29 00:57:27 1997 Bruce Milner <Bruce.Milner@genetics.utah.edu>
* [if1632/winaspi.spec] [misc/aspi.c] [include/aspi.c]
[documentation/aspi] [include/callback.h]
Added support for 16 bit ASPI calls to linux generic SCSI.
The support is not complete, but appears to run my Mustek
scanner from within ipplus.exe.
Mon Oct 27 00:59:41 1997 Alex Korobka <alex@trantor.pharm.sunysb.edu>
* [windows/dce.c]
DC reuse framework.
Sun Oct 26 18:41:21 1997 Huw D M Davies <h.davies1@physics.oxford.ac.uk>
* [graphics/x11drv/xfont.c]
Substituted fonts are removed from the alias table. References to
the old name are also updated.
* [controls/combo.c]
LB_SELECTSTRING32 not CB_SELECTSTRING32 should be sent to
ComboLBox.
Sun Oct 26 14:25:00 1997 Nikita V. Youshchenko <yoush@cs.msu.su>
* [include/drive.h] [files/drive.c] [msdos/int21.c]
Partially implemented DOS drive mapping (int21 AX=440F).
Sat Oct 25 13:03:29 1997 Alexandre Julliard <julliard@lrc.epfl.ch>
* [debugger/debug.l]
Support '.' in identifiers. Use "x . y" to access structure
fields.
* [debugger/hash.c] [loader/pe_image.c]
Load entry points of Win32 modules only when entering the
debugger.
* [debugger/break.c]
New function DEBUG_AddModuleBreakpoint() to set a breakpoint at
the start of every module.
* [files/file.c]
FILE_mmap() can now fake mmap() for unaligned offsets or broken
filesystems.
* [include/callback.h] [misc/callback.c] [if1632/thunk.c]
Use a table of callbacks instead of macros to differentiate
between emulator and Winelib.
* [loader/task.c]
Initialize current directory from cwd, not from module path.
* [tools/build.c]
Read CallTo16 prototypes directly from thunk.c source file.
* [windows/winproc.c] [windows/mdi.c]
Added translation for WM_MDIACTIVATE and WM_MDIGETACTIVE.
Fri Oct 24 21:41:25 1997 Uwe Bonnes <bon@elektron.ikp.tu-darmstadt.de>
* [files/drive.c]
Allow arguments like "a" for the drive related apis.
* [memory/global.c]
Keep the calculation for dwMemoryLoad in range.
* [misc/crtdll.c]
Make CRTDLL_getcwd use GetCurrentDirectory32A and alloc
its memory if requested.
Implemented CRTDLL_rename and CRTDLL_stat needed for
lcc-win32:wedit.exe.
Implemented CRTDLL__fullpath.
* [misc/comm.c]
High speed modes for the 16-bit mode Comm functions.
* [misc/cpu.c]
As applications may treat lpMaximumApplicationAddress as long,
use a valid long number.
* [misc/main.c]
In SystemParametersInfo16 ignore SPI_GETHIGHCONTRAST too.
* [misc/ole2nls.c]
Implement LCMAP_UPPERCASE for LCMapString32.
* [misc/wsprintf]
Made WPRINTF_ParseFormatA understand %ws.
* [win32/file.c]
Ignore FILE_ATTRIBUTE_NORMAL.
Stub for ReadFileEx.
Fri Oct 24 15:36:02 1997 Doug Ridgway <ridgway@routh.ucsd.edu>
* [memory/local.c]
Local heap exhaustion message now prints which builtin heap filled.
Fri Oct 24 00:46:34 1997 Huw D M Davies <h.davies1@physics.oxford.ac.uk>
* [windows/dialog.c]
Reversed CreateFont16/32W typo.
Thu Oct 23 23:44:20 1997 Kristian Nielsen <kristian.nielsen@risoe.dk>
* [if1632/user.spec]
Fixed argument list for ChangeClipboardChain.
* [windows/mdi.c]
Pass correct hInstance to CreateWindow16() in MDICreateChild().
Mon Oct 20 11:51:24 1997 Carsten Fallesen <cf@it.dtu.dk>
* [objects/metafile.c]
Added support for META_SETTEXTCHAREXTRA.
* [objects/region.c]
Fixed crash in XPolygonRegion if there is only one point in
in the region.
* [if1632/gdi32.spec][include/gdi.h][include/windows.h]
[objects/gdiobj.c]
Completed OBJ_XXX defines in gdi.h, removed OBJ_XXX in gdiobj.c
and included gdi.h instead. Implemented GetObjectType32().
Thu Oct 16 17:21:32 1997 Philippe De Muyter <phdm@info.ucl.ac.be>
* [documentation/wine.texinfo]
Fixed WIN32 and Makefiles entries of Reference manual node, that
made makeinfo dump core.
Mon Oct 13 17:15:57 1997 Robert Wilhelm <robert@physiol.med.tu-muenchen.de>
* [if1632/crtdll.spec]
Added missing math functions y0(), y1(), y2(), floor(), frexp(),
ldexp(), modf().
1997-11-01 20:08:16 +01:00
|
|
|
2. Visible region, clipping region and update region
|
|
|
|
|
|
|
|
windows/dce.c
|
|
|
|
windows/winpos.c
|
|
|
|
windows/painting.c
|
|
|
|
|
|
|
|
________________________
|
|
|
|
|_________ | A and B are child windows of C
|
|
|
|
| A |______ |
|
|
|
|
| | | |
|
|
|
|
|---------' | |
|
|
|
|
| | B | |
|
|
|
|
| | | |
|
|
|
|
| `------------' |
|
|
|
|
| C |
|
|
|
|
`------------------------'
|
|
|
|
|
|
|
|
Visible region determines which part of the window is not obscured
|
|
|
|
by other windows. If a window has the WS_CLIPCHILDREN style then all
|
|
|
|
areas below its children are considered invisible. Similarily, if
|
|
|
|
the WS_CLIPSIBLINGS bit is in effect then all areas obscured by its
|
|
|
|
siblings are invisible. Child windows are always clipped by the
|
|
|
|
boundaries of their parent windows.
|
|
|
|
|
|
|
|
B has a WS_CLIPSIBLINGS style:
|
|
|
|
. ______
|
|
|
|
: | |
|
|
|
|
| ,-----' |
|
|
|
|
| | B | - visible region of B
|
|
|
|
| | |
|
|
|
|
: `------------'
|
|
|
|
|
|
|
|
When the program requests a display context (DC) for a window it
|
|
|
|
can specify an optional clipping region that further restricts the
|
|
|
|
area where the graphics output can appear. This area is calculated
|
|
|
|
as an intersection of the visible region and a clipping region.
|
|
|
|
|
|
|
|
Program asked for a DC with a clipping region:
|
|
|
|
______
|
|
|
|
,--|--. | . ,--.
|
|
|
|
,--+--' | | : _: |
|
|
|
|
| | B | | => | | | - DC region where the painting will
|
|
|
|
| | | | | | | be visible
|
|
|
|
`--|-----|---' : `----'
|
|
|
|
`-----'
|
|
|
|
|
|
|
|
When the window manager detects that some part of the window
|
|
|
|
became visible it adds this area to the update region of this
|
|
|
|
window and then generates WM_ERASEBKGND and WM_PAINT messages.
|
|
|
|
In addition, WM_NCPAINT message is sent when the uncovered area
|
|
|
|
intersects a nonclient part of the window. Application must reply
|
|
|
|
to the WM_PAINT message by calling BeginPaint()/EndPaint() pair of
|
|
|
|
functions. BeginPaint() returns a DC that uses accumulated update
|
|
|
|
region as a clipping region. This operation cleans up invalidated
|
|
|
|
area and the window will not receive another WM_PAINT until the
|
|
|
|
window manager creates a new update region.
|
|
|
|
|
|
|
|
A was moved to the left:
|
|
|
|
________________________ ... / C update region
|
|
|
|
|______ | : .___ /
|
|
|
|
| A |_________ | => | ...|___|..
|
|
|
|
| | | | | : | |
|
|
|
|
|------' | | | : '---'
|
|
|
|
| | B | | | : \
|
|
|
|
| | | | : \
|
|
|
|
| `------------' | B update region
|
|
|
|
| C |
|
|
|
|
`------------------------'
|
|
|
|
|
|
|
|
|
|
|
|
Windows maintains a display context cache consisting of entries that
|
|
|
|
include DC itself, window to which it belongs, and an optional clipping
|
|
|
|
region (visible region is stored in the DC itself). When an API call
|
|
|
|
changes the state of the window tree, window manager has to go through
|
|
|
|
the DC cache to recalculate visible regions for entries whose windows
|
|
|
|
were involved in the operation. DC entries (DCE) can be either private
|
|
|
|
to the window, or private to the window class, or shared between all
|
|
|
|
windows. Windows 3.1 limits the number of shared DCEs to 5.
|
|
|
|
|
|
|
|
3. Messaging subsystem
|
|
|
|
|
|
|
|
windows/queue.c
|
|
|
|
windows/message.c
|
1996-06-16 18:16:05 +02:00
|
|
|
|
|
|
|
Each Windows task/thread has its own message queue - this is where
|
|
|
|
it gets messages from. Messages can be generated on the fly
|
|
|
|
(WM_PAINT, WM_NCPAINT, WM_TIMER), they can be created by the system
|
|
|
|
(hardware messages), they can be posted by other tasks/threads
|
|
|
|
(PostMessage), or they can be sent by other tasks/threads (SendMessage).
|
|
|
|
|
|
|
|
Message priority:
|
|
|
|
|
|
|
|
First the system looks for sent messages, then for posted messages,
|
|
|
|
then for hardware messages, then it checks if the queue has the
|
|
|
|
"dirty window" bit set, and, finally, it checks for expired
|
|
|
|
timers. See windows/message.c.
|
|
|
|
|
|
|
|
From all these different types of messages, only posted messages go
|
|
|
|
directly into the private message queue. System messages (even in
|
|
|
|
Win95) are first collected in the system message queue and then
|
|
|
|
they either sit there until Get/PeekMessage gets to process them
|
|
|
|
or, as in Win95, if system queue is getting clobbered, a special
|
|
|
|
thread ("raw input thread") assigns them to the private
|
|
|
|
queues. Sent messages are queued separately and the sender sleeps
|
|
|
|
until it gets a reply. Special messages are generated on the fly
|
|
|
|
depending on the window/queue state. If the window update region is
|
|
|
|
not empty, the system sets the QS_PAINT bit in the owning queue and
|
|
|
|
eventually this window receives a WM_PAINT message (WM_NCPAINT too
|
|
|
|
if the update region intersects with the non-client area). A timer
|
|
|
|
event is raised when one of the queue timers expire. Depending on
|
|
|
|
the timer parameters DispatchMessage either calls the callback
|
|
|
|
function or the window procedure. If there are no messages pending
|
|
|
|
the task/thread sleeps until messages appear.
|
|
|
|
|
|
|
|
There are several tricky moments (open for discussion) -
|
|
|
|
|
|
|
|
a) System message order has to be honored and messages should be
|
|
|
|
processed within correct task/thread context. Therefore when
|
|
|
|
Get/PeekMessage encounters unassigned system message and this
|
|
|
|
message appears not to be for the current task/thread it should
|
|
|
|
either skip it (or get rid of it by moving it into the private
|
|
|
|
message queue of the target task/thread - Win95, AFAIK) and
|
|
|
|
look further or roll back and then yield until this message
|
|
|
|
gets processed when system switches to the correct context
|
|
|
|
(Win16). In the first case we lose correct message ordering, in
|
|
|
|
the second case we have the infamous synchronous system message
|
|
|
|
queue. Here is a post to one of the OS/2 newsgroup I found to
|
|
|
|
be relevant:
|
|
|
|
|
|
|
|
" Here's the problem in a nutshell, and there is no good solution.
|
|
|
|
Every possible solution creates a different problem.
|
|
|
|
|
|
|
|
With a windowing system, events can go to many different windows.
|
|
|
|
Most are sent by applications or by the OS when things relating to
|
|
|
|
that window happen (like repainting, timers, etc.)
|
|
|
|
|
|
|
|
Mouse input events go to the window you click on (unless some window
|
|
|
|
captures the mouse).
|
|
|
|
|
|
|
|
So far, no problem. Whenever an event happens, you put a message on
|
|
|
|
the target window's message queue. Every process has a message
|
|
|
|
queue. If the process queue fills up, the messages back up onto the
|
|
|
|
system queue.
|
|
|
|
|
|
|
|
This is the first cause of apps hanging the GUI. If an app doesn't
|
|
|
|
handle messages and they back up into the system queue, other apps
|
|
|
|
can't get any more messages. The reason is that the next message in
|
|
|
|
line can't go anywhere, and the system won't skip over it.
|
|
|
|
|
|
|
|
This can be fixed by making apps have bigger private message queues.
|
|
|
|
The SIQ fix does this. PMQSIZE does this for systems without the SIQ
|
|
|
|
fix. Applications can also request large queues on their own.
|
|
|
|
|
|
|
|
Another source of the problem, however, happens when you include
|
|
|
|
keyboard events. When you press a key, there's no easy way to know
|
|
|
|
what window the keystroke message should be delivered to.
|
|
|
|
|
|
|
|
Most windowing systems use a concept known as "focus". The window
|
|
|
|
with focus gets all incoming keyboard messages. Focus can be changed
|
|
|
|
from window to window by apps or by users clicking on winodws.
|
|
|
|
|
|
|
|
This is the second source of the problem. Suppose window A has focus.
|
|
|
|
You click on window B and start typing before the window gets focus.
|
|
|
|
Where should the keystrokes go? On the one hand, they should go to A
|
|
|
|
until the focus actually changes to B. On the other hand, you
|
|
|
|
probably want the keystrokes to go to B, since you clicked there
|
|
|
|
first.
|
|
|
|
|
|
|
|
OS/2's solution is that when a focus-changing event happens (like
|
|
|
|
clicking on a window), OS/2 holds all messages in the system queue
|
|
|
|
until the focus change actually happens. This way, subsequent
|
|
|
|
keystrokes go to the window you clicked on, even if it takes a while
|
|
|
|
for that window to get focus.
|
|
|
|
|
|
|
|
The downside is that if the window takes a real long time to get focus
|
|
|
|
(maybe it's not handling events, or maybe the window losing focus
|
|
|
|
isn't handling events), everything backs up in the system queue and
|
|
|
|
the system appears hung.
|
|
|
|
|
|
|
|
There are a few solutions to this problem.
|
|
|
|
|
|
|
|
One is to make focus policy asynchronous. That is, focus changing has
|
|
|
|
absolutely nothing to do with the keyboard. If you click on a window
|
|
|
|
and start typing before the focus actually changes, the keystrokes go
|
|
|
|
to the first window until focus changes, then they go to the second.
|
|
|
|
This is what X-windows does.
|
|
|
|
|
|
|
|
Another is what NT does. When focus changes, keyboard events are held
|
|
|
|
in the system message queue, but other events are allowed through.
|
|
|
|
This is "asynchronous" because the messages in the system queue are
|
|
|
|
delivered to the application queues in a different order from that
|
|
|
|
with which they were posted. If a bad app won't handle the "lose
|
|
|
|
focus" message, it's of no consequence - the app receiving focus will
|
|
|
|
get its "gain focus" message, and the keystrokes will go to it.
|
|
|
|
|
|
|
|
The NT solution also takes care of the application queue filling up
|
|
|
|
problem. Since the system delivers messages asynchronously, messages
|
|
|
|
waiting in the system queue will just sit there and the rest of the
|
|
|
|
messages will be delivered to their apps.
|
|
|
|
|
|
|
|
The OS/2 SIQ solution is this: When a focus-changing event happens,
|
|
|
|
in addition to blocking further messages from the application queues,
|
|
|
|
a timer is started. When the timer goes off, if the focus change has
|
|
|
|
not yet happened, the bad app has its focus taken away and all
|
|
|
|
messages targetted at that window are skipped. When the bad app
|
|
|
|
finally handles the focus change message, OS/2 will detect this and
|
|
|
|
stop skipping its messages.
|
|
|
|
|
|
|
|
|
|
|
|
As for the pros and cons:
|
|
|
|
|
|
|
|
The X-windows solution is probably the easiest. The problem is that
|
|
|
|
users generally don't like having to wait for the focus to change
|
|
|
|
before they start typing. On many occasions, you can type and the
|
|
|
|
characters end up in the wrong window because something (usually heavy
|
|
|
|
system load) is preventing the focus change from happening in a timely
|
|
|
|
manner.
|
|
|
|
|
|
|
|
The NT solution seems pretty nice, but making the system message queue
|
|
|
|
asynchronous can cause similar problems to the X-windows problem.
|
|
|
|
Since messages can be delivered out of order, programs must not assume
|
|
|
|
that two messages posted in a particular order will be delivered in
|
|
|
|
that same order. This can break legacy apps, but since Win32 always
|
|
|
|
had an asynchronous queue, it is fair to simply tell app designers
|
|
|
|
"don't do that". It's harder to tell app designers something like
|
|
|
|
that on OS/2 - they'll complain "you changed the rules and our apps
|
|
|
|
are breaking."
|
|
|
|
|
|
|
|
The OS/2 solution's problem is that nothing happens until you try to
|
|
|
|
change window focus, and then wait for the timeout. Until then, the
|
|
|
|
bad app is not detected and nothing is done." (by David Charlap)
|
|
|
|
|
|
|
|
|
|
|
|
b) Intertask/interthread SendMessage. The system has to inform the
|
1996-08-11 17:49:51 +02:00
|
|
|
target queue about the forthcoming message, then it has to carry
|
|
|
|
out the context switch and wait until the result is available.
|
|
|
|
Win16 stores necessary parameters in the queue structure and then
|
|
|
|
calls DirectedYield() function. However, in Win32 there could be
|
|
|
|
several messages pending sent by preemptively executing threads,
|
|
|
|
and in this case SendMessage has to build some sort of message
|
|
|
|
queue for sent messages. Another issue is what to do with messages
|
|
|
|
sent to the sender when it is blocked inside its own SendMessage.
|
|
|
|
|
1997-06-16 19:43:53 +02:00
|
|
|
|