Is there a way to send data to another process'

2019-02-14 07:30发布

问题:

I was wondering if there was an API, however obscure it would be, that would allow someone to send data to another process's stdin stream under Mac OS X. Under Linux, if I remember correctly, you can use the filesystem in /proc to access these streams (with the correct permissions, of course).

I dunno. Mach ports, anyone?

回答1:

Unfortunately, I don't believe you can do that -- MacPorts are all userland, and the operation you require needs (either a lot of trickery, see below, or) kernel cooperation, which, I believe, isn't forthcoming. For example, Mac OSX Internals, a System Approach in the section on file-descriptor passing, says

The descriptor is local to the process in that it is meaningful only in the process that acquired the descriptorsay, by opening a file. In particular, a process A cannot access a file that is open in another process B by simply using the value of the descriptor representing that file in B.

and then goes on to describe how FDs are sent.

The "trickery" part would require you getting some code of yours to run (either in userland or as part of the kernel) within the other process.

For example, you could do it in userland by patching the binary file that's their executable -- find any instruction early in its startup path that's sure to be executed, and put in its stead a jump to your own code which sends the FD to your watching daemon process, executes the patched-away instruction, then jumps back to the other process's normal sequential flow.

To do it at kernel level would require similar patches to either the kernel code itself, or to code which the kernel loads and runs with entire, unverified trust (so they can hijack an unrelated process's file descriptor table entries) -- I sure hope there are no such code paths left in Mac OS X (since their main use would no doubt be by viruses, trojan horses, and other malware of all kinds) but, if there are and you can find them, this might be a more general solution than patching every single binary executable of interest.

Back to userland, another fairly general approach might be to patch dynamically loaded libraries that all processes of interest load, instead of patching the various processes' several executables.



回答2:

Just a thought, but couldn't you make a pipe, and redirect that (named) pipe to the standard input of the process when starting that process?

Roughly somethink like

mkfifo MYPIPE
Prog < MYPIPE
echo "test" > MYPIPE


回答3:

If you are running the target process at a terminal then you can use writevt, whose source code is here.

Suppose for example that you are running the "cat" command on terminal ttys000.

On Terminal 1:

$ tty
/dev/ttys000
$ cat

On Terminal 2:

$ sudo ./writevt /dev/ttys000 'Hello!^M'

The ^M above is a control character. On my mac, you can input this character by typing Ctrl-V followed by Ctrl-<enter>.

Here is the result at Terminal 1:

$ tty
/dev/ttys000
$ cat
Hello!
Hello!

The writevt program can be compiled from the writevt.c source file with gcc:

$ gcc -o writevt writevt.c 


回答4:

Presuming that it's with the users permission (i.e. you want to capture information from a third party app, to redirect to another app, like Rogue Amoeba's audio apps or some video stream capture apps) then I'd say you either want to look at kernel extensions, or Input Managers.

(See also fscript anywhere, SIMBL and Application Enhancer - all examples of software that inject functionality into third party apps).

A lot of older techniques for user driven code injection have been restricted in 10.6 (input managers are harder to install, for instance).

If you're interested in user input rather than stdin, the replacement Input Method Kit may actually be 'good enough' - classically, Input Managers have been used to inject all sorts of code into applications.

On the other hand, if you want to do this without user permission (i.e. key logging) then you're into hacking. There probably is a chain of as yet unpatched vulnerabilities that can be combined to do what you want to do, but whoever knows it is likely to be making money from it.



回答5:

Well, technically you could mach-inject a thread into the target process and then have it send a dup of the stdin file descriptor back to you… But you probably shouldn't. :-)

What are you really trying to do?



标签: macos stdin