views:

150

answers:

5

In my C program I want to know if my executable is run in foreground like this

$./a.out

or like this

$./a.out &
+2  A: 

To my knowledge this is not possible and usually not necessary either.

Please explain why you want to do this.

dbemerlin
Say my process is doing a process intensive job and wants to print a status bar like thing till the calculation is complete by printing '#' via a signal handler of SIGALRM. If my process is run in background, I don't want to print the '#'s . That is where I wanted to differentiate.
Saradhi
Simply add a --quiet flag and programs that don't want output should call it as ./a.out --quiet. See the getopt() manpages.
dbemerlin
There is precedent for this: for example, scp transfers files in the foreground and the background, but it only updates the status bar when it is in the foreground.
ephemient
scp has several config values and command line parameters that control the status but AFAIR there is no status bar by default (i rarely use scp so i might be wrong). Anyways: Why create a complex solution to a simple problem? If the caller doesn't want a status bar (maybe even when the program is in foreground) he adds a parameter and it's done. Simple Problem, simple Solution. If you want the opposite behaviour just name the parameter --progress and invert the show/hide.
dbemerlin
A: 

For making your executable run in background latter one is correct.

You misunderstood the question. (Wasn't my downvote, but thought you deserved a reason for it just the same.)
Roger Pate
Boy, you downvoters are really harsh on a new SO user. @user278092: If you agree this answer is off the mark, feel free to delete it.
Roger Pate
A: 

[invalid]
IIRC, getppid() (on *nix systems) will give you the parent id. if it is 0, the 'console' is your parent and so you are running in the background.
[/invalid]

[edit]

int devtty;
if ((devtty = open ("/dev/tty", O_RDWR)) < 0)
   printf ("daemon\n");


note that this is only valid on *nix systems (and then only if nobody has deleted /dev/tty -- for whatever reason)
[/edit]

KevinDTimm
dbemerlin
I doubt that getppid() can return 0. It will either return 1 (if you're detached from the console and the kernel made you a child of the init process) or the PID of the bash shell which started you.
Aaron Digulla
edited, absolutely an invalid recollection
KevinDTimm
c'mon now, I was downvoted before the edit, but after?
KevinDTimm
`/dev/tty` is openable even if you're backgrounded, as long as you still have a controlling terminal.
ephemient
+7  A: 

From the Bash Reference Manual: Job Control Basics:

Background processes are those whose process group id differs from the terminal's; such processes are immune to keyboard-generated signals. Only foreground processes are allowed to read from or write to the terminal. Background processes which attempt to read from (write to) the terminal are sent a SIGTTIN (SIGTTOU) signal by the terminal driver, which, unless caught, suspends the process.

So the solution is to install a signal handler for SIGTTIN and then try to read from stdin (turn buffering off or it will block). If you get "0 bytes read" back, then you're running in the foreground.

[EDIT] Note that the status of a process can change. You can use the job control commands of the shell (Ctrl-Z, bg, fg and jobs) to do this.

Aaron Digulla
+3  A: 
ephemient