读写文件之句柄泄露隐患
编程时,我们往往会遇到打开文件忘了关,导致程序存在安全隐患等问题。
比如:
//读取frontPrvFile文件
QFile originFrontPrvFile(frontPrvFile);
if(!originFrontPrvFile.open(QIODevice::ReadOnly|QIODevice::Text))
{
qDebug()<<"open origin frontPrvFile:"<<frontPrvFile<<"failed!";
return false;
}
QTextStream originFrontPrvFileStream(&originFrontPrvFile);
originFrontPrvFileStream.setCodec("UTF-8");
originFrontPrvFileStream.setAutoDetectUnicode(true);
//新建frontPagePrvFile文件
QFile newFrontPrvFile(frontPagePrvFile);
if(!newFrontPrvFile.open(QIODevice::WriteOnly | QIODevice::Text))
{
qDebug()<<"open new frontPrvFile:"<<frontPagePrvFile<<"failed!";
return false;
}
QTextStream newFrontPagePrvFileStream(&newFrontPrvFile);
newFrontPagePrvFileStream.setCodec("UTF-8");
newFrontPagePrvFileStream.setAutoDetectUnicode(true);
//通过读取frontPrvFile的prn序号,来构造正面Prv文件frontPagePrvFile
int nWritePrnNum=0;//记录frontPagePrvFile中写入的prn个数
while(!originFrontPrvFileStream.atEnd())
{
//每读取原始prv文件的一行,就在frontPagePrvFile文件中写入同样的pageCopy行
QString prnFileName = originFrontPrvFileStream.readLine();
if(prnFileName == PRVEND_FLAG)
{
break;
}
//在frontPagePrvFile中写pageCopy行prnFileName
for(int i = 0; i < pageCopy; i++)
{
newFrontPagePrvFileStream<<prnFileName<<"\n";
nWritePrnNum++;
}
}
newFrontPagePrvFileStream<<PRVEND_FLAG<<"\n";//追加结束标志符
newFrontPagePrvFileStream<<nWritePrnNum;//追加PRN文件个数
newFrontPrvFile.close();
originFrontPrvFile.close();
上述代码中需要操作两个句柄,进行两个文件的读写。
其中:
QFile newFrontPrvFile(frontPagePrvFile);
if(!newFrontPrvFile.open(QIODevice::WriteOnly | QIODevice::Text))
{
qDebug()<<"open new frontPrvFile:"<<frontPagePrvFile<<"failed!";
return false;
}
第二个文件打开失败的话,函数立即结束,但第一个文件没有关闭,这样的代码就存在着安全隐患。因此,我们需要将上述代码修改为:
//读取frontPrvFile文件
QFile originFrontPrvFile(frontPrvFile);
if(!originFrontPrvFile.open(QIODevice::ReadOnly|QIODevice::Text))
{
qDebug()<<"open origin frontPrvFile:"<<frontPrvFile<<"failed!";
return false;
}
QTextStream originFrontPrvFileStream(&originFrontPrvFile);
originFrontPrvFileStream.setCodec("UTF-8");
originFrontPrvFileStream.setAutoDetectUnicode(true);
//新建frontPagePrvFile文件
QFile newFrontPrvFile(frontPagePrvFile);
if(!newFrontPrvFile.open(QIODevice::WriteOnly | QIODevice::Text))
{
qDebug()<<"open new frontPrvFile:"<<frontPagePrvFile<<"failed!";
originFrontPrvFile.close();
return false;
}
QTextStream newFrontPagePrvFileStream(&newFrontPrvFile);
newFrontPagePrvFileStream.setCodec("UTF-8");
newFrontPagePrvFileStream.setAutoDetectUnicode(true);
//通过读取frontPrvFile的prn序号,来构造正面Prv文件frontPagePrvFile
int nWritePrnNum=0;//记录frontPagePrvFile中写入的prn个数
while(!originFrontPrvFileStream.atEnd())
{
//每读取原始prv文件的一行,就在frontPagePrvFile文件中写入同样的pageCopy行
QString prnFileName = originFrontPrvFileStream.readLine();
if(prnFileName == PRVEND_FLAG)
{
break;
}
//在frontPagePrvFile中写pageCopy行prnFileName
for(int i = 0; i < pageCopy; i++)
{
newFrontPagePrvFileStream<<prnFileName<<"\n";
nWritePrnNum++;
}
}
newFrontPagePrvFileStream<<PRVEND_FLAG<<"\n";//追加结束标志符
newFrontPagePrvFileStream<<nWritePrnNum;//追加PRN文件个数
newFrontPrvFile.close();
originFrontPrvFile.close();