I want to create a generic logging application (Windows), which shall be able to execute an arbitrary executable as a child process and log the complete standard streams of a specific to a file (stdin, stdout, stderr).
Further, this logging application shall be acting like a kind of a "Man-in-the-Middle" application completely transparent, so that for user who is calling either the original executable or the wrapper logging application, there is not difference.
This functionality is somehow similar to the UNIX command line tool "tee", but as far as I found out, this tool is unfortunately not be able to log also the stdin (only stdout and stderr are supported). In addition, I want to log some more information e.g. who was the calling parent process, timestamps...
I want to use this especially for the command prompt: "cmd.exe" and rename the original and replace it with my own "cmd.exe" to automatically get a history file of all entered (stdin) commands, with its outputs (stdout, stderr).
Does someone have a good idea how to get this easily realized, perhaps with C# and pipes?
Best Regards,
Andreas
A simple version would indeed use pipes. In a native win32 app you would create some inheritable pipes and set them and the STARTF_USESTDHANDLES flag in the STARTUPINFO struct passed to CreateProcess. There is example code for this on MSDN.
You cannot however use this to replace cmd.exe because cmd.exe also uses the special Windows console API in interactive mode to implement features like the F7 history "dialog". You could take a look at some of the free terminal replacements like Console2 to see how they do it.
I have to write a process launcher which starts another process and reads its standard error up to a certain status flag but exits afterwards. The application that is started must keep running. I can succesfully redirect stderr to a pipe and read it from the launcher. My concern is what happens after the launcher terminates. The read end of the pipe is then closed and the application tries writing to a broken pipe. How does one undo the redirection after the child process is started?
What makes the problem even more challenging is that the launcher is cross platform and must be implemented in both POSIX and WinAPI.
Any suggestions on any of the platforms is much appreciated.
In case the parent process (the launcher) exits you will end up (1) with an orphan process and (2) with a broken pipe for stderr. Both these things sound bad...
Some ideas:
Redirect the stderr to a file (i imagine you would want to keep all error messages anyway). The parent/launcher/or any other monitoring process can read from the file as much as needed, at any time, and without getting I/O errors.
Detach the program from the launcher. Usually this is done using fork() followed by an execve() in the forked child process.
I am trying to sandbox I/O with multiple composite windows and I need to pipe whole driver I/O of sandboxed application.
I know how to pipe stdout stdin stderr on Windows, but I want to Pipe all output input devices availible. In C/C++.
How do I list them?
Can I store the old device pipe end?
It is possible to list them by
DeviceIOControl in win32 API
or by
ioctl in unix-like OSes.
When a console application is started from another console application, how does console ownership work?
I see four possibilities:
The second application inherits the console from the first application for its lifetime, with the console returning to the original owner on exit.
Each application has its own console. Windows then somehow merges the content of the two into what the "console" visible to the user
The second application get a handle to the console that belongs to the first application.
The console is placed into shared memory and both applications have equal "ownership"
It's quite possible that I missed something and none of these four options adequately describe what Windows does with its consoles.
If the answer is close to option 4. My follow-up question is which of the two processes is responsible for managing the window? (Handling graphical updates when the screen needs to be refreshed / redrawn, etc)
A concrete example: Run CMD. Then, using CMD, run [console application]. The [console application] will write to what appears to be the same console window that CMD was using.
None of your four possibilities is actually the case, and the answer to your follow-on question, "Which of the two processes is responsible for managing the window?", is that neither process is responsible. TUI programs don't have to know anything about windows at all, and, under the covers, aren't necessarily even plumbed in to the GUI.
Consoles are objects, accessed via handles just like files, directories, pipes, processes, and threads. A single process doesn't "own" a console via its handle to it any more than a process "owns" any file that it has an open handle to. Handles to consoles are inherited by child processes from their parents in the same way that all other (inheritable) handles are. Your TUI application, spawned by CMD, simply inherits the standard handles that CMD said that it should inherit, when it called CreateProcess() — which are usually going to be CMD's standard input, output, and error (unless the command-line told CMD to use some other handles as the child's standard input, output, and error).
Consoles aren't dependent upon CMD. They exist as long as there are (a) any open handles to the console's input or output buffers or (b) any processes otherwise "attached" to the console. So in your example you could kill CMD, but only when you terminated the child process too would the console actually be destroyed.
The process that is in charge of displaying the GUI windows in which consoles are presented is, in Windows NT prior to version 6.1, CSRSS, the Client-Server Runtime SubSystem. The window handling code is in WINSRV.DLL, which contains the "console server" that — under the covers — Win32 programs performing console I/O make LPC calls to. In Windows NT 6.1, this functionality, for reasons covered by Raymond Chen, moved out of CSRSS into a less-privileged process that CSRSS spawns.
My guess is somewhere between 3 and 4. The console is a self-standing object, which has standard input, output and error streams. These streams are attached to the first process that uses the console. Subsequent processes can also inherit these streams if not redirected (e.g. running a command with redirect to a file.)
Normally there is no contention, since parent processes usually wait for their child process to complete, and asynchronous processes typically start their own console (e.g. try "start cmd" in a command prompt) or redirect standard output.
However, there is nothing to stop both processes writing to the output stream at the same time - the streams are shared. This can be a problem when using some runtime libraries since writes to standard output/error may not be immediately flushed, leading to mixed garbled output. In general, having to processes actively writing to the same output stream is usually not a good idea, unless you take measures to co-ordinate their output through concurrency primitives like Mutexes, Events and the like.
The way the SDK talks about it strongly resembles 1. It is an option with CreateProcess, described as follows:
CREATE_NEW_CONSOLE
The new process has a new console, instead of inheriting its parent's console (the default). For more information, see Creation of a Console.
Output however happens through handles, you'd get one with GetStdHandle(). Passing STD_OUTPUT_HANDLE returns the console handle, assuming output isn't redirected. Actual output is done through WriteFile() or WriteConsole/Output(). If both processes keep writing output to the handle then their output will be randomly intermingled. This is otherwise indistinguishable from what would happen when two programs write to the same file handle.
Logically, there's a screen buffer associated with a console. You can tinker with it with SetConsoleScreenBufferXxx(). From that point of view you could call it shared memory. The actual implementation is undiscoverable, handles abstract them away, like any Win32 API. It is sure to have changed considerably in Vista with the new conhost.exe process.
CMD 'owns' the console. When it creates a process for an app, that app inherits handles to the console. It can read and write those. When the process goes away, CMD continues ownership.
Note: I'm not entirely sure that 'ownership' is the right word here. Windows will close the Console when CMD exits, but that may be a simple setting.
Each application will run in it's own AppDomain. Each AppDomain should be running it's own console.
Ah, you're right. I was thinking about running executables within a process and forgot they start their own process - I didn't drill down far enough.
I think it's spelled out fairly well in the documentation.
I'm developing an NSIS installer, to update a program that runs in background. Obviously, I'd like to send the program termination signals, because otherwise I repeatedly get a "can't write" error. How can I do this, with a limited overhead on installer size?
If your app has a window with a unique class name, you could just send it WM_CLOSE/WM_QUIT or whatever message you need.
Or your app could register a local server COM object the uninstaller could call (The system plugin can call COM methods)
Another way to do this is for the program to create a named event and wait on it, the uninstaller would signal it, this would be the clue for the program to quit.
As a last resort, you could kill the process with one of several plugins: KillProcDLL, Processes plug-in, KillProc plug-in and NsProcess
Also, the Locked List plugin might be a better alternative.