乡下人产国偷v产偷v自拍,国产午夜片在线观看,婷婷成人亚洲综合国产麻豆,久久综合给合久久狠狠狠9

  • <output id="e9wm2"></output>
    <s id="e9wm2"><nobr id="e9wm2"><ins id="e9wm2"></ins></nobr></s>

    • 分享

      linux系統(tǒng)下,c 程序,調(diào)用system命令失敗,分析過程

       angelbrian 2013-02-01

      首先,該程序運行,需要很大的數(shù)據(jù),需要很大內(nèi)存。在測試小數(shù)據(jù)的時候,程序沒有任何問題,在運行測試大數(shù)據(jù)的時候,出現(xiàn)問題。個人認為程序本身編程代碼應該沒有問題。

      通過程序錯誤定位,定位到了system命令。system命令調(diào)用,程序根本沒有反應。完全將system命令忽略。

       

      =========================

       

      每個命令都有返回值,重新試過,發(fā)現(xiàn)調(diào)用system命令的返回值都是-1.

        cerr<<"before pdflatex"<<endl;
          sprintf( cmd, "%s %s", "pdflatex -output-directory=/home/user/evaluation", outfilename );
         cerr<<"pdflatex : "<<outfilename<<endl;
          system_cmd = system( cmd );
          cerr<<"system_cmd : "<<system_cmd<<endl;
          system_cmd = system( cmd );
          cerr<<"system_cmd : "<<system_cmd<<endl;

       

      =========================

       

      研究system命令。為何返回-1?

      system()會調(diào)用fork()產(chǎn)生子進程,由子進程來調(diào)用/bin/sh-c string來執(zhí)行參數(shù)string字符串所代表的命令,此命>令執(zhí)行完后隨即返回原調(diào)用的進程。在調(diào)用system()期間SIGCHLD 信號會被暫時擱置,SIGINT和SIGQUIT 信號則會被忽略。

      返回值:

      如果fork()失敗 返回-1:出現(xiàn)錯誤

      如果exec()失敗,表示不能執(zhí)行Shell,返回值相當于Shell執(zhí)行了exit(127)

      如果執(zhí)行成功則返回子Shell的終止狀態(tài)

      如果system()在調(diào)用/bin/sh時失敗則返回127,其他失敗原因返回-1。若參數(shù)string為空指針(NULL),則返回非零值>。如果system()調(diào)用成功則最后會返回執(zhí)行shell命令后的返回值,但是此返回值也有可能為 system()調(diào)用/bin/sh失敗所返回的127,因此最好能再檢查errno 來確認執(zhí)行成功。

       

      =====================================

       

      那么,將錯誤定位為fork()失敗。

      下面是fork():

      fork調(diào)用的一個奇妙之處就是它僅僅被調(diào)用一次,卻能夠返回兩次,它可能有三種不同的返回值:

      在父進程中,fork返回新創(chuàng)建子進程的進程ID;

      在子進程中,fork返回0;

      如果出現(xiàn)錯誤,fork返回一個負值;

      fork出錯可能有兩種原因:

      (1)當前的進程數(shù)已經(jīng)達到了系統(tǒng)規(guī)定的上限,這時errno的值被設置為EAGAIN。

      (2)系統(tǒng)內(nèi)存不足,這時errno的值被設置為ENOMEM。(關于errno的意義,請參考本系列的第一篇文章。)

      fork系統(tǒng)調(diào)用出錯的可能性很小,而且如果出錯,一般都為第一種錯誤。如果出現(xiàn)第二種錯誤,說明系統(tǒng)已經(jīng)沒有可分配的內(nèi)存,正處于崩潰的邊緣,這種情況對Linux來說是很罕見的。

       

      ============================

       

      下面想到的就是查看errno的內(nèi)容。

      linux中的C api函數(shù)發(fā)生異常時,一般會將errno變量(需include errno.h)賦一個整數(shù)值,不同的值表示不同的含義,可以通過查看該值推測出錯的原因,在實際編程中用這一招解決了不少原本看來莫名其妙的問題。但是 errno是一個數(shù)字,代表的具體含義還要到errno.h中去閱讀宏定義,而每次查閱是一件很繁瑣的事情。有下面幾種方法可以方便的得到錯誤信息
       (1)void perror(const char *s)
      函數(shù)說明
      perror ( )用來將上一個函數(shù)發(fā)生錯誤的原因輸出到標準錯誤(stderr),參數(shù)s 所指的字符串會先打印出,后面再加上錯誤原因字符串。此錯誤原因依照全局變量 errno 的值來決定要輸出的字符串。
       (2) char *strerror(int errno)
      將錯誤代碼轉換為字符串錯誤信息,可以將該字符串和其它的信息組合輸出到用戶界面例如
      fprintf(stderr,"error in CreateProcess %s, Process ID %d ",strerror(errno),processID)
      注:假設processID是一個已經(jīng)獲取了的整形ID
       (3)printf("%m", errno);
      另外不是所有的地方發(fā)生錯誤的時候都可以通過error獲取錯誤代碼,例如下面的代碼段

      #include"stdio.h"
      #include "stdlib.h"
      #include "errno.h"
      #include "netdb.h"
      #include "sys/types.h"
      #include "netinet/in.h"
      int main (int argc, char *argv[])
      {
      struct hostent *h;
      if (argc != 2)
      {
      fprintf (stderr ,"usage: getip address\n");
      exit(1);
      }

      if((h=gethostbyname(argv[1])) == NULL)
      {

      herror(“gethostbyname”);
      exit(1);
      }

      printf(“Host name : %s\n”, h->h_name);
      printf(“IP Address : %s\n”, inet_ntoa (*((struct in_addr *)h->h_addr)));
      return 0;
      }


       通過上面的代碼可以看到:使用gethostbyname()函數(shù),你不能使用perror()來輸出錯誤信息(因為錯誤代碼存儲在 h_errno 中而不是errno 中。所以,你需要調(diào)用herror()函數(shù)。
      你 簡單的傳給gethostbyname() 一個機器名(“bbs.tsinghua.edu.cn”),然后就從返回的結構struct hostent 中得到了IP 等其他信息.程序中輸出IP 地址的程序需要解釋一下:h->h_addr 是一個char*,但是inet_ntoa()函數(shù)需要傳遞的是一個struct in_addr 結構。所以上面將h->h_addr 強制轉換為struct in_addr*,然后通過它得到了所有數(shù)據(jù)。

        本站是提供個人知識管理的網(wǎng)絡存儲空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點。請注意甄別內(nèi)容中的聯(lián)系方式、誘導購買等信息,謹防詐騙。如發(fā)現(xiàn)有害或侵權內(nèi)容,請點擊一鍵舉報。
        轉藏 分享 獻花(0

        0條評論

        發(fā)表

        請遵守用戶 評論公約

        類似文章 更多