为什么`execvp`采用`char * const argv []`?

时间:2013-10-21 16:01:28

标签: c exec api

我想知道两个执行函数之间是否存在const之间存在差异的原因,如果这只是单Unix规范中的错误:

摘自Linux手册页(似乎与Single Unix Specification一致),这里有exec的两个版本:

int execlp(const char *file, const char *arg, ...);
int execvp(const char *
file, char *const argv[]);

execlp将其参数视为const char *,并且它需要两个或更多个参数。 C中的const是一个承诺,该函数不会更改指向数据,在这种情况下是构成字符串的实际字符(char)。

execvp将其参数作为指针数组。但是,正如您所期望的那样,const char *关键字不是指向const的指针数组,而是位于不同的位置 - 这对C来说非常重要。execvp说的是可能会修改字符串中的字符,但它承诺不会修改数组 - 即指向字符串的指针。换句话说,

int fake_execvp(const char *file, char *const argv[]) {
    argv[0] = "some other string"; /* this is an error */
    argv[0][0] = 'f';              /* change first letter to 'f': this is perfectly OK! */
    /* ⋮ */
}

特别是,这使得使用C ++的std::string to_cstr()方法调用execvp很困难(技术上是禁止的),该方法返回const char *

似乎execvp真的应该采用const char *const argv[],换句话说,它应该保证不会做上述任何一种变化。

1 个答案:

答案 0 :(得分:9)

引用您链接的页面:

  

包含argv[]envp[]为常量的声明   明确这些语言绑定的未来作者   对象完全不变。由于ISO C的限制   标准,不可能在标准C中陈述这个想法。   指定const的两个级别 - argv[]envp[]的资格   exec函数的const参数似乎很自然   选择,假设这些函数不修改数组   指针或函数指向的字符,但是这个   将禁止现有的正确代码。

基本上,execlpexecvp上的{{1}}资格完全兼容,因为它们对相应的参数指定了相同的限制。