fgetsについて
こんにちは。こちらのカテゴリには初めての投稿です。よろしくお願いします。
C++を用いて、Fedora上で"tcp dump"コマンドを実行し、1秒ごとのeth0(NIC)を通過したackパケットを記録するプログラムを作成しています。(150秒分記録)
ソースコードは質問文最後に記載します。
質問は、下記のプログラムでtcpdumpから1行分実行結果を取り出す際に使用しているfgets関数についてです。
調べてみると、fgtes関数は失敗した際は、NULLを返し「停止」するとあります。
http://www.nxmnpg.com/ja/3/fgets
これがおそらく原因かと思いますが、何も通信が行われていない状況で実行すると、
temp = fgets(buf,150,pp);
の行でプログラムが止まってしまいます。(何かしら通信がある(パケットが通る)と再開します)
よって、正確な時間計測ができず、困っています。
私はC++を勉強したてで、あまり読みやすいプログラムではないと思います。申し訳ありません。
fgetsの代わりになるような関数、または方法はありませんでしょうか。
ご回答、よろしくお願い致します。
//num_ack[]に各秒におけるパケット数を記録します。
//教えてgooの仕様上、tabや半角スペースが使えないので行頭のスペースはすべて全角です。ご了承ください。
#include <iostream>
#include <stdlib.h>
#include <time.h>
#include <string.h>
using namespace std;
#define N 150
int main()
{
time_t start,end;
int num_ack[N];
int i=0;
char buf[150];
char *src,*temp,*srcstr;
char cmp[150];
srcstr = "ack"; //検索ワード:"ack"
FILE *pp;
pp = popen("tcpdump -i eth0","r");
//popen失敗検知
if(pp == NULL)
{
cout << "tcpdump failed" << endl;
exit(EXIT_FAILURE);
}
for(int k=0;k<N;k++) //num_ackを初期化
{
num_ack[k] = 0;
}
while(1)
{
start = time(NULL);
end = time(NULL);
while((int)(end - start) <1) //1秒間計測
{
temp = fgets(buf,150,pp); //tcpdumpから1行(1パケット分)をbufへ取得
src = strstr(buf,srcstr); //bufから、"ack"を検索
if(src != NULL && strcmp(buf,cmp) !=0) //検索結果がNULLでなく、前回から変更がある場合
{
num_ack[i] += 1;
strcpy(cmp,buf);
}
end = time(NULL);
}
j += 1;
}
pclose(pp);
return num_ack;
}
お礼
解決しました。ありがとうございました。 結果は私のおばかでした。 入力ファイルをOPENしFGETSで1行入力した後 テンポラリファイルに出力し 再度テンポラリファイルをFGETSで一行入力してたの ですがこのテンポラリファイル入力時消えていたと思ったのです。 そうではなくテンポラリファイル出力時FPRINTFで出力していたのでここで消えていました。 お騒がせいたしました。
補足
早速のご教授ありがとうございます。 やっぱり消えませんよね・・・ でも不思議なのですがfgetsの行でブレークしてエリアを確認すると%がないんですよ。 ちなみにソースは以下のような感じで書いてます。 プリンタに出力するプログラムです。 fgets(S1_inbuf,259,S1_infp); TextOut(S1_hdc,S1_x,S1_y,S1_inbuf,lstrlen(S1_inbuf));