[fpc-pascal] TBlowfishDecryptStream flaw

Michael Van Canneyt michael at freepascal.org
Sun Mar 6 14:52:24 CET 2011



On Sun, 6 Mar 2011, Jorge Aldo G. de F. Junior wrote:

> Check those two programs
>
> ======= Program A =====
[snip]
> ===== EOF =====
>
> The problem consists that, if lIntermediate.Size is not equal to
> lSource.Size, i will not know how much bytes to "copyfrom" from the
> decrypter.

Correct. You may never know. Imagine your data was compressed. 
You would need the ORIGINAL uncompressed size, not the compressed size.

Please Re-Read my first reply:

"You should always design your algorithms so they don't need size.
Compression and encryption streams cannot have size, since they do not know
the size of the input data."

You'll never know in advance how many bytes go through a socket, unless
the size was sent first. so the comment in your code:

   // ReceiveStreamViaSocket(lIntermediate);  { Lets pretend this function can check the socket for the size of the last UDP packet }

is in general false. Size is not available on a socket, unless it was pushed.
Or if the data comes from standard input, as with piping.

Your idea of a decryptor stream in which you push data is good, but will 
not help in case of a socket or standard input.

Anyway, I don't see what is wrong with

   D:=TDecryptor.Create(SomeStreamWithEncryptedData);
   try
     repeat
       b:=D.Read(ABuffer,BufferSize);
       if b<>0 then
         processbuffer(abuffer,b);
     until (b=0);
   finally
     D.Free;
   end;

If you look at the standard algorithms in the RTL, you'll see that they
never use Size, except in the case of CopyFrom(Somestream,0).

Borland made a design mistake when they implemented Size and Seek as 
standard methods/properties of TStream. These 2 properties are available 
only in a a minority of the streams. (Where they are useful, I'm not 
arguing that).

Michael.



More information about the fpc-pascal mailing list