#include "TFile.h"
#include "TFileCacheRead.h"
#include "TFileCacheWrite.h"
#include "TMath.h"
ClassImp(TFileCacheRead)
TFileCacheRead::TFileCacheRead() : TObject()
{
fBufferSizeMin = 0;
fBufferSize = 0;
fBufferLen = 0;
fNseek = 0;
fNtot = 0;
fNb = 0;
fSeekSize = 0;
fSeek = 0;
fSeekIndex = 0;
fSeekSort = 0;
fPos = 0;
fSeekLen = 0;
fSeekSortLen = 0;
fSeekPos = 0;
fLen = 0;
fFile = 0;
fBuffer = 0;
fIsSorted = kFALSE;
}
TFileCacheRead::TFileCacheRead(TFile *file, Int_t buffersize)
: TObject()
{
if (buffersize <=10000) fBufferSize = 100000;
fBufferSizeMin = buffersize;
fBufferSize = buffersize;
fBufferLen = 0;
fNseek = 0;
fNtot = 0;
fNb = 0;
fSeekSize = 10000;
fSeek = new Long64_t[fSeekSize];
fSeekIndex = new Long64_t[fSeekSize];
fSeekSort = new Long64_t[fSeekSize];
fPos = new Long64_t[fSeekSize];
fSeekLen = new Int_t[fSeekSize];
fSeekSortLen = new Int_t[fSeekSize];
fSeekPos = new Int_t[fSeekSize];
fLen = new Int_t[fSeekSize];
fFile = file;
fBuffer = new char[fBufferSize];
fIsSorted = kFALSE;
if (file) file->SetCacheRead(this);
}
TFileCacheRead::~TFileCacheRead()
{
delete [] fSeek;
delete [] fSeekIndex;
delete [] fSeekSort;
delete [] fPos;
delete [] fSeekLen;
delete [] fSeekSortLen;
delete [] fSeekPos;
delete [] fLen;
delete [] fBuffer;
}
void TFileCacheRead::Prefetch(Long64_t pos, Int_t len)
{
fIsSorted = kFALSE;
if (pos <= 0) {
fNseek = 0;
fNtot = 0;
return;
}
if (fNseek >= fSeekSize) {
fSeekSize *= 2;
Long64_t *aSeek = new Long64_t[fSeekSize];
Long64_t *aSeekIndex = new Long64_t[fSeekSize];
Long64_t *aSeekSort = new Long64_t[fSeekSize];
Long64_t *aPos = new Long64_t[fSeekSize];
Int_t *aSeekLen = new Int_t[fSeekSize];
Int_t *aSeekSortLen = new Int_t[fSeekSize];
Int_t *aSeekPos = new Int_t[fSeekSize];
Int_t *aLen = new Int_t[fSeekSize];
for (Int_t i=0;i<fNseek;i++) {
aSeek[i] = fSeek[i];
aSeekIndex[i] = fSeekIndex[i];
aSeekSort[i] = fSeekSort[i];
aPos[i] = fPos[i];
aSeekLen[i] = fSeekLen[i];
aSeekSortLen[i] = fSeekSortLen[i];
aSeekPos[i] = fSeekPos[i];
aLen[i] = fLen[i];
}
delete [] fSeek;
delete [] fSeekIndex;
delete [] fSeekSort;
delete [] fPos;
delete [] fSeekLen;
delete [] fSeekSortLen;
delete [] fSeekPos;
delete [] fLen;
fSeek = aSeek;
fSeekIndex = aSeekIndex;
fSeekSort = aSeekSort;
fPos = aPos;
fSeekLen = aSeekLen;
fSeekSortLen = aSeekSortLen;
fSeekPos = aSeekPos;
fLen = aLen;
}
fSeek[fNseek] = pos;
fSeekLen[fNseek] = len;
fNseek++;
fNtot += len;
}
void TFileCacheRead::Print(Option_t *option) const
{
TString opt = option;
opt.ToLower();
printf("Number of blocks: %d, total size : %d\n",fNseek,fNtot);
if (!opt.Contains("a")) return;
for (Int_t i=0;i<fNseek;i++) {
if (fIsSorted && !opt.Contains("s")) {
printf("block: %5d, from: %lld to %lld, len=%d bytes\n",i,fSeekSort[i],fSeekSort[i]+fSeekSortLen[i],fSeekSortLen[i]);
} else {
printf("block: %5d, from: %lld to %lld, len=%d bytes\n",i,fSeek[i],fSeek[i]+fSeekLen[i],fSeekLen[i]);
}
}
printf ("Number of long buffers = %d\n",fNb);
for (Int_t j=0;j<fNb;j++) {
printf("fPos[%d]=%lld, fLen=%d\n",j,fPos[j],fLen[j]);
}
}
Int_t TFileCacheRead::ReadBuffer(char *buf, Long64_t pos, Int_t len)
{
if (fNseek > 0 && !fIsSorted) {
Sort();
if (fFile->ReadBuffers(fBuffer,fPos,fLen,fNb)) {
return -1;
}
}
if (TFileCacheWrite *cachew = fFile->GetCacheWrite()) {
if (cachew->ReadBuffer(buf,pos,len) == 0) {
fFile->Seek(pos+len);
return 1;
}
}
Int_t loc = (Int_t)TMath::BinarySearch(fNseek,fSeekSort,pos);
if (loc >= 0 && loc <fNseek && pos == fSeekSort[loc]) {
memcpy(buf,&fBuffer[fSeekPos[loc]],len);
fFile->Seek(pos+len);
return 1;
}
return 0;
}
void TFileCacheRead::SetFile(TFile *file)
{
fFile = file;
Prefetch(0,0);
}
void TFileCacheRead::Sort()
{
if (!fNseek) return;
TMath::Sort(fNseek,fSeek,fSeekIndex,kFALSE);
Int_t i;
Int_t nb = 0;
for (i=0;i<fNseek;i++) {
Long64_t ind = fSeekIndex[i];
fSeekSort[i] = fSeek[ind];
fSeekSortLen[i] = fSeekLen[ind];
}
if (fNtot > fBufferSizeMin) {
fBufferSize = fNtot + 100;
delete [] fBuffer;
fBuffer = new char[fBufferSize];
}
fPos[0] = fSeekSort[0];
fLen[0] = fSeekSortLen[0];
fSeekPos[0] = 0;
for (i=1;i<fNseek;i++) {
fSeekPos[i] = fSeekPos[i-1] + fSeekSortLen[i-1];
if (fSeekSort[i] != fSeekSort[i-1]+fSeekSortLen[i-1]) {
nb++;
fPos[nb] = fSeekSort[i];
fLen[nb] = fSeekSortLen[i];
} else {
fLen[nb] += fSeekSortLen[i];
}
}
fNb = nb+1;
fIsSorted = kTRUE;
}
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.