Redmon starts application as user SYSTEM instead of the current user - windows

I'm using Redmon to start a .Net application that reads data from stdin, then send it to ghostscript to generate a .pdf file, before wrapping everything in a .zip file, which is uploaded to an ftp server.
The problem is, that under some Windows implementations, particularly Windows 10 Pro, the started process will run as user SYSTEM instead of the current user. However, it doesn't seem to be the case every time. I have seen it running nicely on a pc for several weeks, and suddenly something must have changed, because the process began to run as SYSTEM, which makes my application fail because of missing registry entries and user-specific config files.
In Redmon, there is a setting called "run as user", which is enabled, but it doesn't really change anything. The documentation states that "this may or may not work".
I thought of letting the application fork a new process as the currently logged-in user, as suggested by others, but I only know how to do this by supplying a username and the user's password, which I don't have. I don't want to ask the user to enter his credentials.
So basically, I need to know why Redmon (or the Windows spooler) changes to the SYSTEM user on some systems, if this is a Windows setting, and if there is a way to avoid this. Alternatively, if I at least could have the SYSTEM process interact with the desktop, it would also be a step in the right direction.

Related

How to get a Standard EXE and WinService EXE to communicate with each other?

We have an application that is part standard EXE and part WinService EXE. The standard EXE is spawned by the Run section of the registry and comes to life at login under the credentials of the user who just logged in. The WinService EXE is set to Auto Run and therefore is always running and is running as LocalSystem (essentially administrator).
We need these two programs to share data by writing information to XML files.
The app works fine when the logged in user has access to the installed folder (C:\Program Files\ourApp). The Standard EXE writes the data and the WinService EXE reads it without issue, all is well.
However, when the logged in user does not have access to write to the installed folder, the data gets caught up in UAC Virtualization and Data Redirection and ends up somewhere else and the WinService does not find nor cannot read it from the installed folder.
To circumvent this, we tried having both the standard EXE and the WinService EXE write to and read from %ProgramData%. This would work fine except that standard users do not have permissions to write to %ProgramData%.
We cannot use %LocalAppData% because for the logged in user that would be C:\Users\LoggedInUser\AppData\Local and for the winservice it would be C:\Users\Administrator\AppData\Local.
Is there any place left in Vista and Win7 with UAC Virtualization enabled that will allow both a Standard EXE running with only user priveleges and a WinService running as LocalSystem to talk to each other. We tried the registry but the problems are even worse. Also last but not least. We need this to work with XP without any differences in code. Meaning XP also has environment variables for %ProgramData%, %LocalAppData% etc, can it work in both.
Two ideas:
Have each app expose a WCF endpoint using the named pipe
transport, and have them talk to each other over a simple interface
of your choosing.
Use Memory Mapped Files to communicate like
you were with disk files.

Running GUI application in the Windows service mode

I'm writing a server running as a Windows service that by request invokes Firefox to generate a pdf snapshot of a webpage.
I know it is a bad idea to run a GUI program in service mode, but the server nature of my program restricts from running it in the user mode. Running a user-level 'proxy' also is not an option, since there might be no interactive user logged-in on the machine with the server running.
In my experiments Firefox successfully produced pdf when the service was running under a user account that was already logged-in. Obviously it didn't work in other cases: for Local System and user accounts that weren't logged-in. Under LocalSystem with 'Allow service to interact with desktop' option enabled I could see the Firefox started that reports that it's unable to find a printer.
Since it wouldn't be practical to require an opened user session for the pdf server to run, is there any workaround for this except running the whole thing from a virtual machine?
UPDATE: I figured that the problem wasn't really with account permissions, but with an invisible modal dialog that FF was waiting on while running in the service mode.
However it's still unable to create a pdf when FF is running under the LocalSystem account. FF says it can't find a printer and I'm wondering if this is a permission that could be somehow enabled?
You might want to try a different approach where you'd include some .NET PDF library (PDFsharp is a good, open source, choice) in your project and than use that in conjuction with WebBrowser control you'd also include in your project to render the PDF.
Don't forget to use STAThread attribute if you try this.
I've been through a similar conundrum with the MS Word running unattended. What you need to do is to login as the user you set up to be used to run firefox process and go through the process of setting up printers.
It is possible that just logging in as that user will be enough - there is some stuff performed during the first logon.
I apologize I was not clear enough - I mean you have to logon interactively using that account, configure the default printer, logout, and then run your service
Can you run the program as a Scheduled Task instead? The task can be assigned to a given user account which should work around the service limitations.
A couple of year ago I had a related issue: Shared Network Printer on pseudo-device starting up Ghostscript for PS->PCL translation and printing to real printer. The print-spooler service ran as Local System and the pseudo-device driver hat troubles executing Ghostscript from the service-mode. I was able to solve the problem by copying a couple of registry keys from the HKCU-hive to HKLM.

Startup applications per-user and Windows Installer

