Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/146.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 与系统命令相比,execve如何防止漏洞_C++_Linux_Security - Fatal编程技术网

C++ 与系统命令相比,execve如何防止漏洞

C++ 与系统命令相比,execve如何防止漏洞,c++,linux,security,C++,Linux,Security,我指的是链接, 基本上考虑输入快乐;useradd“攻击者”,安全建议区分兼容代码和不兼容代码- 非投诉代码 #include <string.h> #include <stdlib.h> enum { BUFFERSIZE = 512 }; void func(const char *input) { char cmdbuf[BUFFERSIZE]; int len_wanted = snprintf(cmdbuf, BUFFERSIZE,

我指的是链接,
基本上考虑输入<代码>快乐;useradd“攻击者”,安全建议区分兼容代码和不兼容代码-

非投诉代码

#include <string.h>
#include <stdlib.h>
 
enum { BUFFERSIZE = 512 };
 
void func(const char *input) {
  char cmdbuf[BUFFERSIZE];
  int len_wanted = snprintf(cmdbuf, BUFFERSIZE,
                            "any_cmd '%s'", input);
  if (len_wanted >= BUFFERSIZE) {
    /* Handle error */
  } else if (len_wanted < 0) {
    /* Handle error */
  } else if (system(cmdbuf) == -1) {
    /* Handle error */
  }
}
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.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 != -1) &&
      (!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);
    }
  }
}
#包括
#包括
枚举{BUFFERSIZE=512};
void func(常量字符*输入){
char cmdbuf[BUFFERSIZE];
int len_wanted=snprintf(cmdbuf,BUFFERSIZE,
“任意命令“%s”,输入);
如果(len_wanted>=缓冲区大小){
/*处理错误*/
}如果需要,则为else(len_<0){
/*处理错误*/
}否则如果(系统(cmdbuf)=-1){
/*处理错误*/
}
}
兼容代码

#include <string.h>
#include <stdlib.h>
 
enum { BUFFERSIZE = 512 };
 
void func(const char *input) {
  char cmdbuf[BUFFERSIZE];
  int len_wanted = snprintf(cmdbuf, BUFFERSIZE,
                            "any_cmd '%s'", input);
  if (len_wanted >= BUFFERSIZE) {
    /* Handle error */
  } else if (len_wanted < 0) {
    /* Handle error */
  } else if (system(cmdbuf) == -1) {
    /* Handle error */
  }
}
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.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 != -1) &&
      (!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);
    }
  }
}
#包括
#包括
#包括
void func(字符*输入){
pid_t pid;
智力状态;
pid_t ret;
char*const args[3]={“any_exe”,输入,NULL};
字符**env;
外部字符**环境;
/*…清理参数*/
pid=fork();
如果(pid==-1){
/*处理错误*/
}否则如果(pid!=0){
while((ret=waitpid(pid,&status,0))=-1){
如果(错误号!=EINTR){
/*处理错误*/
打破
}
}
如果((ret!=-1)&&
(!WIFEXITED(status)| |!WEXITSTATUS(status))){
/*报告意外的子级状态*/
}
}否则{
/*…将环境初始化为环境的已消毒副本*/
如果(execve(“/usr/bin/any_cmd”,args,env)=-1){
/*处理错误*/
_出口(127);
}
}
}
假设我们以相同的权限将相同的输入传递给两个函数,即由root等运行,第二个解决方案如何确保命令注入攻击被击退


我唯一的猜测是,
execve
将使用
any_cmd
刷新二进制图像,并使用input
happy';useradd'attacker
作为参数添加到
any\u cmd
。因此,我们将有一个相当于“无效参数”的返回值。我的理解正确吗?还是有比我的理解更深刻的东西我还缺少?

主要的区别确实是,通过
系统
功能,你可以启动你的shell可以执行的任何东西,因此你基本上可以通过多个命令进行shell注入。而使用
execve
时,首先指定要执行的特定二进制文件,因此可以非常确定只执行一个命令(除非使用
execve
shell..)。另外,由于您提供了
execve
的完整路径,因此可以避免基于修改
主目录或当前工作目录的黑客攻击


因此,是的,您的理解是相当正确的

您发现
execve
system
各自手册的哪一部分不清楚?我试图理解与系统相比,相同的输入如何不会在execve中造成问题。