Create two processes when another terminal window is opened? - c

The topic might sound weird, but here's what I want to achieve:
In Terminal A, type command line as following:
./create proA
The first process proA is created. It outputs something like
This is process A.
Open another terminal window (called Terminal B). In Terminal B, type the following line:
./create proB
The second process proB is created. It outputs:
This is process B.
UPDATED:
I'm trying to create two processes that communicate with each other. Before going into more details, I just want to try if I can create another process that has some relationship with first process when another terminal window is opened.
Is it possible to achieve something like this? If so, can someone give any tip for how to start in c? Thanks!

The terminals don't matter for inter process communication. There are so many ways to communicate between processes that it doesn't make sense to highlight any of them here.
About having a own terminal for each process. Well:
(xterm -e "${COMMANDLINE1}" &) ; (xterm -e "${COMMANDLINE2}" &)

if you want to see only errors, you should use:
./process > /dev/null 2>&1
if you did't understood 2>&1, read below)
possible numbers:
0 — STDIN, 1 — STDOUT and 2 — STDERR
that means, all std errors will be printed in std out.

Related

How do I use pipes in xv6 to communicate between unrelated processes?

I understand how IPC works and how when you make a pipe before fork() the child/children can inherit the pipe for communication. However, I cant wrap my head around how I would do this for two unrelated processes? (i.e processes that are not the parent or children of each other?).
Im asking because Im trying to get one of my .c files to communicate with another .c file via pipes, but I dont know how that works explicitly in xv6. Any help/ideas would be greatly appreciated!!
There are several ways to accomplish this, for something simple, try checking out popen(). One program can spawn an unrelated one and then can then read and write to each other.
https://man7.org/linux/man-pages/man3/popen.3.html
For other solutions you should look into FIFO files or even sockets as a means of IPC.
Pipes are not able to communicate between 2 processes unless those two processes share a common ancestor, regardless of the Linux distro you use. If you are trying to allow 2 unrelated files to communicate, one of the exec() commands must be used in the child or parent process; this page may have what you're looking for.
What pipe does is to connect the standard output of one program to the standard input of another program.
Consider the cat and wc program in xv6. cat displays the content of a file or files. Let's say we have a text file test.txt with Hello World in it. cat can display its content like this:
$ cat test.txt
Hello World
wc calculates the number of lines, words, and characters in a file, files, OR stdin. So it can be used either like this(read from a file):
$ wc test.txt
1 2 12 test.txt
or this(read from stdin):
$ wc
Hello World
<Press Ctrl-D>
1 2 12
We can use pipe to connect these two commands:
$ cat test.txt | wc
1 2 12
So here cat reads the file and prints its content into stdout, but it doesn't get displayed onto the screen. Instead it gets feeded into the stdin of wc and wc counts the lines, words, and characters in it. Notice that this communication is unidirectional. It only goes from left to right, no backwards.
You can refer to the source code of these two commands to write your program. Basically all you have to do is to make sure the previous command outputs into stdout and the subsequent command reads from stdin.

Using streams to pipe input/output between *nix processes

