Compressing Memory Streams

Filed under Uncategorized

One thing that has definitely taken some getting used to (for me anyway) in VB.NET is the whole concept of streams.

I like the idea, generally, but I was working through some code to stream debugging info into a resource in an already compiled EXE file when I ran into a problem with decompressing the resource data.

It just wouldn’t decompress properly.

After backtracking and puzzling over it, I discovered that the problem was actually in the compression phase.

   Private Function pCompressStream(ByVal UncompressedStream As MemoryStream) As MemoryStream
      Dim CompressedStream As New System.IO.MemoryStream()
      Using GZip As New System.IO.Compression.GZipStream(CompressedStream, System.IO.Compression.CompressionMode.Compress)
         GZip.Write(UncompressedStream.ToArray, 0, UncompressedStream.Length)
      End Using
      Return CompressedStream
   End Function

Note the Dim GZip line? If you look at the overloads, there’s a possible 3’rd option, LeaveOpen. It defaults to false.

From what I can tell, if you connect a GZipStream up to a FileStream, there’s no need for this parameter. When the GZip closes, the file is closed and on you go.

But, with MemoryStreams, it’s quite unlikely that you’d want to close the resulting output memory stream after zipping data into it.

But that’s exactly what happens if you don’t set LeaveOpen to True.

What’s worse. You need to Close the GZipStream before reading that MemoryStream(either by using a USING block as I have, or by calling Close directly). If you don’t, garbage collection might not happen for some time and the final data in the internal GZip buffers won’t get written to your memory stream, resulting in only partial compressed data, which definitely won’t decompress properly!

All this is likely old hat to grizzled .NET heads, but if you’re like me and coming from an extensive VB6/assembler background, it can certainly causing some headscratching for a bit.

Post a Comment

Your email is never published nor shared. Required fields are marked *