When I use blowfish to encrypt / decrypt a stream, the stream will increase in size up a size evenly divisible by 8 when encrypted. When decrypted, the result is padded with null characters.
I did some tests and generated some streams of random data and then encrypted and decrypted.
Windows 11 x64. CT 7.9 - Attached a demo program to show exactly what I am doing.
0. InSize:4095, BlowSize:4096, OutSize:4096, InHash: 657DF591BDFED94A82EF7819EE852CE0, OutHash: 7520CC2C1A5CFE304072C90FDF159327 - Match: False
1. InSize:4096, BlowSize:4096, OutSize:4096, InHash: 9C750B9E40FAF2D84D652EE50DDD9C59, OutHash: 9C750B9E40FAF2D84D652EE50DDD9C59 - Match: True
2. InSize:4097, BlowSize:4104, OutSize:4104, InHash: 98306DE5BE44168AF915BE2A5AFF39F5, OutHash: 3CDEE16FF4B2A22DBC9AC8DA1E9F5EFA - Match: False
3. InSize:4098, BlowSize:4104, OutSize:4104, InHash: DFCF511C61EE9720970D6BB4A978FEEE, OutHash: 13F485B1CDFD8E00E6659BC616EDCBEF - Match: False
4. InSize:4099, BlowSize:4104, OutSize:4104, InHash: 94BD54877F54036A2787DD53F51E6023, OutHash: C220473A50C9E1C396FEF2104186AF89 - Match: False
5. InSize:4100, BlowSize:4104, OutSize:4104, InHash: 5054B6D9796CA07CAF693DE78AC0BE77, OutHash: 18C76E0C3C40EFA790EB9DC854AEAB16 - Match: False
6. InSize:4101, BlowSize:4104, OutSize:4104, InHash: DC9E3653DFAC055F2E1D08C203C8D40D, OutHash: A0011E58C042053D064D9399A4DF8390 - Match: False
7. InSize:4102, BlowSize:4104, OutSize:4104, InHash: 47647827FAD5651D7996F9364C3F31E3, OutHash: C39EBA1459F8C79B085A42F186541AF8 - Match: False
8. InSize:4103, BlowSize:4104, OutSize:4104, InHash: D1F2F6AF89F09DE498E322E96855778B, OutHash: E5E0A99680AFCCBC2AB877E60E02BB5D - Match: False
9. InSize:4104, BlowSize:4104, OutSize:4104, InHash: 2BCE1ED95D7306ACC866143B59B14DE7, OutHash: 2BCE1ED95D7306ACC866143B59B14DE7 - Match: True
Here is my code:
{ Uses BlowFish; }
Function BlowFishEncrypt(Const AClearStream: TStream; Const ABlowStream: TStream; Const APassword: String; Const ABufferSize: DWord): Boolean;
Var
ABlowFish: TBlowFishEncryptStream;
ABuffer: TBytes;
ABytesRead: Integer;
Begin
Result := True;
AClearStream.Position := 0;
ABlowStream.Position := 0;
Try
ABlowFish := TBlowFishEncryptStream.Create(APassword, ABlowStream);
Try
SetLength(ABuffer, ABufferSize);
Try
FillChar(ABuffer[0], ABufferSize, 0);
Repeat
// Read clear data from clear stream
ABytesRead := AClearStream.Read(ABuffer, ABufferSize);
// Write encrypted data to BlowFish stream
ABlowFish.Write(ABuffer, ABytesRead);
Until (ABytesRead < ABufferSize);
Finally
FillChar(ABuffer[0], Length(ABuffer), 0);
SetLength(ABuffer, 0);
End;
Finally
FreeAndNil(ABlowFish);
End;
Except
Result := False;
End;
End;
{ Uses BlowFish; }
Function BlowFishDecrypt(Const ABlowStream: TStream; Const AClearStream: TStream; Const APassword: String; Const ABufferSize: DWord): Boolean;
Var
ABlowFish: TBlowFishDeCryptStream;
ABuffer: TBytes;
ABytesRead: Integer;
Begin
Result := True;
ABlowStream.Position := 0;
AClearStream.Position := 0;
Try
ABlowFish := TBlowFishDeCryptStream.Create(APassword, ABlowStream);
Try
SetLength(ABuffer, ABufferSize);
Try
FillChar(ABuffer[0], ABufferSize, 0);
Repeat
// Read encrypted data from BlowFish stream
ABytesRead := ABlowFish.Read(ABuffer, ABufferSize);
// write clear data to clear stream
AClearStream.Write(ABuffer, ABytesRead);
Until (ABytesRead < ABufferSize);
Finally
FillChar(ABuffer[0], Length(ABuffer), 0);
SetLength(ABuffer, 0);
End;
Finally
FreeAndNil(ABlowFish);
End;
// AClearStream.Size := AClearStream.Size - 2;
Except
Result := False;
End;
End;