首页 > 解决方案 > execvp在C中跳过某些代码

问题描述

这个程序做了两件事:1)复制shell的动作2)记录用户输入到一个tmp.log文件

这里的问题是在我的子进程中, printf("ABC"); 什么也没做。输出日志文件工作正常,但它只是不打印。

为什么会这样?

我知道 execvp 应该替换当前进程,但这并不能解释为什么它会执行输出而不是打印。我看到了下面的链接,但这并没有回答我的问题。 exevp 跳过所有代码,直到在 c 中等待调用

#include <time.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>
#include <string.h>
#include <stdlib.h>
#include  <sys/types.h>
#include <wordexp.h>

void execute(char *user_input)
{
    pid_t pid;        
    int state_loc; 
    if( (pid = fork()) == -1){
      printf("fork failed\n");
      exit(1);
    }
    else if(pid == 0){

      FILE *f;
      //open the file and append. Create if not there.
      f = fopen("tmp.log", "a+"); 
      if (f == NULL) { printf("Something is wrong");}

      struct tm *p;
      struct tm buf;
      char timestring[100];
      time_t ltime = time(NULL);
      if (NULL != (p=localtime_r(&ltime, &buf))){
        strftime(timestring, sizeof(timestring),"** %c: ", p);
        fprintf(f, "%s %s \n", timestring, user_input);
      }
      fclose(f);      

      char* separator = " ";
      char* argv[64];
      int argc = 0;
      char* tmp;
      argv[argc] = strtok_r(user_input, separator, &tmp);
      while( argv[argc] != NULL){
        argc+=1;
        argv[argc] = strtok_r(NULL, separator, &tmp);
      }

      printf("ABC"); //why doesn't this print??

      execvp(argv[0],argv);
    }
    else{          
      wait(&state_loc);
    }
}


int main ()
{
  while(1)
  {
    char user_input[1024];
    printf("recsh>> ");
    //empty the buffer right scanf
    scanf("%[^\n]", user_input);
    //calls each character in the user input, repeat until it reaches the terminating \n
    while( getchar() != '\n'); 
    if(strcmp(user_input, "exit") == 0){
      printf("Exiting\n");
      break;
    }
    else{
      execute(user_input);
    }
  }
  return 0;
}

标签: cshellexec

解决方案


该调用printf在子进程调用之前在子进程中执行execvp

由于默认情况下stdout行缓冲的,并且打印的文本不构成一行(因为没有换行符),所以它留在输出缓冲区中。当图像被替换时,该输出缓冲区与原始可执行文件的其余部分一起消失execvp

道德:始终以换行符 ( \n) 终止您的输出。


推荐阅读