Complete disaster-recovery snapshot: engine/game source, game data assets, VC6 toolchain + DX SDKs, build outputs, deployed game, and _UNUSED archive. Large binaries in Git LFS; text preserved byte-for-byte (core.autocrlf=false, no eol attributes). See RECOVERY.md for the one-clone rebuild procedure.
158 lines
3.1 KiB
C++
158 lines
3.1 KiB
C++
// FilePro.cpp: implementation of the CFilePro class.
|
|
//
|
|
//////////////////////////////////////////////////////////////////////
|
|
|
|
#include "stdafx.h"
|
|
#include "PatchIT.h"
|
|
#include "FilePro.h"
|
|
|
|
#ifdef _DEBUG
|
|
#undef THIS_FILE
|
|
static char THIS_FILE[]=__FILE__;
|
|
#define new DEBUG_NEW
|
|
#endif
|
|
|
|
float SyncRank(DWORD pos,DWORD size,DWORD sloc,DWORD fsize)
|
|
{
|
|
DWORD recommend_size=fsize/1000;
|
|
if(size>recommend_size) return 0.00000001f;
|
|
if(recommend_size==0) recommend_size=1;
|
|
float sweight,pweight;
|
|
if(size<=recommend_size)
|
|
sweight=(float)size/recommend_size;
|
|
else
|
|
sweight=(float)(fsize-(size-recommend_size))/(fsize-recommend_size);
|
|
|
|
//if(size<8 || size>(fsize*2.0)) sweight/=2.0;
|
|
|
|
|
|
pweight=(float)((fsize-sloc)-pos)/(fsize-sloc);
|
|
return pweight*sweight;
|
|
}
|
|
//////////////////////////////////////////////////////////////////////
|
|
// Construction/Destruction
|
|
//////////////////////////////////////////////////////////////////////
|
|
|
|
CFilePro::CFilePro()
|
|
{
|
|
BlockLoc=BlockSize=0;
|
|
}
|
|
|
|
|
|
void CFilePro::ReadBlockAt(DWORD bl)
|
|
{
|
|
BlockLoc=bl;
|
|
if(GetPosition()!=BlockLoc) Seek(bl,CFile::begin);
|
|
BlockSize=GetLength()-BlockLoc;
|
|
if(BlockSize<=BUFFERSIZE)
|
|
LastBlock=true;
|
|
else {BlockSize=BUFFERSIZE; LastBlock=false;}
|
|
|
|
Read(Buffer,BlockSize);
|
|
}
|
|
|
|
DWORD CFilePro::DifferAt(CFilePro &file,DWORD *floc)
|
|
{
|
|
|
|
DWORD pos1,pos2;
|
|
DWORD eof1,eof2;
|
|
eof1=GetLength();
|
|
eof2=file.GetLength();
|
|
pos1=GetPosition();
|
|
pos2=file.GetPosition();
|
|
|
|
while(GetByte(pos1)==file.GetByte(pos2) && pos1<eof1 && pos2<eof2) {pos1++; pos2++;}
|
|
Seek(pos1,CFile::begin);
|
|
file.Seek(pos2,CFile::begin);
|
|
*floc=pos2;
|
|
return pos1;
|
|
}
|
|
|
|
BYTE CFilePro::GetByte(DWORD loc)
|
|
{
|
|
if((loc-BlockLoc)<BlockSize)
|
|
return Buffer[loc-BlockLoc];
|
|
else
|
|
ReadBlockAt(loc);
|
|
return Buffer[0];
|
|
}
|
|
|
|
|
|
bool CFilePro::SyncedAt(CFilePro &file,DWORD *sloc,int earlyout)
|
|
{
|
|
DWORD pos;
|
|
DWORD cur_pos,old_pos,old_pos2,eof,eof2;
|
|
DWORD hipos=0,hisize=0;
|
|
float hirank=0.0f;
|
|
DWORD cnt=1;
|
|
float rank;
|
|
|
|
eof=GetLength();
|
|
eof2=file.GetLength();
|
|
cur_pos=old_pos=GetPosition();
|
|
old_pos2=file.GetPosition();
|
|
|
|
|
|
if(old_pos2>=eof2 || old_pos>=eof) return false;
|
|
|
|
while(cur_pos<eof && (earlyout<0 || hisize<(DWORD)earlyout))
|
|
{
|
|
pos=0;
|
|
while(GetByte(cur_pos)!=file.GetByte(old_pos2) && cur_pos<eof) cur_pos++;
|
|
|
|
if(cur_pos<eof)
|
|
{
|
|
cnt=1;
|
|
while(GetByte(cur_pos+cnt)==file.GetByte(old_pos2+cnt) && (cur_pos+cnt)<eof && (old_pos2+cnt)<eof2) cnt++;
|
|
rank=SyncRank(cur_pos,cnt,old_pos,eof);
|
|
|
|
|
|
if(rank>hirank) //Best Sync Rank
|
|
{
|
|
hirank=rank;
|
|
hisize=cnt;
|
|
hipos=cur_pos;
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
if(cnt>hisize) //Largeest BLock
|
|
{
|
|
hisize=cnt;
|
|
hipos=cur_pos;
|
|
}
|
|
*/
|
|
cur_pos++;
|
|
}
|
|
}
|
|
|
|
Seek(old_pos,CFile::begin);
|
|
file.Seek(old_pos2,CFile::begin);
|
|
*sloc=hipos;
|
|
return (hisize>0)?true:false;
|
|
}
|
|
|
|
unsigned __int64 CFilePro::CRC()
|
|
{
|
|
unsigned __int64 sum=0;
|
|
Seek(0,CFile::begin);
|
|
DWORD pos;
|
|
do
|
|
{
|
|
ReadBlockAt(GetPosition());
|
|
pos=0;
|
|
while(pos<BlockSize) {sum+=(__int64)Buffer[pos]; pos++;}
|
|
}
|
|
while(BlockSize>=BUFFERSIZE);
|
|
|
|
|
|
return sum;
|
|
}
|
|
|
|
CFilePro::~CFilePro()
|
|
{
|
|
|
|
}
|
|
|