Commit graph

53 commits

Author SHA1 Message Date
rc-swag
02db51c9b6 fix(windows): address review comments
Some checks failed
Keyman Build Summary / Summarize build status checks (push) Has been cancelled
2026-04-28 23:16:17 +10:00
rc-swag
f0cf996976 fix(windows): make log code message fix
Some checks failed
Keyman Build Summary / Summarize build status checks (push) Has been cancelled
2026-03-30 13:43:11 +10:00
rc-swag
7084d64b7b fix(windows): clean up debug logs
Some checks failed
Keyman Build Summary / Summarize build status checks (push) Has been cancelled
2026-03-26 22:44:47 +10:00
rc-swag
a1c493665e fix(windows): add key transition to better track key press
Some checks are pending
Keyman Build Summary / Summarize build status checks (push) Waiting to run
Added a Key transition member to the thread globals.
This help so better insure we actually matching the key value
that may have been cleared by kmhook_getmessage to the right key.
More importantly makes sure we are not matching it to the wrong
key press. This was happening when a synthazised capslock key press was followed
by and actuall capslock key press.
2026-03-25 15:16:26 +10:00
rc-swag
c1c3952717 fix(windows): reduce the number of places km scan flag
The SCAN_FLAG_KEYMAN_KEY_EVENT was checked in OnKey pressess as well
as an early return option in _KeymanProcessKeystroke. This change
removes the extra and allows _KeymanProcessKeystroke, to be the
central place for code readablitiy and maintainablity.

It also adds a processToggleChange call in kmhook_getmessage as
it is sometimes called before the TIP hook. the call is also idempotent
2026-03-20 09:22:35 +10:00
rc-swag
6277735dbb fix(windows): fix typos and grammar in commments 2026-03-16 12:02:26 +10:00
rc-swag
bc6b0ea773 fix(windows): change caps on updateable
This change also adds a check in aiTIP.cpp to check the
thread data stored last key press and scan code. Before
if the scan code had been cleared then we would process the
synthasized caps lock key presses which was just for the system
and not for the current Keyman app.
2026-03-12 20:20:42 +10:00
Marc Durdin
711541be60 fix(windows): reinstall low level keyboard hook if it gets removed
This change improves the stability of Keyman for Windows by monitoring
the health of the low level keyboard hook. If keyman.exe is unresponsive
at any time, Windows can silently uninstall its low level keyboard hook,
which results in (at least) two problems:

* Keyman's hotkeys stop working
* A modifier key can become stuck, if it was pressed around the time
  Keyman became unresponsive.

The most common scenario in which Keyman can become unresponsive is high
system load, e.g. rendering graphics, videoconference calls, compiling
software.

Restarting Keyman always resolved both of these two issues in the past,
but with this patch, I hope that this will no longer be necessary.

A related 'fakefreeze' project is included for simulating a keyman.exe
hang by posting a `wm_keyman_control:KMC_WATCHDOG_FAKEFREEZE` message to
it, which keyman.exe responds to by `Sleep()`ing for 5 seconds. While
keyman.exe is freezing, any keystroke will cause the low level hook to
be uninstalled by Windows.

Logging has been updated; look for "LowLevelHookWatchDog" in the log for
related events.

One final small change in keyman32.cpp, as I refactored the
WH_KEYBOARD_LL hook installation/uninstallation, was to always clear out
hook variables when uninstalling a hook, because if the hook fails to
uninstall, there's really nothing we can do about it anyway, and we
probably shouldn't be trying again.

Fixes: #8064
2025-11-17 16:30:43 +01:00
Marc Durdin
50ffbb2722 fix(windows): osk: handle simulated left Control event when AltGr pressed
When a European layout is active, and the user presses AltGr, Windows
generates a simulated VK_LCONTROL event alongside the VK_RMENU event.
This was causing the OSK to show LCtrl as depressed alongside RAlt, so
the OSK would show the wrong modifier layer, which was unhelpful and
confusing to the end user.

It is possible to detect the simulated VK_LCONTROL in the WH_KEYBOARD_LL
hook, because the scan code generated is 0x21D, instead of 0x1D.
Warning: this is not a documented value. (But, this 0x21D scan code is
not passed to the WM_KEYDOWN event!) Therefore, we use Keyman's existing
kmnLowLevelKeyboardProc to pass modifier key events on to the visual
keyboard.

