我试图使用系统系统调用在c程序中执行Linux命令,但不希望它在终端上转储输出或错误日志.我该怎么办?有没有其他方法可以做到这一点?
nos*_*nos 26
由于system()调用使用shell来执行命令,因此可以将stdout和stderr重定向到/ dev/null,例如
system("ls -lh >/dev/null 2>&1");
Run Code Online (Sandbox Code Playgroud)
小智 15
popen是另一种可以做同样事情的方式:
void get_popen()
FILE *pf;
char command[20];
char data[512];
// Execute a process listing
sprintf(command, "ps aux wwwf");
// Setup our pipe for reading and execute our command.
pf = popen(command,"r");
// Error handling
// Get the data from the process execution
fgets(data, 512 , pf);
// the data is now in 'data'
if (pclose(pf) != 0)
fprintf(stderr," Error: Failed to close command stream \n");
return;
}
Run Code Online (Sandbox Code Playgroud)
和system()调用popen()启动一个 shell 并将参数传递给它,这会产生安全漏洞。除非根据 shell 的引用和转义规则正确清理源自用户输入的参数的所有部分,否则攻击者很可能在系统上运行任意命令。
相反,请使用exec命令系列。它们直接启动命令,而不启动 shell。您可能仍然需要清理输入,但只是为了限制可以传递给命令本身的内容。
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <errno.h>
#include <stdlib.h>
void func(char *input) {
pid_t pid;
int status;
pid_t ret;
char *const args[3] = {"any_exe", input, NULL};
char **env;
extern char **environ;
/* ... Sanitize arguments ... */
pid = fork();
if (pid == -1) {
/* Handle error */
} else if (pid != 0) {
while ((ret = waitpid(pid, &status, 0)) == -1) {
if (errno != EINTR) {
/* Handle error */
break;
}
}
if ((ret == 0) ||
!(WIFEXITED(status) && !WEXITSTATUS(status))) {
/* Report unexpected child status */
}
} else {
/* ... Initialize env as a sanitized copy of environ ... */
if (execve("/usr/bin/any_cmd", args, env) == -1) {
/* Handle error */
_Exit(127);
}
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
61130 次 |
| 最近记录: |