Differentiate between a "direct" (i.e. "directly" started by a user) and a non-direct (i.e. started on behalf) process

Avineshwar (Gartner) 1 Reputation point

I am working on a project that is supposed to control whether an application should be allowed to execute or not as well as handle UAC for the users i.e. a user at the maximum, only sees a customized consent screen and never a credential prompt. I intercept the process and block the execution while our custom code is executing and making some determination about the file (now, process). For some background, running custom code is possible since I use a privilege management system where there is an option to run custom code. There were multiple issues, and, I am more or less past that i.e. the project works. I have tested around ~150 setups (pre and post install) and they all seem to be fine; of course, each of these apps have not been tested thoroughly considering them as out-of-scope as well as there are obviously 1000s of apps out there and covering them is the intention. Now, a few technical decision that was made to make this project possible are anti-best-practice. That said, I still went that route since that seemed to be the only possible solution for this based on my exposure with Windows Internals.

Determine if a process is invoked "directly" by a user
If an (immediate, not anywhere in the process tree) invoking process matches from a list of processes (e.g. explorer, cmd, powershell, runtimebroker, chrome, firefox), then it has to be invoked directly by user. I know there are edge cases to this (e.g. there are non-direct processes where a parent could match as per this logic). The implementation ensures we gracefully handle them.
Since I only allow (directly) user started processes after they meet certain criteria, this is an "explicit deny" logic. I prefer "implicit deny" and "explicit allow"
Is there a simple and better way to detect whether a process has been "directly" started by the user? Is there some Windows API that can do this for me? If not, why this is hard to implement or not possible or not worthy?

Whatever suggestions are provided, please share some documentation, if available, as that is going to help in more than one way.

Windows 10
Windows 10
A Microsoft operating system that runs on personal computers and tablets.
10,780 questions
Windows API - Win32
Windows API - Win32
A core set of Windows application programming interfaces (APIs) for desktop and server applications. Previously known as Win32 API.
2,443 questions
0 comments No comments
{count} votes

3 answers

Sort by: Most helpful
  1. Castorix31 82,031 Reputation points

    Is there a simple and better way to detect whether a process has been "directly" started by the user? Is there some Windows API that can do this for me? If not, why this is hard to implement or not possible or not worthy?

    Not sure if it will help you, but you can get the parent of a process with
    NtQueryInformationProcess and InheritedFromUniqueProcessId flag
    I had posted a sample in C# in this thread to differentiate a process launched from Explorer or from the Task Scheduler

  2. MotoX80 32,246 Reputation points

    What is the vulnerability that you are trying to address? Are you just trying to prevent someone from programmatically doing SendKeys and using your app?

    What about implementing a "Click on all pictures that show a flower" CAPTCHA process as part of your "customized consent screen" ? Now I realize that putting flowers on the screen might not be appropriate in a business environment, but from my experience of trying to automate applications it isn't easy to "read" the screen from code. As you noted, maybe just monitoring the mouse position would suffice. Display a graphic that has instructions to move the mouse over an image. Or something like that. Within the main form you should be able to reference X/Y mouse coordinates and detect "human" activity.

    0 comments No comments

  3. Avineshwar (Gartner) 1 Reputation point

    Well, I have not built an app, this is a framework where other applications operate in (e.g. Microsoft Word, WinRAR, WinZip, Zoom). I want to control what applications can be installed and then further be operated just fine. So, to that extent, this is a privilege management system. For comparison, and if you are familiar, imagine an amalgamation of SRP and AppLocker, with more things (e.g. security token swapping/replacement).

    So, talking WinForms won't be correct, as I don't inject/control anything in any app. I hook into Windows Kernel. I am assuming I am at the right place asking all these questions though, yeah?

    Now, in theory, it does looks like that in order to "truly" (like, really truly) detect if it was a user who just opened (well, tried to since I intercept it right away before allowing it) an application (whether via Desktop, Start Menu, pinned shortcut, and so on), things that go into this are: input device and/or location of cursor AND immediate parent process.