This patch handles only this specific scenario, by watching for that
specific scan code in the new handler in the UfrmOSKOnScreenKeyboard
module, together with some minor refactoring so that it fits neatly.

A future improvement would be to have all modifier key processing go
through this new handler, and eliminate the timer-based polling of the
keyboard. However, there is some additional risk around missing events,
leading to 'stuck modifiers'.

Fixes: #14890
Build-bot: skip release:windows
2025-10-08 14:32:40 +02:00
Marc Durdin
0175f906c8
Merge pull request #11921 from keymanapp/refactor/windows/cleanup-engine-logging
refactor(windows): clean up logging
2024-07-27 11:31:37 +10:00
rc-swag
915f710b44 chore(windows): remove posting keydown up events to IM
The code has already been commented out so this was more a clean up
of deadcode. WM_KEYDOWN events are not expected by the IM window anyway.
2024-07-24 17:05:40 +10:00
Marc Durdin
1be73a9c2e refactor(windows): clean up logging
* Remove unused parameters from SendDebugMessage functions
* Add SendDebugEntry and SendDebugExit functions for tracking
  function entry/exit
* Add indenting and function names to log entries
* Remove unused debug functions
* Eliminate now-unused hwnd parameter in initialization functions
* Replace Log,LogEntry,LogExit functions with SendDebug equivalents in
  kmtip

Many functions now have SendDebugEntry/SendDebugExit (or
return_SendDebugExit) pairs. It is important to SendDebugExit on all
returns from a function to keep the log indent depth consistent. In some
cases I chose not to add these logging calls, e.g. on frequently called
functions such as the message hooks.
2024-07-03 21:28:37 +10:00
Marc Durdin
aace36963e refactor(windows): remove wm_keyman_keydown and wm_keyman_keyup
Also cleanup the use of state.msg as that had no relevant data in it.

Fixes: #11917
2024-07-03 09:34:44 +10:00
Marc Durdin
ee1f972b13 chore(windows): remove wm_keymandebug messages and functions
Fixes #10050.

Removes the following unused identifiers:
* ::wm_kmdebug
* ::wm_keymandebug
* AppInt::DebugControlled()
* AITIP::WM_KEYMANDEBUG_CANDEBUG
* AITIP::WM_KEYMANDEBUG_GETUNICODESTATUS
* AITIP::WM_KEYMANDEBUG_GETCONTEXT
* AITIP::WM_KEYMANDEBUG_ACTION
* AITIP::WM_KEYMANDEBUG_RULEMATCH
* AITIP::DebugControlled()
* AITIP::IsDebugControlWindow()
* AITIP::GetDebugControlWindow()
* AITIP::Debug_FillContextBuffer()
* AIDEBUGINFO struct
* ::FillStoreOffsets()
* AIDEBUGKEYINFO struct

