如何使用参数在 linux 中的 C 代码中执行外部程序?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/5237482/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How do I execute external program within C code in linux with arguments?
提问by js0823
I want to execute another program within C code. For example, I want to execute a command
我想在 C 代码中执行另一个程序。比如我想执行一个命令
./foo 1 2 3
foo
is the program which exists in the same folder, and 1 2 3
are arguments.
foo
program creates a file which will be used in my code.
foo
是存在于同一文件夹中的程序,并且1 2 3
是参数。
foo
程序创建一个将在我的代码中使用的文件。
How do I do this?
我该怎么做呢?
采纳答案by Erik
For a simple way, use system()
:
对于简单的方法,请使用system()
:
#include <stdlib.h>
...
int status = system("./foo 1 2 3");
system()
will wait for foo to complete execution, then return a status variable which you can use to check e.g. exitcode (the command's exitcode gets multiplied by 256, so divide system()'s return value by that to get the actual exitcode: int exitcode = status / 256
).
system()
将等待 foo 完成执行,然后返回一个状态变量,您可以使用它来检查退出代码(命令的退出代码乘以 256,因此将 system() 的返回值除以该值以获得实际的退出代码:)int exitcode = status / 256
。
The manpage for wait()
(in section 2, man 2 wait
on your Linux system) lists the various macros you can use to examine the status, the most interesting ones would be WIFEXITED
and WEXITSTATUS
.
的手册页wait()
(在第 2 节中,man 2 wait
在您的 Linux 系统上)列出了可用于检查状态的各种宏,最有趣的是WIFEXITED
和WEXITSTATUS
。
Alternatively, if you need to read foo's standard output, use popen(3)
, which returns a file pointer (FILE *
); interacting with the command's standard input/output is then the same as reading from or writing to a file.
或者,如果您需要读取 foo 的标准输出,请使用popen(3)
,它返回一个文件指针 ( FILE *
); 与命令的标准输入/输出交互与读取或写入文件相同。
回答by Fred Foo
In C
在 C
#include <stdlib.h>
system("./foo 1 2 3");
In C++
在 C++ 中
#include <cstdlib>
std::system("./foo 1 2 3");
Then open and read the file as usual.
然后像往常一样打开并读取文件。
回答by Johan
How about like this:
像这样怎么样:
char* cmd = "./foo 1 2 3";
system(cmd);
回答by Hazok
Here's the way to extend to variable args when you don't have the args hard coded (although they are still technically hard coded in this example, but should be easy to figure out how to extend...):
这是当您没有硬编码 args 时扩展到变量 args 的方法(尽管在本示例中它们仍然是技术硬编码,但应该很容易弄清楚如何扩展...):
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int argcount = 3;
const char* args[] = {"1", "2", "3"};
const char* binary_name = "mybinaryname";
char myoutput_array[5000];
sprintf(myoutput_array, "%s", binary_name);
for(int i = 0; i < argcount; ++i)
{
strcat(myoutput_array, " ");
strcat(myoutput_array, args[i]);
}
system(myoutput_array);
回答by Pedro Alves
You can use fork()
and system()
so that your program doesn't have to wait until system()
returns.
您可以使用fork()
andsystem()
以便您的程序不必等到system()
返回。
#include <stdio.h>
#include <stdlib.h>
int main(int argc,char* argv[]){
int status;
// By calling fork(), a child process will be created as a exact duplicate of the calling process.
// Search for fork() (maybe "man fork" on Linux) for more information.
if(fork() == 0){
// Child process will return 0 from fork()
printf("I'm the child process.\n");
status = system("my_app");
exit(0);
}else{
// Parent process will return a non-zero value from fork()
printf("I'm the parent.\n");
}
printf("This is my main program and it will continue running and doing anything i want to...\n");
return 0;
}
回答by Jonathan Ben-Avraham
The system
function invokes a shell to run the command. While this is convenient, it has well known security implications. If you can fully specify the path to the program or script that you want to execute, and you can afford losing the platform independence that system
provides, then you can use an execve
wrapper as illustrated in the exec_prog
function below to more securely execute your program.
该system
函数调用 shell 来运行命令。虽然这很方便,但它具有众所周知的安全隐患。如果您可以完全指定要执行的程序或脚本的路径,并且可以承受失去所system
提供的平台独立性,那么您可以使用如下函数所示的execve
包装器exec_prog
来更安全地执行您的程序。
Here's how you specify the arguments in the caller:
以下是在调用者中指定参数的方法:
const char *my_argv[64] = {"/foo/bar/baz" , "-foo" , "-bar" , NULL};
Then call the exec_prog
function like this:
然后exec_prog
像这样调用函数:
int rc = exec_prog(my_argv);
Here's the exec_prog
function:
这是exec_prog
函数:
static int exec_prog(const char **argv)
{
pid_t my_pid;
int status, timeout /* unused ifdef WAIT_FOR_COMPLETION */;
if (0 == (my_pid = fork())) {
if (-1 == execve(argv[0], (char **)argv , NULL)) {
perror("child process execve failed [%m]");
return -1;
}
}
#ifdef WAIT_FOR_COMPLETION
timeout = 1000;
while (0 == waitpid(my_pid , &status , WNOHANG)) {
if ( --timeout < 0 ) {
perror("timeout");
return -1;
}
sleep(1);
}
printf("%s WEXITSTATUS %d WIFEXITED %d [status %d]\n",
argv[0], WEXITSTATUS(status), WIFEXITED(status), status);
if (1 != WIFEXITED(status) || 0 != WEXITSTATUS(status)) {
perror("%s failed, halt system");
return -1;
}
#endif
return 0;
}
Remember the includes:
记住包括:
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <stdio.h>
See related SE postfor situations that require communication with the executed program via file descriptors such as stdin
and stdout
.
有关需要通过文件描述符(例如和 )与执行的程序进行通信的情况,请参阅相关的 SE 帖子。stdin
stdout
回答by Billy
system()
executes a shell which is then responsible for parsing the arguments and executing the desired program. To execute the program directly, use fork() and exec() (which is what system() uses to execute the shell as well as what the shell itself uses to execute commands).
system()
执行一个 shell,然后负责解析参数并执行所需的程序。要直接执行程序,请使用 fork() 和 exec()(这是 system() 用于执行 shell 以及 shell 本身用于执行命令的内容)。
#include <unistd.h>
int main() {
if (fork() == 0) {
/*
* fork() returns 0 to the child process
* and the child's PID to the parent.
*/
execl("/path/to/foo", "foo", "arg1", "arg2", "arg3", 0);
/*
* We woundn't still be here if execl() was successful,
* so a non-zero exit value is appropriate.
*/
return 1;
}
return 0;
}