【问题标题】:Is there an alternative to the 'system()' command in C++.?C++ 中的“system()”命令是否有替代方法?
【发布时间】:2021-01-30 06:29:54
【问题描述】:

我读过很多回答说system() 命令不好。首先,为什么它这么糟糕?其次,是否有不产生这种安全漏洞的替代方案?我主要想知道是否有办法在 C++ 中清除屏幕。在 python 中,我有一个明确的函数来检查操作系统名称并运行system('cls')system('clear')。这也是一个安全漏洞吗?如果是这样,是否有 python 替代品?

【问题讨论】:

标签: c++ windows operating-system system


【解决方案1】:

system 函数(跨多种语言,包括 Python 和 C++)本质上并不“坏”,但它们很难正确使用。

安全

您需要绝对确保通过system 执行的任何操作都是安全的。

如果您写system("echo hello " + name),那么您需要绝对确定name 不能被恶意用户控制。 name = "; rm -rf /" 会导致 echo hello ; rm -rf /,所以如果它来自用户,通过网络表单或数据库之类的东西,那么你需要非常小心,我会推荐一个比 system 更复杂的解决方案.

system("clear") 这样的电话对您来说是安全的。

可用性

系统调用为您提供了几个输出(我将举一个调用bash shell 的示例):

  • 状态码(shell 是否指示错误情况)
  • STDOUT 的内容
  • STDERR 的内容

system 返回状态码。对于ls这样的命令,你有兴趣接收STDOUT,你也可以查看状态码。这对system 来说很笨拙。

Python subprocess 模块被社区普遍接受为管理这些问题的更简单方法。

如何管理控制台

如果您尝试管理控制台显示,您可能会对像 ncurses 这样具有广泛操作系统支持的库感兴趣。

添加ncurses 作为依赖项可能会很麻烦,如果清除屏幕是您唯一需要做的事情。如果是这种情况,那么我认为像您正在做的那样使用 system() 没有任何问题。

【讨论】:

  • 当我使用system("cls"); 命令时,命令提示符变得疯狂,并且只是逐行打印并且不会停止。这是有原因的吗?
  • 实际上,只有当我使用 Path 变量时。如果我在工作区,它工作得很好。这是有原因的吗?
  • @RedSox2,就运行system("cls") 而言,“当我为 ti 使用 Path 变量时”应该是什么意思?哪个工作区运行良好?
  • @ajm "如果你写system("echo hello " + name)" 请注意,这不可能直接,假设name是键入char*。该命令需要使用std::stringstrcat() 构造。
  • 在 Windows 中,您的 Path 变量可以让您更快地运行 .exe 文件(例如,您必须将 min-GW bin 的路径放在路径变量中才能正常工作)。因此,如果我要运行的文件是 foo.exe,我可以输入%foo%,而不是每次运行命令提示符时导航到文件夹。
【解决方案2】:

首先,为什么会这么糟糕?

因为您在代码中引入了对操作系统的依赖关系,并使其不可移植。

其次,有没有不会产生这种安全漏洞的替代方法?

不,现有的替代方案(POSIX 兼容)fork()execxx()pipe() 存在引入操作系统依赖项和安全漏洞的相同问题。

这也是一个安全漏洞吗?

主要的安全漏洞是通过由参数构造的命令引入的,例如

void exec_ls(const std::string param) {
    std::string cmd;
    cmd = "ls -l " + param;
    system(cmd.c_str());

如果有人设法通过param 注入一些额外的命令,例如

 std::string param = "dir ; rm -rf /*";
                       // ^^^^^^^^^^^
 exec_ls(param);

他们可以调用各种恶意命令。 另一个安全漏洞来自这一点,有人可能会用一些恶意代码替换您系统上的clsclear 命令。
克服这个问题的唯一方法是以某种方式保护您的系统,这是不可能的。

如果是这样,是否有 python 替代品?

使用不同的编程语言作为中间调用者并不能解决我上面提到的问题。

【讨论】:

  • system 的安全漏洞在于它通过 shell 运行命令,这是一种 脚本语言。如果您只是让用户运行任意命令,那很好。不管结果如何;这是他们的错。但是,如果您允许用户为模板命令提供参数,那么如果您选择通过system 运行命令,则完全是您的错。那将是重大过失。
  • @ErykSun 添加了一个比其他答案更现实的例子。
猜你喜欢
  • 2010-09-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-10-09
  • 2011-04-21
  • 2011-05-02
  • 1970-01-01
相关资源
最近更新 更多