I have an application that is installed per-machine (since it uses a service). One part of the application is a system tray application that allows the logged-in user to monitor the service operations. I'm trying to figure out how to best install this monitor application.
Each individual user should be allowed to configure whether or not he/she wants to run the monitor application at login. This means that the HKLM/Software/Microsoft/Windows/Run key is out - this only allows configuration for all users.
There is of course the corresponding HKCU-key, however if one simply installs to this key, it will only be for the user that installs the application.
The SO question Launch app on startup for all users, but also allow per-user setting (Windows) refers to the technique of simply having a user-configurable regkey or similar that is checked by the startup-application on to determine whether or not to run. But this means that the application has to start in order to check the value and I would prefer not to bloat the user's startup if I can avoid it. The benefit of this approach is that it is possible to remove the regkey on uninstall.
Another way to accomplish the installation part may be to use Active Setup to create the HKCU regkey on login, this is however undocumented and it seems to me that there is no easy way to uninstall the regkey if the application is uninstalled? I would assume that leaving registry values under the Run key for HKCU might create problems for users after uninstallation.
Is there a standard way to handle per-user startup applications using Windows Installer? Especially with regard to how to uninstall these later on?
Looks to me like you're close to answering your own question. I think you may just need to divide up the responsibility of configures whether to auto-run for each user... er, let me explain:
You can use either a self-healing component of HKCU Registry keys or ActiveSetup to ensure that every user gets the configuration.
If you use an HKCU Registry key, your MSI installer needs to have a component with it's "key file" as an HKCU entry--so thus the first time a new user launches the program, Windows Installer will do a self-heal to write those entries. One of those entries would be your HKCU/Software/Microsoft/Windows/Run value, but not the key value, because you want the users to be able to remove it and not have it come back every time they run the program! You would then want your program to have an option to remove the auto-run value.
If you use ActiveSetup (which I would recommend because it's simple and it "just works"), then you might find it easiest to make a simple app (or VBScript or such) which prompts the user if they want to have the monitor program auto-run. So your ActiveSetup would launch the prompt program/script, and the prompt program would create the HKCU/Software/Microsoft/Windows/Run value or, better yet, just a shortcut in the user's Start Menu\Programs\Startup directory.
A bit lowtech possibly, but can't you just add a shortcut to the user's startup folder (Start menu/Programs/Startup)?
I guess you would use the HKLM/Software/Microsoft/Windows/Run in this case. The feature to run the monitor application at startup or not really belongs to the monitor application and not the installer. At log-on the monitor application can detect if this is the first time that the monitor application has been run and present the user with an option to always run the monitor application on start up or not.

Where should I store shared resources between LocalSystem and regular user with UAC?

My application consists of two parts: A Windows Service running under the LocalSystem account and a client process running under the currently logged in regular user.
I need to deploy the application across Windows versions from XP up to Win7.
The client will retrieve files from the web and collect user data from the user.
The service will construct files and data of it's own which the client needs to read.
I'm trying to figure out the best place (registry or filesystem, or mix) to store all this. One file the client or service needs to be able to retrieve from the net is an update_patch executable which needs to run whenever an upgrade is available.
I need to be sure the initial installer SETUP.EXE, and also the update_patch can figure out this ideal location and set a RegKey to be read later by both client and server telling them the magic location (The SETUP.EXE will run with elevated privileges since it needs to install the service)
On my Win7 test system the service %APPDATA% points to:
C:\Windows\system32\config\systemprofile\AppData\Roaming
and the %APPDATA% of the client points to:
C:\Users\(username)\AppData\Roaming
Interestingly Google Chrome stores everything (App and Data) in
C:\Users\(username)\AppData\Local\Google\Chrome
Chrome runs pretty much in exactly the way I want my suite to run (able to silently update itself in the background)
What I'm trying to avoid is nasty popups warning the user that the app wants to modify the system, and I want to avoid problems when VirtualStore doesn't exist because the user is running XP/2000/2003 or has UAC turned off.
My target audience are non-tech-savvy general Windows users.
Chrome doesn't have any services running under the LocalSystem account, though.
If you want to have files that can be shared between accounts on the same system, store them under the %ALLUSERSPROFILE% folder.
If you just want to be able to auto-update programs, then doing what Chrome does is fine: just make sure you launch the updated elevated when UAC is turned on.

Starting a Windows service in an interactive session

A colleague has a batch script program which needs to to run on a Windows Server in console mode, so that it has access to a Windows interactive session. The server is rebooted at regular intervals automatically (there's an unrelated closed-source application that runs on this machine that we have no control over). After a reboot he wants to automatically start a Windows interactive session and have this script run, plus the service needs to also have access to network resources (CIFS drives, in particular).
Here's what we've tried so far:
Start as Windows service. This failed, since a Windows service can either have access to interactive session or to network resources, but never both.
Used Microsoft management console to add the script to run at startup, however this did not work.
Used an HKLM registry key to start to run this script, however it only gets started when we manually open a remote desktop session on the server.
Creating a scheduled task. The program invoked did not have access to interactive windows session.
Any other suggestions? (Or maybe he missed something when he set up one of these suggestions?)
In case "Interact with desktop" on the service is not enough (I have seen a handful of cases where it is not), you can combine it with AutoAdminLogon. Create three (or four for a domain) REG_SZ values under HKLM\Software\Microsoft\Windows NT\CurrentVersion\Winlogon:
DefaultUsername
DefaultPassword
DefaultDomain
AutoAdminLogon
AutoAdminLogon should be set to the string "1", the others are self-explanatory.
Obviously this has security issues big enough to fly Jupiter through.
Have you tried having your script run as a Windows service, but allowing it to interact with the desktop?
Specifically:
Go to the service properties page
Click on the "Log On" tab
Select "Local System account"
Check "Allow service to interact with desktop"
See my similar question and real answer to it: How to start a process from windows service into currently logged in user's session
NOTE: "Interact with desktop" checkbox is not enough at all.
I recommend going about this another way. You could build another Windows app that communicates via IPC to the Windows Service and that could be what deals with the closed souorce application. But if you must, you can specify an option in the service (you can do this through MMC, registry, etc). Basically, you can see this option by going to Computer Management->Services and Applications->Services->Right click your service->Change account to Local System and check "Allow system to interact with desktop."
However, again, I recommend choosing another path.
I had to do something similar recently; a route that I found but discarded due to security concerns is to have the interactive service set self as running in interactive mode and then run the ImpersonateUser function in the win32 API, which I think will provide the benefits of both a user and the interactive session available from the LocalSystem.
Needless to say, if someone broke into a service that did that, they would have total control of the machine.

Resources