Removes overloads which are now no-ops:
* AITIP::HandleWindow()
* AITIP::IsWindowHandled()
* AITIP::QueueAction()
2023-11-23 10:49:58 +10:00
Marc Durdin
db76e2541d chore: rename KM_KBP_ to KM_CORE_ 2023-10-09 14:53:22 +07:00
Marc Durdin
ba5f18defd chore: rename km_kbp_ to km_core_ 2023-10-09 14:53:13 +07:00
Ross
7e83079499 chore(windows): remove WM_UNICHAR completley 2023-05-10 22:48:03 +10:00
Ross
2935084b45 chore(windows): do nothing on WM_UNICHAR 2023-05-03 15:09:45 +10:00
Ross
9aa6ab2ee0 chore(windows): remove addins c-h files 2023-05-03 14:48:03 +10:00
Ross
0ee25dc59f chore(windows): Revert "chore(windows): remove addins c-h files"
This reverts commit 5f07f7ad08.
2023-04-27 14:15:06 +10:00
Ross
5f07f7ad08 chore(windows): remove addins c-h files 2023-04-21 19:02:03 +10:00
Ross
4019a79676 chore(windows): address review comments 2023-04-21 18:43:50 +10:00
Ross
8f20507a82 chore(windows): remove legacy core and flag
Removing the legacy code that was replaced by the core.
Also removing the feature flag for core integeration.
2023-04-14 13:59:49 +10:00
Ross
102f34ecb0 feat(windows): convert wm keyevent and to private wm user message
wm_keyman_keyevent and wm_keyman_modifierevent have been convert to use
the WM_USER message range and no longer global message
2022-10-26 15:34:12 +10:00
Ross
ba72b3929d fix(windows): use GlobalGetAtomName to access global list
Incorrectly calling the the local atom list which meant
the flag isKeymanKeyboardActive was always false.
2022-04-29 15:34:48 +10:00
Ross
f8402a35e0 fix(windows): Fix scope of variables in case statement 2022-03-25 08:50:09 +10:00
Ross
342af79c34 fix(windows): add cs_clsidKMTipTextService const 2022-03-23 15:12:48 +10:00
rc-swag
4f218e7d6f
fix(windows): apply review comments as batch
Co-authored-by: Marc Durdin <marc@durdin.net>
2022-03-23 15:07:10 +10:00
Ross
c2d478ba4e fix(windows): rename header - review comments 2022-03-22 16:34:46 +10:00
Ross
dbc950741a fix(windows): change variable name add comments 2022-03-18 14:41:26 +10:00
Ross
d58a8c97d8 fix(windows): add threat check 2022-03-18 08:25:45 +10:00
Ross
be333860f0 fix(windows): framework for switching of pipeline
We want to be able to switch of the seralized pipeline if a keyman
keyboard is not active. To do this we need to store this information
in a way the seralized thread can get the information.
2022-03-17 13:02:50 +10:00
Ross
d5e228d6cc fix(windows): update comment remove casts 2022-02-10 11:48:06 +10:00
Ross
8c8859bcf1 feat(windows): add process_queued_actions 2022-01-20 14:33:00 +10:00
Ross
7efb4b1756 feat(windows): add wm_kewm_keymanim_close for core
This commit adds call to the core keyboard processor
on wm_keymanim_close event. To get the latest actions.
It also changes the core to allow QIT BACK even when
the context is empty.
2022-01-13 13:59:43 +10:00
Ross
a4801373db feat(windows): err logs, DEBUG_ASSERT macro
Added some more error logs
Added a DEBUG_ASSERT macro
Update variable names
2021-08-24 17:17:26 +10:00
Ross
0f4e3d1768 feat(windows): core saving context null pointer check 2021-08-17 14:10:44 +10:00
Marc Durdin
d26b01ad99 chore(windows): remove KMC_CHANGEUISTATE
The `KMC_CHANGEUISTATE` flag for `wm_keyman_control` is no longer
processed anywhere. Removes it and the `UpdateKeymanUI` function which
called it.

The `#define` for the flag has been left, commented out, to clarify what
would otherwise be a gap in identifiers (use `git blame` to learn more).
2021-05-11 15:19:01 +10:00
Marc Durdin
fbcfd62678 fix(windows): refactor controller windows
Fixes #5004.

This cleans up the use of controller windows. A single window is now
given the responsibility of being the master controller, which receives
messages from Keyman32 and other components around UI activation, active
keyboard, etc.

The master controller is keyman.exe's `TApplication` window, which does
not get destroyed and recreated, unlike the main form window.

Any thread which has responsibility for Keyman UI (keyman.exe main
thread, keymanx64.exe main thread) is also registered as a controller
thread. A controller thread has special handling for interactions with
keyman32 around focus tracking.

Caveats:

* While keymanx64 does not have a visible window and thus probably does
  not need to be registered as a controller thread, it doesn't really
  hurt.
* Note that keymanx64 registers the 32-bit controller thread as well,
  which again is probably unnecessary as the 64-bit process cannot
  interact with the 32-bit thread.
* Keyman's main form still handles wm_keyman_control messages, as there
  are a number of other components which post to that window (e.g. text
  editor, com library visual keyboard interactions). Unlike the original
  problem trigger, the reference handle is not stored long-term and so
  there is unlikely to be a problem with main form window re-creation
  causing an issue in these contexts.

There are several TODO items in this which I will address in follow-ups,
to reduce the scope of these changes.

I hope to cherry-pick this to stable-14.0, but will run for a while in
15.0 before doing so.
2021-05-11 14:47:17 +10:00
Marc Durdin
d7e4e18987 fix(windows): Handle Caps Lock event correctly from TIP
Fixes #4525.

This is a regression from #4468, which inadvertently added modifier
checks for `VK_CAPITAL` and `VK_NUMLOCK`, when it should not have done
so, as the flag was then being reset when the key was released rather
than toggled.

