|Subject:||Re: Performance problem with hugh attachement|
|Posted by:||Remy Lebeau (TeamB) (firstname.lastname@example.org)|
|Date:||Thu, 7 Apr 2005|
"Charles Molnar" <charles.moln…@micotan.com> wrote in message
> I know it is the problem of the TMemoryStream. With the original
> Borland TMemoryStream every time when the stream size is
> increased the whole stream content is reallocated and copied.
Not always. Only when the new Size exceeds the current Capacity.
TMemoryStream allocates extra memory so that each time Write() is called,
the stream is not unnecessarily reallocated each time. The allocated memory
is always in increments of 8192 bytes. When the current Size exceeds 8192
bytes, the memory allocated such that an even multiple of 8192 bytes is
reallocated to contain the new Size.
> While the email is received the stream size is always increased
> with the received chunk length.
The Size is increased with each Write(), but not the Capacity. Reallocation
only occurs when the Size exceeds the Capacity.
> I'm not sure how bug is your receive buffer
The ReceiveBuffer has nothing to do with it.
> but assume it is 1024 or 4096 bytes.
The ReceiveBuffer is 32K (32768 bytes) by default.
> Let's say 1024, in this case the increasing size stream
> gets copied 14336 times.
The Size is increased, but not the Capacity. For a 14Mb stream, the memory
is reallocated at most 1792 times, not 14336. Probaby even less, if the
socket is able to receive more than 8192 at a time so that the stream is
allocated multiple increments of 8192 at a time.
With that said, you can always preallocate your stream by setting its Size
property ahead of time. However, there is no way to know ahead of time how
large the message will actually be, so you will just have to pick a default
size and if the message is larger then live with the knowledge that the
stream will still reallocate itself as needed.
> As an other workaround I created the TSmartMemoryStream
> object which is inherited from the original TMemoryStream, the
> Realloc function is overrided so I can take charge of the memory
You should not need to do that. TMemoryStream already does exactly that,
and has done so for many years.
Performance problem with hugh attachement posted by Charles Molnar on Thu, 07 Apr 2005