Why does SetWindowsHookEx take an HINSTANCE parameter?

Date:August 11, 2006 / year-entry #271
Tags:history
Orig Link:https://blogs.msdn.microsoft.com/oldnewthing/20060811-20/?p=30153
Comments:    10
Summary:An anonymous commenter asked why the SetWindowsHookEx function takes an HINSTANCE parameter if the first thing it's going to do is convert the instance handle into a file name. Because that's not how it worked in 16-bit Windows. In 16-bit Windows there was no such thing as hook injection. All 16-bit Windows applications ran in...

An anonymous commenter asked why the SetWindowsHookEx function takes an HINSTANCE parameter if the first thing it's going to do is convert the instance handle into a file name.

Because that's not how it worked in 16-bit Windows.

In 16-bit Windows there was no such thing as hook injection. All 16-bit Windows applications ran in the same address space, so there was no need to inject anything anywhere. Consequently, there was no need to convert the instance handle into a file name in order to inject it.

Instead, the instance handle was used to increment the reference count on the module so that the hook procedure wouldn't get unloaded while the hook was active. When the hook was uninstalled, the module reference count was decremented.

Even in 32-bit Windows, the window manager needs the instance handle in order to convert the function pointer back to an RVA so the function can be located when the module is loaded into another process. If you passed a LPCWSTR with a path to the module, the window manager would have to do a GetModuleHandle anyway to recover the instance handle. Since most programs have their instance handle readily available, that was the more natural choice. (Not to mention that it would preserve source compatibility with 16-bit Windows, which was an important criterion when trying to get people interested in porting their code to Win32.)


Comments (10)
  1. Stu says:

    The biggest problem with the Win32 API: It was designed to be source compatible with Win16, yet Win16 had a completely different set of assumptions: co-operative multitasking, shared address space, 16-bit pointers…

    Win16 compatability should have been shoved in a seperate library and marked deprecated in it’s entirety.

  2. peterchen says:

    RVA?

    Stu: Compatibility, source code and otherwise, drove Microsoft where it is today.

    [Sorry. RVA = relative virtual address. The offset in virtual address space from the start of the module to the start of the hook function. -Raymond]
  3. Gabe says:

    The whole reason that there are millions of Windows apps today is that Win32 is almost completely source compatible with Win16. If Win32 weren’t compatible, people wouldn’t bother porting their apps, and Win32 would just be another OS/2.

    Do you think there would be any Win64 apps if it weren’t source compatible with Win32?

  4. ShayEr says:

    TopSecret: The OldNewThing “Why did XXX does YYY?” Template

    {In/Before} {Windows 16-bit/Windows 3.1/Windows 95} we {run on the same address space/the size of int/pointer was 16 bit/check a legacy program/game} and discover that/therefore {crashing randomly/use undocumented future/no memory protection/no preemptive multitasking}  so we {reproduce that behavior/kept the old APIs} so that is why. But now you can run that crapy^H^H^H^H^H software/game even today in {Windows Vista/64 bit platform} :)

  5. Arno Schoedl says:

    With respect to the source compatibility argument, Microsoft is bending over backwards to make things source-compatible when going from Win16 to 32 to 64, with documentation and compiler support to prepare developers for the change. Yet when it comes to introducing new APIs, chaos reigns, with no smooth migration path anywhere in sight. As the worst example so far, C++ and Win32 is completely swapped out for C# and first Windows Forms and now WPF, and without excessive interop code, there is little chance for existing native code to use the new features or have the "look" of a Vista application. Even Microsoft’s own Office 2007 core apps are still native and seemingly use a proprietary native graphics engine rather than WPF.

  6. Dean Harding says:

    Even Microsoft’s own Office 2007 core apps are still native and

    > seemingly use a proprietary native graphics engine rather than WPF.

    Well of course it does, WPF isn’t even FINISHED yet, how could expect otherwise?

  7. Arno Schoedl says:

    Dean, if Office 2007 would use WPF, I would expect Office 2007 Beta 2 to install some WinFX runtime, which it does not, I checked the registry. I would also expect it to use resolution-independent XAML pictures as icons, but the current Office 2007 icons are clearly pixel-based (set screen DPI to 192 and see yourself). Some documentation also said that RibbonX is still COM-based, with interop to allow managed add-ins.

  8. Justin Tay says:

    Arno, I think you misunderstand what Dean is saying. He’s not saying that Office 2007 uses WPF. He’s saying that Office 2007 core apps are still native because WPF isn’t finished.  You can’t build an application reliably based on something that is itself work in progress.

  9. Arno Schoedl says:

    Office XP uses GDI+ for painting shapes, although it was not shipped as GDIPLUS.DLL, but instead compiled into MSO.DLL. So it looks like for Office XP, Microsoft spawned off an early internal version of GDI+. Office 2003 then switched to the regular GDIPLUS.DLL. So it is quite conceivable that Office 2007 would use an early branch of WinFX/WPF, in particular since it targets >=Windows XP, for which WinFX is available.

  10. Frank Hileman says:

    If Office used WPF, it would probably consume so much memory, and be so slow, as to be unusable.

Comments are closed.


*DISCLAIMER: I DO NOT OWN THIS CONTENT. If you are the owner and would like it removed, please contact me. The content herein is an archived reproduction of entries from Raymond Chen's "Old New Thing" Blog (most recent link is here). It may have slight formatting modifications for consistency and to improve readability.

WHY DID I DUPLICATE THIS CONTENT HERE? Let me first say this site has never had anything to sell and has never shown ads of any kind. I have nothing monetarily to gain by duplicating content here. Because I had made my own local copy of this content throughout the years, for ease of using tools like grep, I decided to put it online after I discovered some of the original content previously and publicly available, had disappeared approximately early to mid 2019. At the same time, I present the content in an easily accessible theme-agnostic way.

The information provided by Raymond's blog is, for all practical purposes, more authoritative on Windows Development than Microsoft's own MSDN documentation and should be considered supplemental reading to that documentation. The wealth of missing details provided by this blog that Microsoft could not or did not document about Windows over the years is vital enough, many would agree an online "backup" of these details is a necessary endeavor. Specifics include:

<-- Back to Old New Thing Archive Index