I'm working on a fairly simple application in C. The end goal is to pipe the output from one process to in input of another in a *nix environment (yes, I am aware of the pipe() command and dup/dup2 but I'm trying to find away around using those commands). I was wondering if there is any way to connect the streams rather than using file descriptors (The systems aren't guaranteed to be POSIX compliant).
So basically I want to do something like this (pseudo-code)
pid = fork()
if pid == 0
// assign this process's stdin to the parents stdout.
stdin = parent.stdout;
exec() // launch new process that receives the parents stdout as stdin
// child stuff....
else
// parent stuff....
I know that it probably won't be as simple as just doing an assignment as above, but is there any way to do this using only streams? I tried looking around, but couldn't find anything..
Thanks!
sorry if I'm missing the point here but the whole philosophy of *nix is one program, one job. If you need a program to dump the contents of a program to the screen then you have the cat command. If the files too big and you need page breaks you pipe the output of cat to the more command:
cat myfile.txt | more
If you need to pipe between two terminal applications then you're meant to use the command line to do so:
myprog1 | myprog2
Obviously that's the philosophical approach, so if that doesn't help then can you clarify what you're trying to pipe and why you're trying to do it in process ?

Running program in background

Ive got my program in C, 6 source files, and the aim is to copy those files to any other Linux OS computer, and (probably compile, im newbie, so not sure what is needed here) run this program in background. Something like:
user#laptop:~$ program
Program is running in a background. In order to stop Program, type
XXX.
Any tips on this?
Thanks in advance!
Put a daemon(0,0); call in your C program.
stopping it is a bit trickier, I suppose there is only one copy of the program running. Put the program's PID in a file, write another utility (XXX) which reads the PID from the file and kills it.
Important: daemon forks, get the PID of the program after calling daemon.
But maybe you are too newby and just want to execute your program with program& and later kill it.
I completely missunderstood the question. You need shell scripting for this.
For file copying you can use scp. Execute command on the other host with ssh. It should be something like (not tested):
pid=`ssh user#host "make >/dev/null 2>&1; nohup ./program; echo $!`
later you can stop it with
ssh user#host "kill $pid"
First, you should fork().
In parent, you should just exit, in child process - you should handle SIGHUP signal.
In such way - you have daemon.

Poking a character into a parent process's buffer

I am trying to write a program that runs in the background that can "type" into a parent process, e.g. issue shell commands as if I had typed them myself at the keyboard. I have tried doing this with ungetc() to push back to STDIN:
#include <stdio.h>
int main (int argc, char** argv) {
ungetc('x', stdin);
return 0;
}
I would expect that doing:
$ gcc -o unget unget.c
$ ./unget&
Would have left me at the $ prompt with x there as if I'd just typed it, but instead I get nothing. Have I "lost" STDIN by going into the background? Thanks!
What you're trying to do simply cannot work. ungetc operates on the stdio FILE buffer, not the underlying open file description, and thus there is no way for it to be shared with another process.
You might try running the interactive session in screen and using screen's exec command to redirect file descriptors through a process that will inject data. Or you could implement something like this yourself using pseudo-tty devices.
Further, from your comments, I think what you're trying to do is an extremely bad idea. If you get unlucky and the input comes in the middle of you typing something interactively, it could have disastrous consequences. For instance imaging the automated command is
command_foo my_important_file
Now suppose you're in the middle of typing
rm -rf useless_crap
Bam! my_important_file just got deleted.
This second answer is not so much an answer to your question as written, but to the problem you're trying to solve. It's much more robust than sending keystrokes to your shell.
In the shell, use the trap command to setup a signal handler. For example:
trap "echo hello" USR2
Replace USR2 with whatever signal you want to use. Then run a child process that periodically sends the signal to its parent.
No -- ungetc only "pushes" the character back into the programs own buffer, so when the next character that same program reads will be what was passed to ungetc. Transmitting something back to the parent requires something entirely different (e.g., creating some pipes).
Just off the top of my head, maybe you could tweak the pipes of your terminal so that the cout of your child is cin for the parent. In bash it would go something like this:
exec 6>&1
exec 7<&0
exec 1>&7
exec 0<&6
Then when you start your programs the pipes should be inverted. So everything you put into cout should come out at cin from your parent (the bash process in this case).

ftp client controlled by pipe in C

I am trying to control ftp client from C program (OS X). I did fork and execve - process is started ok. The problem is with pipes - I can send command to ftp client process and get feedback from it just fine (If i send "help\n" i get back help output) but what I never get in pipe is "ftp> " prompt. Any ideas?
Ivan
Your ftp client is probably behaving differently if stdin/stdout is a terminal or something else (lots of program do, for a start the C library does buffering in a different way...) If you want to control that, search information about pseudo-terminals, that's a little too technical to be explained here. (And looks first at programs like expect, it's possible you won't have to write yours).
A program can examine stdin to find out whether it's a terminal or a pipe. In your case, the FTP program probably does that (for example to know whether it can use escape sequences to render progress bars or offer command line editing).
If you really need the prompt, you have to look into PTYs (pseudo terminals) which emulate a console.
wild guess: isn't the "ftp>" prompt written to STDERR ?

Resources