0

我试图了解 execl 在尝试启动不存在的文件时返回的错误。

这是我的这个实验的代码,其中 main 调用函数 spawn1 将创建 fork 并尝试启动 execl:

# include <stdio.h>
# include <assert.h>
# include <sys/types.h>
# include <sys/wait.h>
# include <unistd.h>
# include <stdlib.h>

int spawn1(char *, char *, char *);

int main(){
  int i, t, tt, state;

  for(i = 0; i < 10; i++){
    t = spawn1("functiondoesntexist", "strange name", "argument");
    if (t < 0){
      perror("fork"); // fork error
      break;
    }
    tt = wait(&state);
    assert(tt == t);
    if (state != 0){
      perror("exec didn't work");
      break;
    }
  }
  return i != 10;
}

int spawn1(char * file, char * command, char * arg){
  int t;

  t = fork();
  if (t < 0)                    // fork error
    return -1;

  if (t == 0){                  // child
    execl(file, command, arg, (void *)0);
    exit(1); 

  }
                                // parent
  return t;
}

返回的错误是:

exec didn't work: File exists

为什么不是更像“文件不存在”?

4

1 回答 1

4

你没有perror在正确的地方打电话。

当某个函数失败时,需要在失败的函数后立即errno检查或调用。在失败之后调用的任何其他系统或库函数都将被其自己的错误代码覆盖。perror errno

更改您的代码以立即调用perror,如下所示:

int main(){
  int i, t, tt, state;

  for(i = 0; i < 10; i++){
    t = spawn1("functiondoesntexist", "strange name", "argument");
    if (t < 0){
      fprintf(stderr, "fork failed\n");   // not perror
      break;
    }
    tt = wait(&state);
    assert(tt == t);
    if (state != 0){
      fprintf(stderr, "exec didn't work\n");    // not perror
      break;
    }
  }
  return i != 10;
}

int spawn1(char * file, char * command, char * arg){
  int t;

  t = fork();
  if (t < 0) {                   // fork error
    perror("fork failed");      // call perror here to check fork
    return -1;
  }

  if (t == 0){                  // child
    execl(file, command, arg, (void *)0);
    perror("exec failed");      // call perror here to check execl
    exit(1); 

  }
                                // parent
  return t;
}
于 2017-11-24T03:15:06.437 回答