`ProcessModifierChange` pretended that it could handle `VK_CAPITAL` and
`VK_NUMLOCK` but it would never have worked, and the other caller (the
GetMessage hook) never passed those key events through, only Shift, Ctrl
and Alt, so that's now what the TIP handler does as well.

This leaves the rest of the fix from #4468 in place as that appears
correct.

I took the opportunity to move a repeated function declaration into
keyman64.h.
2021-02-26 10:54:30 +11:00
Marc Durdin
32d42d7d31 fix(windows): Track modifier changes in UWP apps
Fixes #4369.

When Keyman is not handling a particular virtual key, it does not
preserve the virtual key (TSF terminology, essentially reserves that
virtual key + modifier for Keyman). In this situation, Keyman still
receives and processes the virtual key event, but the modifier state
is not passed through by kmtip to keyman32. This is normally okay,
because our `GetMessage` hook is responsible for tracking modifiers.

However, in UWP apps, our `GetMessage` hook does not get run, and so
we lose the modifier keys. Thus, this update ensures that the modifier
keys are processed when received by the TSF TIP.

It does not hurt to process modifier events twice.
2021-02-11 10:17:21 +11:00
Marc Durdin
cea564a072 fix(windows): Improve refresh performance
When a keyboard is installed, Keyman will now only refresh its internal
state on a given thread when that thread receives focus and/or input,
rather than immediately. This will dramatically reduce the chatter
caused by Keyman Engine when a keyboard is installed or settings are
changed.
2020-12-17 11:13:18 +11:00
Marc Durdin
9e46b555d9 fix(windows): Rename to Keyman
Fixes #4003.

This addresses the majority of locations where we use the name "Keyman
Desktop" in code. There will be some filenames and paths that do not
change at this point -- particularly at a source level. For now, the
focus is on the user interface changes.

While making these changes, I also made the VERSION and MANIFEST
resources more consistent.
2020-12-02 09:56:14 +11:00
Marc Durdin
fc7b51c4ca fix(windows): remove msctf free from DllMain
Fixes #3650.

This removes the bad call to `FreeLibrary` that was still present in
a callee of `DllMain` in keyman32. The refactor moves responsibility for
loading TSF to the `SelectKeyboard` functions and gets rid of the
associated thread globals.

The `TSFINTERFACES` struct is of course a future candidate for a class.

In the process I removed a lot of cruft from keyman32.cpp which was
either obsolete, irrelevant or just plain wrong. None of which had
material impact on the running code.
2020-10-28 16:17:52 +11:00
Marc Durdin
0406cb1381 fix(windows): coverity reports for keyman32 2020-10-02 14:54:43 +10:00
Marc Durdin
d8c45f25dc [Windows] Address review comments 2018-10-29 16:34:00 +11:00
Marc Durdin
b395f7b122 [Windows] Remove USE_SERIALEVENTSERVER define 2018-10-19 05:34:48 +11:00
Marc Durdin
738e1946a6 [Windows] Debug logging and proof of concept tests for keyboarding support within metro-style apps
[Windows] More tidyup and robustness for metro app support - debug cleanup and serialization of input (not quite finished)

[windows] Refactor serialized input code when used with key event thread model

[windows] Add consistent precompiled headers for other projects

[windows] Merge console window test into metro support

[Windows] Tidy up work and identify additional TODOs for metro-style app support

[Windows] Ensure error case falls through to default hook processing for console windows

[Windows] Refactor shared memory into memory mapped file so we can cross 32-64 bit boundary

[Windows] Tweaks to C++ security calls and parameters

[Windows] Start refactor of SerialKeyEvent* classes

[Windows] Rename to SerialKeyEventServer (refactoring)

[Windows] Complete refactoring of SerialKeyEventClient class

[Windows] Further encapsulation and cleanup with 'interfaces' to reduce header pollution

[Windows] Complete serialization fix with move of modifier state management from client thread to server thread to guarantee consistency

[Windows] Replace atom-based keyboard switching with memory mapped file indexed to avoid security constraints

[Windows] Fixup Left Alt+Shift interaction with serializer

[Windows] Use Windows 8.1 SDK for test
2018-10-18 20:00:49 +11:00
Marc Durdin
56115da652 [Windows] Serialized input: don't trigger on console windows 2018-10-05 14:40:57 +10:00
Marc Durdin
7e2c21b8a7 [Windows] Refactor serialized input to use a low level keyboard hook to avoid conflicts 2018-10-03 15:22:38 +10:00