GDI Leak when rendering alpha-blend contents to some printers in Windows 10

Andy De Filippo 6 Reputation points
2021-03-31T14:53:11.257+00:00

I'm experiencing a very odd legacy gdi object leak when printing on certain printers under Windows 10.

It happens even when you print on Microsoft virtual printers, such as the "Microsoft XPS Document Writer".
It has to do with rendering 32bppARGB images to a printer Graphics, regardless of its origin. It happens when you render an in-memory created bitmap with argb contents.

The memory leak happens on Windows 10 19042.867 x64 and does not happen on Windows 7 (x64, x32), with the same virtual printer.
It does not happen when the contents of the image being rendered do not contain any semi-transparent pixels.

I've created a test project to easily reproduce the behavior:

Imports System.Drawing
Imports System.Drawing.Printing

Module Module1

    Sub Main()

        ' Get Microsoft XPS Document Writer printer settings
        Dim prnSettings As New PrinterSettings() With {.PrinterName = "Microsoft XPS Document Writer"}

        ' Ensure printer is valid
        If prnSettings.IsValid = False Then
            MsgBox("Can't find Microsoft XPS Document Writer.", MsgBoxStyle.Exclamation)
            Exit Sub
        End If

        ' Init document settings
        m_prtDoc = New PrintDocument With {.DocumentName = "PNG24 print test",
                                           .PrinterSettings = prnSettings}

        ' Start printing
        m_prtDoc.Print()

        ' Clean up
        m_prtDoc.Dispose()

        MsgBox("Check GDI objects count, probably thru the roof.", MsgBoxStyle.Information)

    End Sub

    ' Document settings
    Private WithEvents m_prtDoc As PrintDocument = Nothing

    ' Page count
    Private m_iPageCount As Integer = 0

    Private Sub PrintPage(sender As Object, e As PrintPageEventArgs) Handles m_prtDoc.PrintPage

        Try

            ' Create in memory image of the same size
            Using imgMemory As New Bitmap(600, 400)

                ' Fill with alpha color
                Using gphMemory As Graphics = Graphics.FromImage(imgMemory)
                    gphMemory.Clear(Color.FromArgb(128, 255, 0, 0)) ' Red at 0.5 alpha
                End Using

                ' Draw in-memory image
                e.Graphics.DrawImageUnscaled(imgMemory, e.PageBounds.Location)

            End Using

            ' Increase page counter
            m_iPageCount += 1

            ' The number of rendering repetitions
            Const REPETITIONS As Integer = 20

            ' Print up to REPETITIONS pages
            e.HasMorePages = (m_iPageCount < REPETITIONS)

        Catch ex As Exception
            ' Error, Stop printing
            MsgBox(ex.Message, MsgBoxStyle.Critical)
        End Try

    End Sub
End Module

Stack overflow question:
https://stackoverflow.com/questions/66872343/gdi-memory-leak-when-printing-png24-images-with-gdiplus

Any help is appreciated.
Thank you.

Developer technologies | VB
Developer technologies | C#
Developer technologies | C#
An object-oriented and type-safe programming language that has its roots in the C family of languages and includes support for component-oriented programming.
{count} votes

1 answer

Sort by: Most helpful
  1. Andy De Filippo 6 Reputation points
    2021-04-14T07:53:08.977+00:00

    For anyone stumbling upon this issue, it seems that the problem was solved with update KB5001649

    Make sure you and/or your customers keep Windows up to date and this issue won't affect your projects.

    1 person found this answer helpful.
    0 comments No comments

Your answer

Answers can be marked as 'Accepted' by the question author and 'Recommended' by moderators, which helps users know the answer solved the author's problem.