The standard I/O function library provides a popen function that initiates another process to execute a shell command line.
Here we call the process called Popen the parent process, and the process initiated by Popen is called a subprocess.
The Popen function also creates a pipe for parent-child interprocess communication. The subprocess either reads the information from the pipe or writes the information to the pipe, and whether it is read or write depends on the parameters that are passed when the parent process calls Popen. The definition of Popen and Pclose is given below:
03 |
function function: Popen () invokes fork () to produce the child process, and then calls/bin/sh-c from the child process to execute the command of the parameter command. |
04 |
The parameter type can be read by using "R", and "w" for writing. |
05 |
According to this type value, Popen () establishes a standard output device or standard input device that is attached to a subprocess, and then returns a file pointer. |
06 |
The process can then use this file pointer to read the output device of a child process or to a standard input device written to a child process |
07 |
Return value: Returns a file pointer if successful, otherwise null is returned, and the reason for the error is stored in errno |
09 |
FILE * Popen (const char * command,constchar * type); |
12 |
function function: Pclose () is used to close the pipe and file pointers established by Popen. Parameter stream is the file pointer previously returned by Popen () |
13 |
Return value: If the end state of the shell is returned successfully (also known as the terminating state of the child process), if error returns-1, the cause of the error is stored in errno |
15 |
int Pclose (FILE * stream); |
The following example looks at the use of Popen:
If we want to get the number of files in the current directory, we can use it under the shell:
We can write this in the program:
01 |
/* Get the number of files in the current directory * * |
11 |
Charresult_buf[maxline], Command[maxline]; |
12 |
INTRC = 0; Used to receive command return values |
15 |
/* Write the command you want to execute to buf*/ |
16 |
snprintf (command,sizeof (command), "ls./| wc-l"); |
18 |
* * Execute pre-set commands and read out the standard output of the command. |
19 |
fp = popen (Command, "R"); |
22 |
Perror ("Popen execution failed. "); |
25 |
while (Fgets (result_buf,sizeof (RESULT_BUF), FP)!= NULL) |
27 |
* * For the following output better, the command returned to remove the line break * * |
28 |
if (' \ n ' = Result_buf[strlen (RESULT_BUF)-1]) |
30 |
Result_buf[strlen (RESULT_BUF)-1] = '; |
32 |
printf ("command"%s "output"%s "\ r \ n", command, RESULT_BUF); |
35 |
/* Wait for command execution complete and close pipe and file pointer. |
39 |
Perror ("Close file pointer failed"); |
44 |
printf ("command%s" subprocess End status "%d" command return value "%d" \ r \ n), command, RC, Wexitstatus (RC)); |
Compile and execute:
$ gcc POPEN.C
$./a.out
Command "ls./| Wc-l "Output" 2 "
Command "ls./| Wc-l "Child process End status" 0 "command return value" 0 "
The above Popen captures only the standard output of the command, and if command execution fails, the child process prints the error message to the standard error output and the parent process is not available. For example, command is "LS nofile.txt", in fact we do not have nofile.txt this file, then the shell will output "Ls:nofile.txt:No such file or directory." This output is on the standard error output. The above program is not available.
Note: If you set the command in the above program to "LS Nofile.txt", compile the execution program and you will see the following results:
$ gcc POPEN.C
$./a.out
Ls:nofile.txt:No such file or directory
Command "LS nofile.txt" sub process End State "256" command return value "1"
Note that the first row of output is not the output of the parent process, but the standard error output of the child process.
Sometimes the child process's error message is useful, so how can the parent process get the child process error message?
Here we can redirect the error output of the subprocess, redirect the error output to standard output (2>&1) so that the parent process can catch the error message of the subprocess. For example, the command is "LS nofile.txt 2>&1" and the output is as follows:
Command "LS nofile.txt 2>&1" output "Ls:nofile.txt:No such file or directory"
Command "LS nofile.txt 2>&1" Sub process End State "256" command return value "1"
attached: The termination status of the child process to determine the macro involved, set the process termination status for status.
Wifexited (status) is a value other than 0 if the child process ends normally.
Wexitstatus (status) Gets the end code returned by the subprocess exit (), typically using the wifexited to determine whether the macro will be used before it ends normally.
wifsignaled (status) This macro value is true if the child process ends because of a signal.
Wtermsig (status) to get the child process because the signal to abort the signal code, the general will use the wifsignaled to judge before using this macro.
wifstopped (status) This macro value is true if the child process is in a paused execution condition. This is generally the case only if you are using wuntraced.
Wstopsig (status) obtains the signal code that raises the child process pause, usually uses wifstopped to judge before using this macro.
2011-11-12 Ninhong qdurenhongcai@163.com
Reprint please indicate the source.
01 |
gstring* exec_and_out (char* cmd) |
03 |
gstring* ret = g_string_new (""); |
08 |
Popen Execute and Open stream |
09 |
stream = Popen (cmd, "R"); |