我有点问题。当我在main中返回零时,我的程序会抛出分段错误。
主要功能如下:
int main(int argc, char* argv[]){
ifstream fs("test.dat", ios::binary);
cSendStream sendstr(&fs,20);
char *zomg=sendstr.data();
//zomg[20]=0;
sendstr.read(20);
cout<<"Buffer: "<<sendstr.data()<<endl;
cout<<"Remaining: "<<sendstr.dataAvailable()<<endl;
sendstr.read(2);
cout<<"Buffer: "<<zomg<<endl;
cout<<"Remaining: "<<sendstr.dataAvailable()<<endl;
sendstr.read(10);
cout<<"Buffer: "<<zomg<<endl;
cout<<"Remaining: "<<sendstr.dataAvailable()<<endl;
cout<<"end..."<<endl;
return 0;
}
评论zomg
部分是使程序崩溃的重点。 zomg
指向char[20]
。我在这一行的观点是设置数组的结束,因为如果我不这样做,流读取的数据超过20个字节,但它只打印一个不必要的符号。
有趣的是,即使我在此处写了一些额外的代码并返回0,它在返回时会先抛出错误。
仅针对您想要查看cSendStream类的情况:
cSendStream.h:
class cSendStream{
public:
cSendStream(std::istream*, int streamsize);
int read(int);
int dataAvailable();
char* data();
private:
void shift(int);
std::istream *source;
int streamsize;
char* buffer;
};
和cSendStream.cpp:
#include "cSendStream.h"
cSendStream::cSendStream(std::istream *src, int size){
source=src;
streamsize=size;
buffer=new char[streamsize];
memset(buffer,0,streamsize);
}
int cSendStream::read(int i){
if(dataAvailable()<1 || i<=0){
return 0;
}
if(i>dataAvailable()){
i=dataAvailable()-1;
}
if(i>streamsize){
i=streamsize;
}
shift(i);
source->read(&(buffer[streamsize-i]),i);
return i;
}
int cSendStream::dataAvailable(){
int current=source->tellg();
source->seekg (0, std::ios::end);
int available = (int)(source->tellg())-current;
source->seekg (current);
return available;
}
char* cSendStream::data(){
return buffer;
}
void cSendStream::shift(int i){
char tmp[2048];
memcpy(tmp,buffer,streamsize);
memcpy(&(buffer[0]),&(tmp[i]),streamsize-i);
}
答案 0 :(得分:6)
zomg [20] = 0正在写一个超出分配数组的末尾,但很难猜出为什么会发生段错误。我的猜测是你聪明的编译器正在使用alloca进行分配,而你正在给返回地址涂鸦。
查看程序集(通常是-S)以查看正在发生的事情可能会很有趣。
答案 1 :(得分:5)
您正在分配一个char[20]
数组,其有效索引为0-19,但您正在尝试访问索引20.这会导致段错误。
答案 2 :(得分:1)
所以这里的这个位分配了大小为20的缓冲区:
new char[streamsize]
但是你正试图找到第21个角色:
buf[20]
你有段错误。数组基于零,因此对于大小为20的数组,索引从0到19。
答案 3 :(得分:1)
要扩展int3的答案,如果您的数据长度为20个字符,则需要声明一个长度为21个字符的数组,以便您可以使用空终止字符“完成”。如果您这样做,那么您的代码将起作用,因为zomg[20]
将是数组中的有效条目。