diff --git a/base/inc/TBuffer.h b/base/inc/TBuffer.h
index cc9ec36ffeb3b5e1d71fa7ad36cc30e9ff257a41..efeb5fd7ab8f2886b69f5e48aac68bf9fc5d3bca 100644
--- a/base/inc/TBuffer.h
+++ b/base/inc/TBuffer.h
@@ -1,4 +1,4 @@
-// @(#)root/base:$Name:  $:$Id: TBuffer.h,v 1.4 2000/12/12 18:22:11 rdm Exp $
+// @(#)root/base:$Name:  $:$Id: TBuffer.h,v 1.5 2001/03/21 09:28:01 brun Exp $
 // Author: Fons Rademakers   04/05/96
 
 /*************************************************************************
@@ -50,6 +50,8 @@ protected:
       TExMap *fWriteMap;   //Map containing object,id pairs during writing
    };
 
+   enum { kIsOwner = BIT(14) };  //If set TBuffer owns fBuffer
+
    static Int_t fgMapSize; //Default map size for all TBuffer objects
 
    // Default ctor
@@ -73,7 +75,8 @@ public:
    enum { kInitialSize = 1024, kMinimalSize = 128 };
    enum { kMapSize = 503 };
 
-   TBuffer(EMode mode, Int_t bufsiz = kInitialSize, void *buf = 0);
+   TBuffer(EMode mode, Int_t bufsiz = kInitialSize, void *buf = 0,
+           Bool_t adopt = kTRUE);
    virtual ~TBuffer();
 
    void     MapObject(const TObject *obj, UInt_t offset = 1);
@@ -84,7 +87,7 @@ public:
    void     SetReadParam(Int_t mapsize);
    void     SetWriteMode();
    void     SetWriteParam(Int_t mapsize);
-   void     SetBuffer(void *buf, UInt_t bufsiz = 0);
+   void     SetBuffer(void *buf, UInt_t bufsiz = 0, Bool_t adopt = kTRUE);
    void     SetBufferOffset(Int_t offset = 0) { fBufCur = fBuffer+offset; }
 
    char    *Buffer() const { return fBuffer; }
@@ -115,9 +118,8 @@ public:
 
    void     SetBufferDisplacement(Int_t skipped)
             { fDisplacement =  (Int_t)(Length() - skipped); }
-   void     SetBufferDisplacement()
-            { fDisplacement = 0; }
-   Int_t    GetBufferDisplacement() { return fDisplacement; }
+   void     SetBufferDisplacement() { fDisplacement = 0; }
+   Int_t    GetBufferDisplacement() const { return fDisplacement; }
 
    Int_t    ReadArray(Char_t   *&c);
    Int_t    ReadArray(UChar_t  *&c);
diff --git a/base/src/TBuffer.cxx b/base/src/TBuffer.cxx
index 608d7c00afbe6bdacbe50fb6e1e3c284d0f0eef0..019a422cbe8a2919d26d5334dca6134b1e5391b0 100644
--- a/base/src/TBuffer.cxx
+++ b/base/src/TBuffer.cxx
@@ -1,4 +1,4 @@
-// @(#)root/base:$Name:  $:$Id: TBuffer.cxx,v 1.17 2001/06/18 02:16:09 brun Exp $
+// @(#)root/base:$Name:  $:$Id: TBuffer.cxx,v 1.18 2001/11/16 02:44:33 rdm Exp $
 // Author: Fons Rademakers   04/05/96
 
 /*************************************************************************
@@ -51,12 +51,15 @@ Int_t TBuffer::fgMapSize   = kMapSize;
 
 
 ClassImp(TBuffer)
+
 //______________________________________________________________________________
-TBuffer::TBuffer(EMode mode, Int_t bufsiz, void *buf)
+TBuffer::TBuffer(EMode mode, Int_t bufsiz, void *buf, Bool_t adopt)
 {
    // Create an I/O buffer object. Mode should be either TBuffer::kRead or
    // TBuffer::kWrite. By default the I/O buffer has a size of
-   // TBuffer::kInitialSize (1024) bytes.
+   // TBuffer::kInitialSize (1024) bytes. An external buffer can be passed
+   // to TBuffer via the buf argument. By default this buffer will be adopted
+   // unless adopt is false.
 
    // Before using the buffer make sure some assumptions are true
    Assert(sizeof(Short_t) == 2);
@@ -79,9 +82,12 @@ TBuffer::TBuffer(EMode mode, Int_t bufsiz, void *buf)
    fReadMap  = 0;
    fDisplacement = 0;
 
-   if (buf)
+   SetBit(kIsOwner);
+
+   if (buf) {
       fBuffer = (char *)buf;
-   else
+      if (!adopt) ResetBit(kIsOwner);
+   } else
       fBuffer = new char[fBufSize+kExtraSpace];
    fBufCur = fBuffer;
    fBufMax = fBuffer + fBufSize;
@@ -92,7 +98,8 @@ TBuffer::~TBuffer()
 {
    // Delete an I/O buffer object.
 
-   delete [] fBuffer;
+   if (TestBit(kIsOwner))
+      delete [] fBuffer;
    fBuffer = 0;
 
    if (IsReading())
@@ -147,14 +154,23 @@ TBuffer &TBuffer::operator>>(Long_t &l)
 }
 
 //______________________________________________________________________________
-void TBuffer::SetBuffer(void *buf, UInt_t newsiz)
+void TBuffer::SetBuffer(void *buf, UInt_t newsiz, Bool_t adopt = kTRUE)
 {
-   // Adopt new buffer. First deletes existing buffer. Expects buf to
-   // have been allocated with new char [].
-
-   if (fBuffer)
+   // Sets a new buffer in an existing TBuffer object. If newsiz=0 then the
+   // new buffer is expected to have the same size as the previous buffer.
+   // The current buffer position is reset to the start of the buffer.
+   // If the TBuffer owned the previous buffer, it will be deleted prior
+   // to accepting the new buffer. By default the new buffer will be
+   // adopted unless adopt is false.
+
+   if (fBuffer && TestBit(kIsOwner))
       delete [] fBuffer;
 
+   if (adopt)
+      SetBit(kIsOwner);
+   else
+      ResetBit(kIsOwner);
+
    fBuffer = (char *)buf;
    fBufCur = fBuffer;
    if (newsiz > 0) fBufSize = newsiz;