有关fstream::read()读取错误问题

来源:互联网 发布:淘宝客优惠券推广 编辑:程序博客网 时间:2024/06/05 18:34

  在C++中,读取文件经常会用ifstream类进行数据的读取。我在最近编写有关解析pcap文件代码的时候,便是使用了ifstream类进行读取,也碰到了一些小问题。

  在以前的学习使用中,一般对ifstream的文件读取操作一般不会超过1K,所以并没有碰到这种问题,但是这次面对超过190k的pcap文件,我在使用read读取的时候,还没到1k就被判定为文件读取结束而提前结束程序,而我调试了很久依旧没找到问题。

  以下是发生错误的一段代码:

  

while(!File.eof()){    len = getlen(File);//获取包长度    getIP_port(File,len);//获取使用TCP协议中                                      的四元祖}

  getlen跟getIP_port当中都会对File进行read操作,并进行相应的处理,逐步分析pcap中的每一个包。但是这段程序在分析到第12个 包之后,就判定文件结束,进而结束了循环。而我通过ifstream::seekg()跟ifstream::tellg()操作确定文件长度方面并没有任何问题。所以我做出了以下假设:

  1、文件本身发生错误,导致程序判定文件结束

  2、在getIP_port进行包解析时,缺乏完备性,导致误操作将文件读取完毕

  3、文件打开方式错误


  针对第一种可能性,我重新抓取了三个包,并依此进行试验,发现都会发生类似问题:它们分别在第7个、10个、13个包中停止分析,并同样得出文件结束的结论,虽然包的个数没有规律可循,但是通过字节数的分析,我发现4个包都在分析到1000出头的字节时发生错误结束。


  对于第二种可能性,我经过不断的调试与数据追踪,确认了数据的准确性,并且判定,是read()函数在超过一定字节后发生了不知名错误导致不再读取数据。


  对于第三种情况,首先介绍一下fstream类中打开文件的open函数

  

void open (const char* filename,           ios_base::openmode mode = ios_base::in | ios_base::out);void open (const string& filename,           ios_base::openmode mode = ios_base::in | ios_base::out);


  第一个参数为文件路径,第二 个参数为文件打开方式,第三个参数为文件类型,具体相关取值请自行查看


  我之前在打开文件时,都是采用  File.open(Path); 的方式进行操作,对第二第三个参数选取了默认值。这里不得不说一下一个较为坑的事情,当时我首先是在百度文库中找到一个相关open函数的介绍与使用方法,在该文档中,文件的第二参数默认值为 ios::binary|ios::in  ,意思为以二进制方式,并从文件到内存的读取方式,但是事实上, 从以上函数声明可以看出,open函数第二参数默认值仅仅为 ios::in 并没有所谓的 ios::binary!!

  在发现这个错误之后,我立马对第二参数增加了binary值,以二进制方式进行读取,果然,这回成功了……


  这次总结只是对自己学习过程当中问题的一个记录,文笔不好,内容可能太简单,请大家见谅……

  在此次解析中,仍然还有一个问题困扰着我,就是在没有ios::binary值时,四个文件的读取字节数都在1000到1100范围以内,我不知道这是不是巧合,但是的确没有找到任何相关资料跟信息,也没有找到文件不以二进制读取时会误操作退出的原因,若有大神了解,请麻烦告知一下~~

0 0