Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Check if Windows is currently locked

I'm on Windows 10 Pro x64 ver 1703 build 15063.726, trying to write a program rebooter service. It runs under my user on admin permissions, every 10 minutes via a scheduled task.

If the server is unavailable or borked:

  • if my computer is locked, the rebooter kills and restarts the server program.
  • if my computer isn't locked, the rebooter shows a dialog to confirm reboot. I may be doing work on the server program and not want a reboot to ruin any debugging.

The only complication is detecting if the computer is locked. I've tried several methods:

  1. OpenInputDesktop()

Returns NULL only if the user has started to input their password since the computer was locked. Besides that returns a valid handle. Presumably the input desktop isn't deselected until the user attempts to login and their input switches.

  1. OpenInputDesktop() vs GetThreadDesktop()

(Passing in GetCurrentThreadID() of course)

Handles still match, probably due to same reason 1 fails.

  1. Process check for LockApp.exe/LockAppHost.exe

Seems to relate to user inputting their password as well... or because my server rebooter app is 32-bit, having problems reading the 64-bit process LockApp.exe.

  1. GetForegroundWindow() returns null when locked

While mentioned as dubious, I tried this too. False negative, said it wasn't locked

  1. Switching desktop manually and seeing if it worked

Described with code example here, this one was also a bust and gave a false negative.

Is there any way left? I'd really rather not have a service just for registering locking/unlocking running constantly.

Or should one of these ways worked already, and my Windows is bugged?

Cheers

like image 626
Phi Avatar asked Nov 20 '17 13:11

Phi


People also ask

How do I unlock my Microsoft Windows?

Press CTRL+ALT+DELETE to unlock the computer. Type the logon information for the last logged on user, and then click OK. When the Unlock Computer dialog box disappears, press CTRL+ALT+DELETE and log on normally.

How do I unlock my screen on Windows 10?

Unlocking Your Computer From the Windows 10 login screen, press Ctrl + Alt + Delete (press and hold down the Ctrl key, then press and hold down the Alt key, press and release the Delete key, and then finally release the keys).

Does your computer still run when locked?

Yes, when the computer is in lock mode the program and you run any programs it will run, if it is in sleep mode, program will stop running.


2 Answers

I'm not sure how to do it in C#, but with PowerShell, I checked if the LockApp.exe threads are Suspended to see if the desktop is unlocked or locked, like so:

$lockapp = Get-Process lockapp

for ($i = 0; $i -lt 60; $i++)
{
    $process=[System.Diagnostics.Process]::GetProcessById($lockapp.Id)
    $threads=$process.Threads
    if ($threads[0].WaitReason -eq "Suspended") { "It's unlocked" } else { "It's locked" }
    Sleep 1
}

This script loops for 60 seconds and writes out the locked/unlocked state.

like image 56
Keith Lammers Avatar answered Oct 04 '22 11:10

Keith Lammers


Searching for LogonUI running in process list seems to be the way to go.

pslist is 32-bit but in the background, spawns a 64-bit process to list the 64-bit counterparts, so there's no dependency on the C# app being x86 or x64 (or LockApp for that matter).

It's not great, but it works.

Process p = new Process
{
    StartInfo = new ProcessStartInfo
    {
        FileName = @"[path to SysSuite]\pslist.exe",
        Arguments = " -nobanner logonui",
        UseShellExecute = false,
        RedirectStandardOutput = true,
        CreateNoWindow = true
    }
};

p.Start();
p.WaitForExit();
string s = p.StandardOutput.ReadToEnd();
if (!s.Contains("process logonui was not found on "))
{
    Debug.WriteLine("Windows is locked.");
    return true;
}

It's really dumb that Windows has no built-in way for such a basic feature, though.

EDIT: Nope, this way doesn't work either. While LogonUI does run upon lock, and sticks around for a while, I've had it also vanish if the computer isn't interacted with for a couple hours or so. Notably, overnight, my computer gets clogged with dialogs that only spawn that frequently if logged in.

I'm now using SystemEvents.SessionSwitch and a single process as Hans suggested. I was kinda hoping for a current reading thing for future reference, but at this point it's mostly curiosity.

like image 32
Phi Avatar answered Oct 04 '22 12:10

Phi