Eli Zaretskii writes: > So we need to load that DLL at run time via LoadLibrary, ... I have added that. > (I'm a bit surprised that Remote Desktop Services need to be used for > this purpose. Are you sure there's no other way for Emacs to know > that the system is going to be locked? Where did you read about the > need to reset the keyboard hook state in that case, and the way to do > it?) For me, the need to reset the hook state is implied by the existence of the ‘reset_w32_kbdhook_state’ function defined in ‘w32fns.c’ and its call site. This function has been there since 2016, but was never called, because the ‘WM_WTSSESSION_CHANGE’ message wasn't received. From [0]: MS> This message is sent only to applications that have registered to MS> receive this message by calling WTSRegisterSessionNotification. This seems to be the only way to find out it's being locked; at least I couldn't find anything indicating otherwise on the Microsoft website and a quick web search didn't turn up anything either. >> To receive session notifications, one must provide a window handle, >> which is fine if Emacs does not run in console mode. I don't know >> whether it is possible to get these notifications in console Emacs; at >> least using the console handle didn't work for me. > > Please try the technique used by the function find_child_console which > is defined in w32proc.c. Unfortunately, this didn't work for me. I tried calling ‘EnumWindows(find_child_console, ...)’ with a ‘child_process’ instance containing the current process id as returned by ‘GetCurrentProcessId’, but I don't seem to get a useful window handle. I must be doing something wrong here. OTOH, [1] says: MS> Note For Windows 8 and later, EnumWindows enumerates only top-level MS> windows of desktop apps. Does this mean that ‘EnumWindows’ it doesn't work for console windows or is this remark irrelevant here? I am not familiar with the Windows terminology. Come to think of it, don't I need the window handle of the console window that Emacs is running in, which would imply that a handle for Emacs' pid doesn't exist? I was starting Emacs in cmd.exe using ‘emacs -Q -nw’, so I would probably have to find the pid of the ‘cmd’ process first, right? >> I also noticed that while the keyboard hook is set up in console mode >> using ‘setup_w32_kbdhook’, there does not seem to be a corresponding >> call to ‘remove_w32_kbdhook’. > > Doesn't Windows remove the hook when the process exits? According to [2] we have to remove the hook: MS> Before terminating, an application must call the UnhookWindowsHookEx MS> function function to free system resources associated with the hook. >> Also, in console mode the keyboard hook is always installed, while >> in GUI Emacs it is only installed when ‘WINDOWSNT’ is defined. > > That's because w32console.c is not compiled into the Cygwin build > (which does not define WINDOWSNT), whereas w32fns.c is. Ok, that makes sense, I have removed my superfluous #ifdef. > Do we really need to use WTSRegisterSessionNotificationEx? Can't we > use WTSRegisterSessionNotification instead? AFAIK, the latter is > available since Windows XP, whereas the former only since Vista. Yes, ‘WTSRegisterSessionNotification’ works, too. However, [3] says that the minimum supported client here is Windows Vista, as with the ‘-Ex’ version. I attached my current patch version. Regards, Raffael [0] https://learn.microsoft.com/en-us/windows/win32/termserv/wm-wtssession-change [1] https://learn.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-enumwindows [2] https://learn.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-setwindowshookexa [3] https://learn.microsoft.com/en-us/windows/win32/api/wtsapi32/nf-wtsapi32-wtsregistersessionnotification