Skip to content

[io] Properly abort when buffer size overflows max integer or size > maxBufferSize #19606

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 19 additions & 19 deletions core/base/inc/TBuffer.h
Original file line number Diff line number Diff line change
Expand Up @@ -64,9 +64,9 @@ class TBuffer : public TObject {
void operator=(const TBuffer &) = delete;

Int_t Read(const char *name) override { return TObject::Read(name); }
Int_t Write(const char *name, Int_t opt, Int_t bufsize) override
Int_t Write(const char *name, Int_t opt, Long64_t bufsize) override
{ return TObject::Write(name, opt, bufsize); }
Int_t Write(const char *name, Int_t opt, Int_t bufsize) const override
Int_t Write(const char *name, Int_t opt, Long64_t bufsize) const override
{ return TObject::Write(name, opt, bufsize); }

public:
Expand All @@ -78,53 +78,53 @@ class TBuffer : public TObject {
enum { kInitialSize = 1024, kMinimalSize = 128 };

TBuffer(EMode mode);
TBuffer(EMode mode, Int_t bufsize);
TBuffer(EMode mode, Int_t bufsize, void *buf, Bool_t adopt = kTRUE, ReAllocCharFun_t reallocfunc = nullptr);
TBuffer(EMode mode, Long64_t bufsize);
TBuffer(EMode mode, Long64_t bufsize, void *buf, Bool_t adopt = kTRUE, ReAllocCharFun_t reallocfunc = nullptr);
virtual ~TBuffer();

Int_t GetBufferVersion() const { return fVersion; }
Bool_t IsReading() const { return (fMode & kWrite) == 0; }
Bool_t IsWriting() const { return (fMode & kWrite) != 0; }
void SetReadMode();
void SetWriteMode();
void SetBuffer(void *buf, UInt_t bufsize = 0, Bool_t adopt = kTRUE, ReAllocCharFun_t reallocfunc = nullptr);
void SetBuffer(void *buf, Long64_t bufsize = 0, Bool_t adopt = kTRUE, ReAllocCharFun_t reallocfunc = nullptr);
ReAllocCharFun_t GetReAllocFunc() const;
void SetReAllocFunc(ReAllocCharFun_t reallocfunc = nullptr);
void SetBufferOffset(Int_t offset = 0) { fBufCur = fBuffer+offset; }
void SetBufferOffset(Long64_t offset = 0) { fBufCur = fBuffer+offset; }
void SetParent(TObject *parent);
TObject *GetParent() const;
char *Buffer() const { return fBuffer; }
char *GetCurrent() const { return fBufCur; }
Int_t BufferSize() const { return fBufSize; }
void DetachBuffer() { fBuffer = nullptr; }
Int_t Length() const { return (Int_t)(fBufCur - fBuffer); }
void Expand(Int_t newsize, Bool_t copy = kTRUE); // expand buffer to newsize
void AutoExpand(Int_t size_needed); // expand buffer to newsize
void Expand(Long64_t newsize, Bool_t copy = kTRUE); // expand buffer to newsize
void AutoExpand(Long64_t size_needed); // expand buffer to newsize
Bool_t ByteSwapBuffer(Long64_t n, EDataType type); // Byte-swap N primitive-elements in the buffer

virtual Bool_t CheckObject(const TObject *obj) = 0;
virtual Bool_t CheckObject(const void *obj, const TClass *ptrClass) = 0;

virtual Int_t ReadBuf(void *buf, Int_t max) = 0;
virtual void WriteBuf(const void *buf, Int_t max) = 0;
virtual Long64_t ReadBuf(void *buf, Long64_t max) = 0;
virtual void WriteBuf(const void *buf, Long64_t max) = 0;

virtual char *ReadString(char *s, Int_t max) = 0;
virtual char *ReadString(char *s, Long64_t max) = 0;
virtual void WriteString(const char *s) = 0;

virtual Int_t GetVersionOwner() const = 0;
virtual Int_t GetMapCount() const = 0;
virtual void GetMappedObject(UInt_t tag, void* &ptr, TClass* &ClassPtr) const = 0;
virtual void MapObject(const TObject *obj, UInt_t offset = 1) = 0;
virtual void MapObject(const void *obj, const TClass *cl, UInt_t offset = 1) = 0;
virtual void MapObject(const TObject *obj, ULong64_t offset = 1) = 0;
virtual void MapObject(const void *obj, const TClass *cl, ULong64_t offset = 1) = 0;
virtual void Reset() = 0;
virtual void InitMap() = 0;
virtual void ResetMap() = 0;
virtual void SetReadParam(Int_t mapsize) = 0;
virtual void SetWriteParam(Int_t mapsize) = 0;

virtual Int_t CheckByteCount(UInt_t startpos, UInt_t bcnt, const TClass *clss) = 0;
virtual Int_t CheckByteCount(UInt_t startpos, UInt_t bcnt, const char *classname) = 0;
virtual void SetByteCount(UInt_t cntpos, Bool_t packInVersion = kFALSE)= 0;
virtual Long64_t CheckByteCount(ULong64_t startpos, ULong64_t bcnt, const TClass *clss) = 0;
virtual Long64_t CheckByteCount(ULong64_t startpos, ULong64_t bcnt, const char *classname) = 0;
virtual void SetByteCount(ULong64_t cntpos, Bool_t packInVersion = kFALSE)= 0;

virtual void SkipVersion(const TClass *cl = nullptr) = 0;
virtual Version_t ReadVersion(UInt_t *start = nullptr, UInt_t *bcnt = nullptr, const TClass *cl = nullptr) = 0;
Expand Down Expand Up @@ -164,7 +164,7 @@ class TBuffer : public TObject {
virtual void SetPidOffset(UShort_t offset) = 0;
virtual Int_t GetBufferDisplacement() const = 0;
virtual void SetBufferDisplacement() = 0;
virtual void SetBufferDisplacement(Int_t skipped) = 0;
virtual void SetBufferDisplacement(Long64_t skipped) = 0;

// basic types and arrays of basic types
virtual void ReadFloat16 (Float_t *f, TStreamerElement *ele = nullptr) = 0;
Expand Down Expand Up @@ -320,8 +320,8 @@ class TBuffer : public TObject {
// Utilities for TStreamerInfo
virtual void ForceWriteInfo(TVirtualStreamerInfo *info, Bool_t force) = 0;
virtual void ForceWriteInfoClones(TClonesArray *a) = 0;
virtual Int_t ReadClones (TClonesArray *a, Int_t nobjects, Version_t objvers) = 0;
virtual Int_t WriteClones(TClonesArray *a, Int_t nobjects) = 0;
virtual Int_t ReadClones (TClonesArray *a, Long64_t nobjects, Version_t objvers) = 0;
virtual Int_t WriteClones(TClonesArray *a, Long64_t nobjects) = 0;

// Utilities for TClass
virtual Int_t ReadClassEmulated(const TClass *cl, void *object, const TClass *onfile_class = nullptr) = 0;
Expand Down
18 changes: 9 additions & 9 deletions core/base/inc/TDirectory.h
Original file line number Diff line number Diff line change
Expand Up @@ -254,20 +254,20 @@ can be replaced with the simpler and exception safe:
virtual void Save() {}
virtual Int_t SaveObjectAs(const TObject * /*obj*/, const char * /*filename*/="", Option_t * /*option*/="") const;
virtual void SaveSelf(Bool_t /*force*/ = kFALSE) {}
virtual void SetBufferSize(Int_t /* bufsize */) {}
virtual void SetBufferSize(Long64_t /* bufsize */) {}
virtual void SetModified() {}
virtual void SetMother(TObject *mother) {fMother = (TObject*)mother;}
void SetName(const char* newname) override;
virtual void SetTRefAction(TObject * /*ref*/, TObject * /*parent*/) {}
virtual void SetSeekDir(Long64_t) {}
virtual void SetWritable(Bool_t) {}
Int_t Sizeof() const override {return 0;}
virtual Int_t Write(const char * /*name*/=nullptr, Int_t /*opt*/=0, Int_t /*bufsize*/=0) override {return 0;}
virtual Int_t Write(const char * /*name*/=nullptr, Int_t /*opt*/=0, Int_t /*bufsize*/=0) const override {return 0;}
virtual Int_t WriteTObject(const TObject *obj, const char *name =nullptr, Option_t * /*option*/="", Int_t /*bufsize*/ =0);
virtual Int_t Write(const char * /*name*/=nullptr, Int_t /*opt*/=0, Long64_t /*bufsize*/=0) override {return 0;}
virtual Int_t Write(const char * /*name*/=nullptr, Int_t /*opt*/=0, Long64_t /*bufsize*/=0) const override {return 0;}
virtual Int_t WriteTObject(const TObject *obj, const char *name =nullptr, Option_t * /*option*/="", Long64_t /*bufsize*/ =0);
private:
/// \cond HIDDEN_SYMBOLS
Int_t WriteObject(void *obj, const char* name, Option_t *option="", Int_t bufsize=0); // Intentionally not implemented.
Int_t WriteObject(void *obj, const char* name, Option_t *option="", Long64_t bufsize=0); // Intentionally not implemented.
/// \endcond
public:
/// \brief Write an object with proper type checking.
Expand All @@ -280,7 +280,7 @@ can be replaced with the simpler and exception safe:
/// from TObject. The method redirects to TDirectory::WriteObjectAny.
template <typename T>
inline std::enable_if_t<!std::is_base_of<TObject, T>::value, Int_t>
WriteObject(const T *obj, const char *name, Option_t *option = "", Int_t bufsize = 0)
WriteObject(const T *obj, const char *name, Option_t *option = "", Long64_t bufsize = 0)
{
return WriteObjectAny(obj, TClass::GetClass<T>(), name, option, bufsize);
}
Expand All @@ -294,12 +294,12 @@ can be replaced with the simpler and exception safe:
/// TObject. The method redirects to TDirectory::WriteTObject.
template <typename T>
inline std::enable_if_t<std::is_base_of<TObject, T>::value, Int_t>
WriteObject(const T *obj, const char *name, Option_t *option = "", Int_t bufsize = 0)
WriteObject(const T *obj, const char *name, Option_t *option = "", Long64_t bufsize = 0)
{
return WriteTObject(obj, name, option, bufsize);
}
virtual Int_t WriteObjectAny(const void *, const char * /*classname*/, const char * /*name*/, Option_t * /*option*/="", Int_t /*bufsize*/ =0) {return 0;}
virtual Int_t WriteObjectAny(const void *, const TClass * /*cl*/, const char * /*name*/, Option_t * /*option*/="", Int_t /*bufsize*/ =0) {return 0;}
virtual Int_t WriteObjectAny(const void *, const char * /*classname*/, const char * /*name*/, Option_t * /*option*/="", Long64_t /*bufsize*/ =0) {return 0;}
virtual Int_t WriteObjectAny(const void *, const TClass * /*cl*/, const char * /*name*/, Option_t * /*option*/="", Long64_t /*bufsize*/ =0) {return 0;}
virtual void WriteDirHeader() {}
virtual void WriteKeys() {}

Expand Down
4 changes: 2 additions & 2 deletions core/base/inc/TObject.h
Original file line number Diff line number Diff line change
Expand Up @@ -170,8 +170,8 @@ class TObject {
virtual void SetDrawOption(Option_t *option=""); // *MENU*
virtual void SetUniqueID(UInt_t uid);
virtual void UseCurrentStyle();
virtual Int_t Write(const char *name = nullptr, Int_t option = 0, Int_t bufsize = 0);
virtual Int_t Write(const char *name = nullptr, Int_t option = 0, Int_t bufsize = 0) const;
virtual Int_t Write(const char *name = nullptr, Int_t option = 0, Long64_t bufsize = 0);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That might be necessary but is a serious problem. This function is overload a lot in both our code but also very possibly in user code. Unless those user have upgrade their code to use the override keyword (which is unlikely in my opinion), their code will compile correctly but do the wrong thing (revert to use the default behavior rather than their customization .... )

Copy link
Collaborator Author

@ferdymercury ferdymercury Aug 14, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What if we implement a dummy

Int_t Write(const char *name, Int_t option, Int_t bufsize) const final;

to trigger a compilation error, or at least a warning and avoid that silenced wrong behavior?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That would indeed provoke a compilation error ....

virtual Int_t Write(const char *name = nullptr, Int_t option = 0, Long64_t bufsize = 0) const;

/// IsDestructed
///
Expand Down
30 changes: 16 additions & 14 deletions core/base/src/TBuffer.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -70,10 +70,10 @@ TBuffer::TBuffer(EMode mode)
/// Create an I/O buffer object. Mode should be either TBuffer::kRead or
/// TBuffer::kWrite.

TBuffer::TBuffer(EMode mode, Int_t bufsize)
TBuffer::TBuffer(EMode mode, Long64_t bufsize)
{
if (bufsize < 0)
Fatal("TBuffer","Request to create a buffer with a negative size, likely due to an integer overflow: 0x%x for a max of 0x%x.", bufsize, kMaxBufferSize);
if (bufsize > kMaxBufferSize)
Fatal("TBuffer","Request to create a too large buffer: 0x%llx for a max of 0x%x.", bufsize, kMaxBufferSize);
if (bufsize < kMinimalSize) bufsize = kMinimalSize;
fBufSize = bufsize;
fMode = mode;
Expand Down Expand Up @@ -101,10 +101,10 @@ TBuffer::TBuffer(EMode mode, Int_t bufsize)
/// is provided, a Fatal error will be issued if the Buffer attempts to
/// expand.

TBuffer::TBuffer(EMode mode, Int_t bufsize, void *buf, Bool_t adopt, ReAllocCharFun_t reallocfunc)
TBuffer::TBuffer(EMode mode, Long64_t bufsize, void *buf, Bool_t adopt, ReAllocCharFun_t reallocfunc)
{
if (bufsize < 0)
Fatal("TBuffer","Request to create a buffer with a negative size, likely due to an integer overflow: 0x%x for a max of 0x%x.", bufsize, kMaxBufferSize);
if (bufsize > kMaxBufferSize)
Fatal("TBuffer","Request to create a too large buffer: 0x%llx for a max of 0x%x.", bufsize, kMaxBufferSize);
fBufSize = bufsize;
fMode = mode;
fVersion = 0;
Expand Down Expand Up @@ -155,10 +155,10 @@ TBuffer::~TBuffer()
/// If the size_needed is larger than the current size, the policy
/// is to expand to double the current size or the size_needed which ever is largest.

void TBuffer::AutoExpand(Int_t size_needed)
void TBuffer::AutoExpand(Long64_t size_needed)
{
if (size_needed < 0) {
Fatal("AutoExpand","Request to expand to a negative size, likely due to an integer overflow: 0x%x for a max of 0x%x.", size_needed, kMaxBufferSize);
if (size_needed > kMaxBufferSize) {
Fatal("AutoExpand","Request to expand a too large buffer: 0x%llx for a max of 0x%x.", size_needed, kMaxBufferSize);
}
if (size_needed > fBufSize) {
Long64_t doubling = 2LLU * fBufSize;
Expand All @@ -184,8 +184,10 @@ void TBuffer::AutoExpand(Int_t size_needed)
/// is provided, a Fatal error will be issued if the Buffer attempts to
/// expand.

void TBuffer::SetBuffer(void *buf, UInt_t newsiz, Bool_t adopt, ReAllocCharFun_t reallocfunc)
void TBuffer::SetBuffer(void *buf, Long64_t newsiz, Bool_t adopt, ReAllocCharFun_t reallocfunc)
{
if (newsiz > kMaxBufferSize)
Fatal("SetBuffer","Request to create a too large buffer: 0x%llx for a max of 0x%x.", newsiz, kMaxBufferSize);
if (fBuffer && TestBit(kIsOwner))
delete [] fBuffer;

Expand Down Expand Up @@ -220,19 +222,19 @@ void TBuffer::SetBuffer(void *buf, UInt_t newsiz, Bool_t adopt, ReAllocCharFun_t
/// In order to avoid losing data, if the current length is greater than
/// the requested size, we only shrink down to the current length.

void TBuffer::Expand(Int_t newsize, Bool_t copy)
void TBuffer::Expand(Long64_t newsize, Bool_t copy)
{
Int_t l = Length();
if ( (l > newsize) && copy ) {
if ( (Long64_t(l) > newsize) && copy ) {
newsize = l;
}
const Int_t extraspace = (fMode&kWrite)!=0 ? kExtraSpace : 0;

if ( ((Long64_t)newsize+extraspace) > kMaxBufferSize) {
if ( newsize > kMaxBufferSize - kExtraSpace) {
if (l < kMaxBufferSize) {
newsize = kMaxBufferSize - extraspace;
} else {
Fatal("Expand","Requested size (%d) is too large (max is %d).", newsize, kMaxBufferSize);
Fatal("Expand","Requested size (%lld) is too large (max is %d).", newsize, kMaxBufferSize);
}
}
if ( (fMode&kWrite)!=0 ) {
Expand Down
9 changes: 5 additions & 4 deletions core/base/src/TDirectory.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -343,11 +343,12 @@ static TBuffer* R__CreateBuffer()
if (!creator) {
R__LOCKGUARD(gROOTMutex);
TClass *c = TClass::GetClass("TBufferFile");
TMethod *m = c->GetMethodWithPrototype("TBufferFile","TBuffer::EMode,Int_t",kFALSE,ROOT::kExactMatch);
TMethod *m = c->GetMethodWithPrototype("TBufferFile","TBuffer::EMode,Long64_t",kFALSE,ROOT::kExactMatch);
assert(m != nullptr);
creator = (tcling_callfunc_Wrapper_t)( m->InterfaceMethod() );
}
TBuffer::EMode mode = TBuffer::kWrite;
Int_t size = 10000;
Long64_t size = 10000;
void *args[] = { &mode, &size };
TBuffer *result;
creator(nullptr,2,args,&result);
Expand Down Expand Up @@ -1424,9 +1425,9 @@ void TDirectory::RegisterGDirectory(TDirectory::SharedGDirectory_t &gdirectory_p
}

////////////////////////////////////////////////////////////////////////////////
/// \copydoc TDirectoryFile::WriteObject(const T*,const char*,Option_t*,Int_t).
/// \copydoc TDirectoryFile::WriteObject(const T*,const char*,Option_t*,Long64_t).

Int_t TDirectory::WriteTObject(const TObject *obj, const char *name, Option_t * /*option*/, Int_t /*bufsize*/)
Int_t TDirectory::WriteTObject(const TObject *obj, const char *name, Option_t * /*option*/, Long64_t /*bufsize*/)
{
const char *objname = "no name specified";
if (name) objname = name;
Expand Down
4 changes: 2 additions & 2 deletions core/base/src/TObject.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -940,7 +940,7 @@ void TObject::UseCurrentStyle()
/// The function returns the total number of bytes written to the file.
/// It returns 0 if the object cannot be written.

Int_t TObject::Write(const char *name, Int_t option, Int_t bufsize) const
Int_t TObject::Write(const char *name, Int_t option, Long64_t bufsize) const
{
if (R__unlikely(option & kOnlyPrepStep))
return 0;
Expand All @@ -962,7 +962,7 @@ Int_t TObject::Write(const char *name, Int_t option, Int_t bufsize) const
/// Write this object to the current directory. For more see the
/// const version of this method.

Int_t TObject::Write(const char *name, Int_t option, Int_t bufsize)
Int_t TObject::Write(const char *name, Int_t option, Long64_t bufsize)
{
return ((const TObject*)this)->Write(name, option, bufsize);
}
Expand Down
4 changes: 2 additions & 2 deletions core/cont/inc/TCollection.h
Original file line number Diff line number Diff line change
Expand Up @@ -206,8 +206,8 @@ class TCollection : public TObject {
void SetName(const char *name) { fName = name; }
virtual void SetOwner(Bool_t enable = kTRUE);
virtual bool UseRWLock(Bool_t enable = true);
Int_t Write(const char *name = nullptr, Int_t option = 0, Int_t bufsize = 0) override;
Int_t Write(const char *name = nullptr, Int_t option = 0, Int_t bufsize = 0) const override;
Int_t Write(const char *name = nullptr, Int_t option = 0, Long64_t bufsize = 0) override;
Int_t Write(const char *name = nullptr, Int_t option = 0, Long64_t bufsize = 0) const override;

R__ALWAYS_INLINE Bool_t IsUsingRWLock() const { return TestBit(TCollection::kUseRWLock); }

Expand Down
4 changes: 2 additions & 2 deletions core/cont/inc/TMap.h
Original file line number Diff line number Diff line change
Expand Up @@ -84,8 +84,8 @@ friend class TMapIter;
TPair *RemoveEntry(TObject *key);
virtual void SetOwnerValue(Bool_t enable = kTRUE);
virtual void SetOwnerKeyValue(Bool_t ownkeys = kTRUE, Bool_t ownvals = kTRUE);
Int_t Write(const char *name=nullptr, Int_t option=0, Int_t bufsize=0) override;
Int_t Write(const char *name=nullptr, Int_t option=0, Int_t bufsize=0) const override;
Int_t Write(const char *name=nullptr, Int_t option=0, Long64_t bufsize=0) override;
Int_t Write(const char *name=nullptr, Int_t option=0, Long64_t bufsize=0) const override;

ClassDefOverride(TMap,3) //A (key,value) map
};
Expand Down
4 changes: 2 additions & 2 deletions core/cont/src/TCollection.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -678,7 +678,7 @@ void TCollection::Streamer(TBuffer &b)
/// objects using a single key specify a name and set option to
/// TObject::kSingleKey (i.e. 1).

Int_t TCollection::Write(const char *name, Int_t option, Int_t bufsize) const
Int_t TCollection::Write(const char *name, Int_t option, Long64_t bufsize) const
{
if ((option & kSingleKey)) {
return TObject::Write(name, option, bufsize);
Expand All @@ -702,7 +702,7 @@ Int_t TCollection::Write(const char *name, Int_t option, Int_t bufsize) const
/// objects using a single key specify a name and set option to
/// TObject::kSingleKey (i.e. 1).

Int_t TCollection::Write(const char *name, Int_t option, Int_t bufsize)
Int_t TCollection::Write(const char *name, Int_t option, Long64_t bufsize)
{
return ((const TCollection*)this)->Write(name,option,bufsize);
}
Expand Down
4 changes: 2 additions & 2 deletions core/cont/src/TMap.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -402,7 +402,7 @@ void TMap::Streamer(TBuffer &b)
/// objects using a single key specify a name and set option to
/// TObject::kSingleKey (i.e. 1).

Int_t TMap::Write(const char *name, Int_t option, Int_t bufsize) const
Int_t TMap::Write(const char *name, Int_t option, Long64_t bufsize) const
{
if ((option & kSingleKey)) {
return TObject::Write(name, option, bufsize);
Expand All @@ -429,7 +429,7 @@ Int_t TMap::Write(const char *name, Int_t option, Int_t bufsize) const
/// objects using a single key specify a name and set option to
/// TObject::kSingleKey (i.e. 1).

Int_t TMap::Write(const char *name, Int_t option, Int_t bufsize)
Int_t TMap::Write(const char *name, Int_t option, Long64_t bufsize)
{
return ((const TMap*)this)->Write(name,option,bufsize);
}
Expand Down
4 changes: 2 additions & 2 deletions hist/hbook/inc/THbookBranch.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,8 @@ class THbookBranch : public TBranch {

public:
THbookBranch() {}
THbookBranch(TTree *tree, const char *name, void *address, const char *leaflist, Int_t basketsize=32000, Int_t compress = ROOT::RCompressionSetting::EAlgorithm::kInherit);
THbookBranch(TBranch *branch, const char *name, void *address, const char *leaflist, Int_t basketsize=32000, Int_t compress = ROOT::RCompressionSetting::EAlgorithm::kInherit);
THbookBranch(TTree *tree, const char *name, void *address, const char *leaflist, Long64_t basketsize=32000, Int_t compress = ROOT::RCompressionSetting::EAlgorithm::kInherit);
THbookBranch(TBranch *branch, const char *name, void *address, const char *leaflist, Long64_t basketsize=32000, Int_t compress = ROOT::RCompressionSetting::EAlgorithm::kInherit);
~THbookBranch() override;
void Browse(TBrowser *b) override;
Int_t GetEntry(Long64_t entry=0, Int_t getall=0) override;
Expand Down
Loading
Loading