2017-02-13 116 views
1

我必須寫一個程序,將使用execvp當用戶輸入某個命令啓動一個名爲demo.cpp新的程序。用戶將在格式輸入輸入execvp無法運行新程序

BG演示字INT1 INT2(忽略字BG的詞相關性,我把它存儲在一個字符串名爲命令在我的代碼)。

這是代碼:

int main(){ 

char *argv[5]; 
argv[0] = new char[10]; 
argv[1] = new char[10]; 
argv[2] = new char[10]; 
argv[3] = new char[10]; 
argv[4] = nullptr; 


string command; 
pid_t PID; 

cin>>command; //store the string 'bg' 

cin>>argv[0]>>argv[1]>>argv[2]>>argv[3]; 

PID = fork(); 

if(PID<0){ 
    perror("Fork failed!"); 
} 

else if(PID==0){ 

    if(execvp("./demo.cpp",argv)<0) 
      printf("Failed"); 
    } 

wait(0); 

return 0; 
} 

每次代碼打印 「失敗」。我唯一能想到的是,也許在傳遞給execvp的參數格式上有錯誤。此代碼和demo.cpp存儲在同一個文件夾中。

+2

什麼是' 。/ demo.cpp'?它是一個C++源文件嗎?你不能執行一個C++源文件。 – mch

+0

搜索上如此相似的問題,檢查這個問題,例如 http://stackoverflow.com/questions/14301407/how-does-execvp-run-a-command – Laza

+0

@mch:我是愚蠢的!當然,你不能執行C++源文件。 –

回答

2

你有兩個問題:一是execvp需要提供的參數列表爲空值終止。您需要

char *argv[5]; // Not 4. 

    ... // input as before 

    argv[4] = nullptr; 

順便說一句,我個人將其更改爲:

std::array<std::string,4> arguments; 
    std::cin>>arguments[0]>>arguments[1]>>arguments[2]>>arguments[3]; 
    char *argv[5]; 
    for (size_t i = 0; i<4; i++) { 
     argv[i] = const_cast<char*>(arguments[i].c_str()); 
    } 
    argv[4] = nullptr; 

關鍵是要做到投入std::string,然後拿到字符指針之後。這樣可以避免任何緩衝區溢出的風險。 (另一方面,const_cast不是很好 - 但我很確定它實際上是安全的。)

其次,您不能通過exec* C++源文件的名稱!你必須生成可執行文件(可能調用它demo),然後exec的是:(你還需要確保當前目錄是包含可執行文件的目錄)

if(execvp("./demo",argv)<0) 

+0

我嘗試了第一個建議,但仍然失敗,儘管我已經編輯了問題中的代碼以合併您的建議 – Sim

+0

您是對的,錯誤是我傳遞了源文件!爲什麼沒有教程提到這個細節! – Sim