320 fBrNames(new
TList), fTree(
tree), fPrefillType(GetConfiguredPrefillType())
323 Int_t nleaves =
tree->GetListOfLeaves()->GetEntriesFast();
387 const char *bname =
b->GetName();
388 if (
fTree->IsA() == TChain::Class()) {
395 const char *mothername =
b->GetMother()->GetName();
396 if (
b !=
b->GetMother() && mothername[strlen(mothername)-1] !=
'.') {
399 if (bem->GetType() < 3) {
403 if (strncmp(bname,build.
Data(),build.
Length()) != 0) {
405 bname = build.
Data();
412 if (
gDebug > 0) printf(
"Entry: %lld, registering branch: %s\n",
b->GetTree()->GetReadEntry(),
b->GetName());
420 for (
Int_t j = 0; j < nb; j++) {
422 if (!branch)
continue;
447 TLeaf *leaf, *leafcount;
458 if (!strcmp(bname,
"*")) all =
kTRUE;
459 for (i=0;i<nleaves;i++) {
466 if (strcmp(bname,branch->
GetName())
475 if (leafcount && !all) {
482 if (nb==0 && strchr(bname,
'*')==0) {
503 char *subbranch = (
char*)strstr(bname,fe->
GetName());
504 if (subbranch!=bname) subbranch = 0;
506 subbranch += strlen(fe->
GetName());
507 if ( *subbranch !=
'.' ) subbranch = 0;
519 if (!nb && !foundInFriend) {
520 if (
gDebug > 0) printf(
"AddBranch: unknown branch -> %s \n", bname);
521 Error(
"AddBranch",
"unknown branch -> %s", bname);
551 if (
gDebug > 0) printf(
"Entry: %lld, un-registering branch: %s\n",
b->GetTree()->GetReadEntry(),
b->GetName());
560 for (
Int_t j = 0; j < nb; j++) {
562 if (!branch)
continue;
587 TLeaf *leaf, *leafcount;
598 if (!strcmp(bname,
"*")) all =
kTRUE;
599 for (i=0;i<nleaves;i++) {
606 if (strcmp(bname,branch->
GetName())
615 if (leafcount && !all) {
622 if (nb==0 && strchr(bname,
'*')==0) {
643 char *subbranch = (
char*)strstr(bname,fe->
GetName());
644 if (subbranch!=bname) subbranch = 0;
646 subbranch += strlen(fe->
GetName());
647 if ( *subbranch !=
'.' ) subbranch = 0;
659 if (!nb && !foundInFriend) {
660 if (
gDebug > 0) printf(
"DropBranch: unknown branch -> %s \n", bname);
661 Error(
"DropBranch",
"unknown branch -> %s", bname);
728 Int_t *lbaskets =
b.GetBasketBytes();
735 Int_t blistsize =
b.GetWriteBasket();
744 if (basketOffset < 0) {
750 if ((basketOffset < blistsize) &&
b.GetListOfBaskets()->UncheckedAt(basketOffset)) {
756 Long64_t pos =
b.GetBasketSeek(basketOffset);
757 Int_t len = lbaskets[basketOffset];
798 TBranch *resultBranch =
nullptr;
801 std::vector<std::pair<size_t, Int_t>> basketsInfo;
805 for (
int i = 0; i < count; i++) {
810 if (iopos.
fLen == 0) {
813 if (iopos.
fPos == pos && iopos.
fLen == len) {
814 found_request =
kTRUE;
822 Int_t blistsize =
b->GetWriteBasket();
823 Int_t basketNumber = -1;
824 for (
Int_t bn = 0; bn < blistsize; ++bn) {
825 if (iopos.
fPos ==
b->GetBasketSeek(bn)) {
830 if (basketNumber >= 0)
831 basketsInfo.emplace_back((
size_t)i, basketNumber);
840 for (
auto &info : basketsInfo) {
841 perfStats->SetLoadedMiss(info.first, info.second);
892 std::vector<Long64_t> positions;
893 positions.reserve(
fMissCache->fEntries.size());
894 std::vector<Int_t> lengths;
898 positions.push_back(mcentry.fIO.fPos);
899 lengths.push_back(mcentry.fIO.fLen);
900 mcentry.fIndex = cumulative;
901 cumulative += mcentry.fIO.fLen;
933 auto iter = std::lower_bound(
fMissCache->fEntries.begin(),
fMissCache->fEntries.end(), mcentry);
936 if (len > iter->fIO.fLen) {
940 auto offset = iter->fIndex;
941 memcpy(buf, &(
fMissCache->fData[offset]), len);
961 auto offset = iter->fIndex;
963 memcpy(buf, &(
fMissCache->fData[offset]), len);
984 Range() : fMin(-1), fMax(-1) {}
988 if (fMin == -1 || min < fMin)
994 if (fMax == -1 || fMax < max)
998 Bool_t Contains(
Long64_t entry) {
return (fMin <= entry && entry <= fMax); }
1001 std::vector<Range> fRanges;
1002 std::map<Long64_t,size_t> fMinimums;
1003 std::map<Long64_t,size_t> fMaximums;
1005 BasketRanges(
size_t nBranches) { fRanges.resize(nBranches); }
1009 Range &range = fRanges.at(branchNumber);
1012 range.UpdateMin(min);
1013 range.UpdateMax(max);
1015 if (old.fMax != range.fMax) {
1016 if (old.fMax != -1) {
1017 auto maxIter = fMaximums.find(old.fMax);
1018 if (maxIter != fMaximums.end()) {
1019 if (maxIter->second == 1) {
1020 fMaximums.erase(maxIter);
1022 --(maxIter->second);
1030 void Update(
size_t branchNumber,
size_t basketNumber,
Long64_t *entries,
size_t nb,
size_t max)
1032 Update(branchNumber, entries[basketNumber],
1033 (basketNumber < (nb - 1)) ? (entries[basketNumber + 1] - 1) : max - 1);
1037 bool CheckAllIncludeRange()
1040 for (
const auto &
r : fRanges) {
1041 if (result.fMin == -1 || result.fMin <
r.fMin) {
1043 result.fMin =
r.fMin;
1045 if (result.fMax == -1 ||
r.fMax < result.fMax) {
1047 result.fMax =
r.fMax;
1054 Range allIncludedRange(AllIncludedRange());
1056 return (result.fMin == allIncludedRange.fMin && result.fMax == allIncludedRange.fMax);
1066 Range AllIncludedRange()
1069 if (!fMinimums.empty())
1070 result.fMin = fMinimums.rbegin()->first;
1071 if (!fMaximums.empty())
1072 result.fMax = fMaximums.begin()->first;
1077 UInt_t BranchesRegistered()
1080 for (
const auto &
r : fRanges) {
1081 if (
r.fMin != -1 &&
r.fMax != -1)
1091 for (
const auto &
r : fRanges) {
1092 if (
r.fMin != -1 &&
r.fMax != -1)
1093 if (
r.fMin <= entry && entry <=
r.fMax)
1101 for (
size_t i = 0; i < fRanges.size(); ++i) {
1102 if (fRanges[i].fMin != -1 || fRanges[i].fMax != -1)
1103 Printf(
"Range #%zu : %lld to %lld", i, fRanges[i].fMin, fRanges[i].fMax);
1162 if (entry < 0) entry = 0;
1168 if (entry < 0)
return kFALSE;
1174 if (entry < 0 && fEntryNext > 0) {
1194 static constexpr bool showMore =
kFALSE;
1196 static const auto PrintAllCacheInfo = [](
TObjArray *branches) {
1197 for (
Int_t i = 0; i < branches->GetEntries(); i++) {
1203 if (showMore ||
gDebug > 6)
1204 Info(
"FillBuffer",
"***** Called for entry %lld", entry);
1212 if (!
b->fCacheInfo.AllUsed()) {
1219 if (showMore ||
gDebug > 5)
1220 Info(
"FillBuffer",
"All baskets used already, so refresh the cache early at entry %lld", entry);
1239 resetBranchInfo =
kTRUE;
1240 if (showMore ||
gDebug > 6)
1241 Info(
"FillBuffer",
"*** Will reset the branch information about baskets");
1242 }
else if (showMore ||
gDebug > 6) {
1243 Info(
"FillBuffer",
"*** Info we have on the set of baskets");
1250 auto entryCurrent = clusterIter();
1266 if (showMore ||
gDebug > 6)
1280 if (resetBranchInfo) {
1283 if (!(fEntryCurrent < fCurrentClusterStart || fEntryCurrent >=
fNextClusterStart)) {
1284 Error(
"FillBuffer",
"Inconsistency: fCurrentClusterStart=%lld fEntryCurrent=%lld fNextClusterStart=%lld "
1285 "but fEntryCurrent should not be in between the two",
1301 if (
fTree->IsA() ==TChain::Class()) {
1309 Int_t ntotCurrentBuf = 0;
1313 ntotCurrentBuf =
fNtot;
1322 ntotCurrentBuf =
fNtot;
1329 Int_t clusterIterations = 0;
1333 Int_t nReadPrefRequest = 0;
1336 struct collectionInfo {
1337 Int_t fClusterStart{-1};
1341 void Rewind() { fCurrent = (fClusterStart >= 0) ? fClusterStart : 0; }
1343 std::vector<collectionInfo> cursor(
fNbranches);
1351 prevNtot = ntotCurrentBuf;
1357 Int_t nDistinctLoad = 0;
1369 auto CollectBaskets = [
this, elist, chainOffset, entry, clusterIterations, resetBranchInfo, perfStats,
1370 &cursor, &lowestMaxEntry, &maxReadEntry, &minEntry,
1371 &reachedEnd, &skippedFirst, &oncePerBranch, &nDistinctLoad, &progress,
1372 &ranges, &memRanges, &reqRanges,
1373 &ntotCurrentBuf, &nReadPrefRequest](EPass pass, ENarrow narrow,
Long64_t maxCollectEntry) {
1377 Int_t nReachedEnd = 0;
1379 auto oldnReadPrefRequest = nReadPrefRequest;
1380 std::vector<Int_t> potentialVetoes;
1382 if (showMore ||
gDebug > 7)
1383 Info(
"CollectBaskets",
"Called with pass=%d narrow=%d maxCollectEntry=%lld", pass, narrow, maxCollectEntry);
1390 if (
b->GetDirectory()->GetFile() !=
fFile)
1392 potentialVetoes.clear();
1393 if (pass == kStart && !cursor[i].fLoadedOnce && resetBranchInfo) {
1397 b->fCacheInfo.GetUnused(potentialVetoes);
1398 if (showMore ||
gDebug > 7) {
1400 for(
auto v : potentialVetoes) {
1404 if (!potentialVetoes.empty())
1405 Info(
"FillBuffer",
"*** Potential Vetos for branch #%d: %s", i, vetolist.
Data());
1407 b->fCacheInfo.Reset();
1409 Int_t nb =
b->GetMaxBaskets();
1410 Int_t *lbaskets =
b->GetBasketBytes();
1411 Long64_t *entries =
b->GetBasketEntry();
1412 if (!lbaskets || !entries)
1416 Int_t blistsize =
b->GetListOfBaskets()->GetSize();
1418 auto maxOfBasket = [
this, nb, entries](
int j) {
1419 return ((j < (nb - 1)) ? (entries[j + 1] - 1) :
fEntryMax - 1);
1422 if (pass == kRewind)
1424 else if (cursor[i].fCurrent == -1) {
1426 cursor[i].fCurrent = (start < 0) ? 0 : start;
1428 for (
auto &j = cursor[i].fCurrent; j < nb; j++) {
1431 if (j < blistsize && b->GetListOfBaskets()->UncheckedAt(j)) {
1433 if (showMore ||
gDebug > 6) {
1434 ranges.Update(i, entries[j], maxOfBasket(j));
1435 memRanges.Update(i, entries[j], maxOfBasket(j));
1437 if (entries[j] <= entry && entry <= maxOfBasket(j)) {
1438 b->fCacheInfo.SetIsInCache(j);
1439 b->fCacheInfo.SetUsed(j);
1453 if (entries[j] >= maxCollectEntry) {
1459 Int_t len = lbaskets[j];
1460 if (pos <= 0 || len <= 0)
1464 if ((showMore ||
gDebug > 7) &&
1465 (!(entries[j] < minEntry && (j < nb - 1 && entries[j + 1] <= minEntry))))
1466 Info(
"FillBuffer",
"Skipping branch %s basket %d is too large for the cache: %d > %d",
1471 if (nReadPrefRequest && entries[j] > (reqRanges.AllIncludedRange().fMax + 1)) {
1481 if (showMore ||
gDebug > 8)
1482 Info(
"FillBuffer",
"Skipping for now due to gap %d/%d with %lld > %lld", i, j, entries[j],
1483 (reqRanges.AllIncludedRange().fMax + 1));
1487 if (entries[j] < minEntry && (j<nb-1 && entries[j+1] <= minEntry))
1491 if (cursor[i].fClusterStart == -1)
1492 cursor[i].fClusterStart = j;
1497 emax = entries[j + 1] - 1;
1498 if (!elist->
ContainsRange(entries[j]+chainOffset,emax+chainOffset))
1502 if (
b->fCacheInfo.HasBeenUsed(j) ||
b->fCacheInfo.IsInCache(j) ||
b->fCacheInfo.IsVetoed(j)) {
1505 if (showMore ||
gDebug > 7)
1506 Info(
"FillBuffer",
"Skipping basket to avoid redo: %d/%d veto: %d", i, j,
b->fCacheInfo.IsVetoed(j));
1510 if (std::find(std::begin(potentialVetoes), std::end(potentialVetoes), j) != std::end(potentialVetoes)) {
1517 b->fCacheInfo.Veto(j);
1518 if (showMore ||
gDebug > 7)
1519 Info(
"FillBuffer",
"Veto-ing cluster %d [%lld,%lld[ in branch %s #%d", j, entries[j],
1520 maxOfBasket(j) + 1,
b->GetName(), i);
1525 if ((((entries[j] > entry)) || (j < nb - 1 && entries[j + 1] <= entry))) {
1527 if (j == cursor[i].fClusterStart && entry > entries[j])
1529 if (entries[j] > entry)
1538 if (clusterIterations > 0 && cursor[i].fLoadedOnce) {
1542 if (showMore ||
gDebug > 5) {
1545 "Breaking early because %d is greater than %d at cluster iteration %d will restart at %lld",
1546 (ntotCurrentBuf + len),
fBufferSizeMin, clusterIterations, minEntry);
1552 if (pass == kStart || !cursor[i].fLoadedOnce) {
1560 if (showMore ||
gDebug > 5) {
1561 Info(
"FillBuffer",
"Breaking early because %d is greater than 4*%d at cluster iteration "
1562 "%d pass %d will restart at %lld",
1574 if (showMore ||
gDebug > 5) {
1575 Info(
"FillBuffer",
"Breaking early because %d is greater than 2*%d at cluster iteration "
1576 "%d pass %d will restart at %lld",
1588 reqRanges.Update(i, j, entries, nb,
fEntryMax);
1589 if (showMore ||
gDebug > 6)
1590 ranges.Update(i, j, entries, nb,
fEntryMax);
1592 b->fCacheInfo.SetIsInCache(j);
1594 if (showMore ||
gDebug > 6)
1595 Info(
"FillBuffer",
"*** Registering branch %d basket %d %s", i, j,
b->GetName());
1597 if (!cursor[i].fLoadedOnce) {
1598 cursor[i].fLoadedOnce =
kTRUE;
1602 perfStats->SetLoaded(i, j);
1609 ntotCurrentBuf =
fNtot;
1618 ntotCurrentBuf =
fNtot;
1621 if ( ( j < (nb-1) ) && entries[j+1] > maxReadEntry ) {
1623 maxReadEntry = entries[j+1];
1627 Warning(
"FillBuffer",
"There is more data in this cluster (starting at entry %lld to %lld, "
1628 "current=%lld) than usual ... with %d %.3f%% of the branches we already have "
1629 "%d bytes (instead of %d)",
1633 if (pass == kStart) {
1635 auto high = maxOfBasket(j);
1636 if (high < lowestMaxEntry)
1637 lowestMaxEntry = high;
1641 }
else if ((j + 1) == nb || entries[j + 1] >= maxReadEntry || entries[j + 1] >= lowestMaxEntry) {
1643 auto high = maxOfBasket(j);
1644 if (high < lowestMaxEntry)
1645 lowestMaxEntry = high;
1652 if (cursor[i].fCurrent == nb) {
1657 Info(
"CollectBaskets",
1658 "Entry: %lld, registering baskets branch %s, fEntryNext=%lld, fNseek=%d, ntotCurrentBuf=%d",
1662 skippedFirst = (nSkipped > 0);
1663 oncePerBranch = (nDistinctLoad ==
fNbranches);
1664 progress = nReadPrefRequest - oldnReadPrefRequest;
1671 full = CollectBaskets(kStart, kNarrow,
fEntryNext);
1675 while (!full && !reachedEnd && progress) {
1676 full = CollectBaskets(kStart, kFull, std::min(maxReadEntry,
fEntryNext));
1679 resetBranchInfo =
kFALSE;
1684 full = CollectBaskets(kRegular, kFull,
fEntryNext);
1685 }
while (!full && !reachedEnd && progress);
1689 if (!full && skippedFirst) {
1690 full = CollectBaskets(kRewind, kFull,
fEntryNext);
1691 while (!full && !reachedEnd && progress) {
1692 full = CollectBaskets(kRegular, kFull,
fEntryNext);
1696 clusterIterations++;
1698 minEntry = clusterIter.
Next();
1716 (prevNtot < ntotCurrentBuf) && (minEntry <
fEntryMax))) {
1717 if (showMore ||
gDebug > 6)
1718 Info(
"FillBuffer",
"Breaking because %d <= %lld || (%d >= %d) || %lld >= %lld",
fBufferSizeMin,
1719 ((
Long64_t)ntotCurrentBuf * (clusterIterations + 1)) / clusterIterations, prevNtot, ntotCurrentBuf,
1728 if (minEntry >= fEntryCurrentMax && fEntryCurrentMax > 0)
1736 if (showMore ||
gDebug > 6) {
1737 Info(
"FillBuffer",
"Mem ranges");
1739 Info(
"FillBuffer",
"Combined ranges");
1741 Info(
"FillBuffer",
"Requested ranges");
1746 if (nReadPrefRequest == 0) {
1750 if (showMore ||
gDebug > 5) {
1751 Info(
"FillBuffer",
"For entry %lld, nothing was added to the cache.", entry);
1753 }
else if (
fEntryNext < firstClusterEnd && !reqRanges.Contains(entry)) {
1765 if (showMore ||
gDebug > 5) {
1766 Error(
"FillBuffer",
"Reset the next entry because the currently loaded range does not contains the request "
1767 "entry: %lld. fEntryNext updated from %lld to %lld. %d",
1768 entry,
fEntryNext, firstClusterEnd, nReadPrefRequest);
1774 if (showMore ||
gDebug > 5) {
1775 Info(
"FillBuffer",
"Complete adding %d baskets from %d branches taking in memory %d out of %d",
1776 nReadPrefRequest, reqRanges.BranchesRegistered(), ntotCurrentBuf,
fBufferSizeMin);
1805 if (!(stcp =
gSystem->
Getenv(
"ROOT_TTREECACHE_PREFILL")) || !*stcp) {
1903 printf(
"Number of branches in the cache ...: %d\n",
fNbranches);
1904 printf(
"Cache Efficiency ..................: %f\n",
GetEfficiency());
1909 if ( opt.
Contains(
"cachedbranches") ) {
1911 printf(
"Cached branches....................:\n");
1914 for (
Int_t i = 0; i < nbranches; ++i) {
1916 printf(
"Branch name........................: %s\n",branch->
GetName());
1935 ::Info(
"TTreeCache::ReadBufferNormal",
"Cache miss after an %s FillBuffer: pos=%lld",
1936 bufferFilled ?
"active" :
"inactive", basketpos);
1937 for (
Int_t i = 0; i < branches->GetEntries(); ++i) {
1939 Int_t blistsize =
b->GetListOfBaskets()->GetSize();
1940 for (
Int_t j = 0; j < blistsize; ++j) {
1941 if (basketpos ==
b->GetBasketSeek(j)) {
1943 ::Info(
"TTreeCache::ReadBufferNormal",
" Missing basket: %d for %s", j,
b->GetName());
1957 else if (res == 0) {
1961 recordMiss(perfStats,
fBranches, bufferFilled, pos);
1974 recordMiss(perfStats,
fBranches, bufferFilled, pos);
2044 if (
b->GetDirectory()->GetFile() !=
fFile)
2046 b->fCacheInfo.Reset();
2078 if (res == 0 && buffersize <= prevsize) {
2113 Info(
"SetEntryRange",
"fEntryMin=%lld, fEntryMax=%lld, fEntryNext=%lld",
2116 if (needLearningStart) {
2264 if (entry < fEntryMin || entry >
fEntryMax)
return;
#define R__unlikely(expr)
unsigned long long ULong64_t
void Printf(const char *fmt,...)
R__EXTERN TSystem * gSystem
A Branch for the case of an object.
A TTree is a list of TBranches.
@ kDoNotProcess
Active bit for branches.
void PrintCacheInfo() const
Print the information we have about which basket is currently cached and whether they have been 'used...
Long64_t fEntries
Number of entries.
A chain is a collection of files containing TTree objects.
virtual Int_t GetTreeNumber() const
Long64_t * GetTreeOffset() const
virtual Int_t GetEntries() const
virtual Int_t GetValue(const char *name, Int_t dflt) const
Returns the integer value for a resource.
A TEventList object is a list of selected events (entries) in a TTree.
virtual Bool_t ContainsRange(Long64_t entrymin, Long64_t entrymax)
Return TRUE if list contains entries from entrymin to entrymax included.
A cache when reading files over the network.
virtual Int_t SetBufferSize(Int_t buffersize)
Sets the buffer size.
virtual Int_t ReadBuffer(char *buf, Long64_t pos, Int_t len)
Read buffer at position pos.
virtual void SecondPrefetch(Long64_t, Int_t)
virtual void Print(Option_t *option="") const
Print cache statistics.
Bool_t fEnablePrefetching
reading by prefetching asynchronously
Int_t fNtot
Total size of prefetched blocks.
virtual void Prefetch(Long64_t pos, Int_t len)
Add block of length len at position pos in the list of blocks to be prefetched.
Int_t fBufferSizeMin
Original size of fBuffer.
Bool_t fIsTransferred
True when fBuffer contains something valid.
TFile * fFile
Pointer to file.
Int_t fNseek
Number of blocks to be prefetched.
virtual Int_t GetBufferSize() const
virtual void SetFile(TFile *file, TFile::ECacheAction action=TFile::kDisconnect)
Set the file using this cache and reset the current blocks (if any).
A ROOT file is a suite of consecutive data records (TKey instances) with a well defined format.
virtual Bool_t ReadBuffers(char *buf, Long64_t *pos, Int_t *len, Int_t nbuf)
Read the nbuf blocks described in arrays pos and len.
ECacheAction
TTreeCache flushing semantics.
virtual void SetCacheRead(TFileCacheRead *cache, TObject *tree=0, ECacheAction action=kDisconnect)
Set a pointer to the read cache.
A TFriendElement TF describes a TTree object TF in a file.
virtual TTree * GetTree()
Return pointer to friend TTree.
A TLeaf describes individual elements of a TBranch See TBranch structure in TTree.
virtual TLeaf * GetLeafCount() const
If this leaf stores a variable-sized array or a multi-dimensional array whose last dimension has vari...
TBranch * GetBranch() const
virtual void Add(TObject *obj)
virtual TObject * Remove(TObject *obj)
Remove object from the list.
virtual TObject * FindObject(const char *name) const
Find an object in this list using its name.
virtual void Delete(Option_t *option="")
Remove all objects from the list AND delete all heap based objects.
virtual const char * GetName() const
Returns name of object.
Int_t GetEntriesFast() const
virtual void AddAtAndExpand(TObject *obj, Int_t idx)
Add object at position idx.
TObject * UncheckedAt(Int_t i) const
virtual TObject * Remove(TObject *obj)
Remove object from array.
virtual void AddAt(TObject *obj, Int_t idx)
Add object at position ids.
Collectable string class.
const char * GetName() const
Returns name of object.
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Regular expression class.
void ToLower()
Change string to lower-case.
Int_t Atoi() const
Return integer value of string.
const char * Data() const
TString & ReplaceAll(const TString &s1, const TString &s2)
TString & Append(const char *cs)
void Form(const char *fmt,...)
Formats a string using a printf style format descriptor.
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
virtual const char * Getenv(const char *env)
Get environment variable.
A cache to speed-up the reading of ROOT datasets.
virtual Int_t AddBranch(TBranch *b, Bool_t subgbranches=kFALSE)
Add a branch to the list of branches to be stored in the cache this function is called by the user vi...
virtual void SetLearnPrefill(EPrefillType type=kNoPrefill)
Set whether the learning period is started with a prefilling of the cache and which type of prefillin...
virtual void UpdateBranches(TTree *tree)
Update pointer to current Tree and recompute pointers to the branches in the cache.
void SetOptimizeMisses(Bool_t opt)
Start of methods for the miss cache.
Double_t GetEfficiencyRel() const
This will indicate a sort of relative efficiency... a ratio of the reads found in the cache to the nu...
Bool_t fReverseRead
! reading in reverse mode
Bool_t fLearnPrefilling
! true if we are in the process of executing LearnPrefill
Long64_t fLastMiss
! set to the event # of the last miss.
Int_t fNMissReadPref
Number of blocks read into the secondary ("miss") cache.
virtual Int_t SetBufferSize(Int_t buffersize)
Change the underlying buffer size of the cache.
Int_t fNMissReadOk
Number of blocks read, not found in the primary cache, and found in the secondary cache.
Bool_t fOneTime
! used in the learning phase
virtual void SetFile(TFile *file, TFile::ECacheAction action=TFile::kDisconnect)
Change the file that is being cached.
Long64_t fEntryMin
! first entry in the cache
virtual Bool_t FillBuffer()
Fill the cache buffer with the branches in the cache.
Bool_t ProcessMiss(Long64_t pos, int len)
! Given a file read not in the miss cache, handle (possibly) loading the data.
static void SetLearnEntries(Int_t n=10)
Static function to set the number of entries to be used in learning mode The default value for n is 1...
Long64_t fEntryNext
! next entry number where cache must be filled
Int_t fNReadMiss
Number of blocks read and not found in the cache.
Double_t GetEfficiency() const
Give the total efficiency of the primary cache... defined as the ratio of blocks found in the cache v...
Bool_t fEnabled
! cache enabled for cached reading
Bool_t fIsLearning
! true if cache is in learning mode
Long64_t fNextClusterStart
! End+1 of the cluster(s) where the current content was picked out
const TObjArray * GetCachedBranches() const
virtual ~TTreeCache()
Destructor. (in general called by the TFile destructor)
Bool_t CheckMissCache(char *buf, Long64_t pos, int len)
Check the miss cache for a particular buffer, fetching if deemed necessary.
Int_t fNMissReadMiss
Number of blocks read and not found in either cache.
IOPos FindBranchBasketPos(TBranch &, Long64_t entry)
Given a branch and an entry, determine the file location (offset / size) of the corresponding basket.
virtual void SetEntryRange(Long64_t emin, Long64_t emax)
Set the minimum and maximum entry number to be processed this information helps to optimize the numbe...
TTreeCache()
Default Constructor.
std::unique_ptr< MissCache > fMissCache
! Cache contents for misses
Bool_t fFirstTime
! save the fact that we processes the first entry
void StartLearningPhase()
The name should be enough to explain the method.
virtual Int_t LearnBranch(TBranch *b, Bool_t subgbranches=kFALSE)
Add a branch discovered by actual usage to the list of branches to be stored in the cache this functi...
Bool_t fReadDirectionSet
! read direction established
TBranch * CalculateMissEntries(Long64_t, int, bool)
Given an file read, try to determine the corresponding branch.
Long64_t fCurrentClusterStart
! Start of the cluster(s) where the current content was picked out
Double_t GetMissEfficiency() const
The total efficiency of the 'miss cache' - defined as the ratio of blocks found in the cache versus t...
virtual Int_t ReadBufferNormal(char *buf, Long64_t pos, Int_t len)
Old method ReadBuffer before the addition of the prefetch mechanism.
virtual void ResetCache()
This will simply clear the cache.
Bool_t fIsManual
! true if cache is StopLearningPhase was used
EPrefillType fPrefillType
Whether a pre-filling is enabled (and if applicable which type)
virtual void LearnPrefill()
Perform an initial prefetch, attempting to read as much of the learning phase baskets for all branche...
virtual Int_t ReadBuffer(char *buf, Long64_t pos, Int_t len)
Read buffer at position pos if the request is in the list of prefetched blocks read from fBuffer.
Long64_t fEntryMax
! last entry in the cache
static Int_t fgLearnEntries
number of entries used for learning mode
virtual Int_t DropBranch(TBranch *b, Bool_t subbranches=kFALSE)
Remove a branch to the list of branches to be stored in the cache this function is called by TBranch:...
virtual Int_t ReadBufferPrefetch(char *buf, Long64_t pos, Int_t len)
Used to read a chunk from a block previously fetched.
Long64_t fEntryCurrent
! current lowest entry number in the cache
void ResetMissCache()
Reset all the miss cache training.
Long64_t fFirstMiss
! set to the event # of the first miss.
Double_t GetMissEfficiencyRel() const
Relative efficiency of the 'miss cache' - ratio of the reads found in cache to the number of reads so...
Long64_t fFirstEntry
! save the value of the first entry
Int_t fFillTimes
! how many times we can fill the current buffer
Int_t fNReadPref
Number of blocks that were prefetched.
TTree * fTree
! pointer to the current Tree
EPrefillType GetConfiguredPrefillType() const
Return the desired prefill type from the environment or resource variable.
Bool_t fFirstBuffer
! true if first buffer is used for prefetching
static Int_t GetLearnEntries()
Static function returning the number of entries used to train the cache see SetLearnEntries.
virtual void StopLearningPhase()
This is the counterpart of StartLearningPhase() and can be used to stop the learning phase.
Bool_t fOptimizeMisses
! true if we should optimize cache misses.
Int_t fNbranches
! Number of branches in the cache
Int_t fNReadOk
Number of blocks read and found in the cache.
virtual void Print(Option_t *option="") const
Print cache statistics.
TObjArray * fBranches
! List of branches to be stored in the cache
TList * fBrNames
! list of branch names in the cache
Helper class to iterate over cluster of baskets.
Long64_t Next()
Move on to the next cluster and return the starting entry of this next cluster.
A TTree represents a columnar dataset.
virtual TVirtualPerfStats * GetPerfStats() const
virtual TBranch * GetBranch(const char *name)
Return pointer to the branch with the given name in this tree or its friends.
virtual TObjArray * GetListOfLeaves()
virtual Long64_t GetEntries() const
virtual Long64_t GetReadEntry() const
virtual TTree * GetTree() const
TEventList * GetEventList() const
virtual TList * GetListOfFriends() const
Provides the interface for the PROOF internal performance measurement and event tracing.
virtual void SetMissed(TBranch *b, size_t basketNumber)=0
virtual void UpdateBranchIndices(TObjArray *branches)=0
void Print(std::ostream &os, const OptionType &opt)
Long64_t BinarySearch(Long64_t n, const T *array, T value)
Int_t fLen
Position in file of cache entry.