1

How do I subscribe to Windows Low memory notification from c# ?

our c# app has substantial unmanaged memory allocation, which we can free if OS memory availability is low.

Lydon Ch
  • 8,637
  • 20
  • 79
  • 132
  • You can [check available memory](https://stackoverflow.com/questions/3296211/how-to-get-the-size-of-available-system-memory) and when it's low - do something. – SᴇM Feb 05 '19 at 06:16
  • Yes we do this at the moment, looping every 60s. but surely a low memory notification is ideal? – Lydon Ch Feb 05 '19 at 06:17
  • 1
    Well there is an event, called `LowMemory` in `SystemEvents`, but it's as far as I know, is obsolete. – SᴇM Feb 05 '19 at 06:20
  • @Johnny query WMI? is there a way for WMI to 'push' low memory event to an application? – Lydon Ch Feb 05 '19 at 06:25
  • 1
    @Johnny decided to use QueryMemoryResourceNotification and CreateMemoryResourceNotification to subscribe to windows low memory event, through PInvoke – Lydon Ch Feb 05 '19 at 07:42

1 Answers1

2

Using CreateMemoryResourceNotification and QueryMemoryResourceNotification to check memory status

    enum MemoryResourceNotificationType : int
    {
        LowMemoryResourceNotification = 0,
        HighMemoryResourceNotification = 1,
    }

    [DllImport("kernel32.dll", SetLastError = true)]
    static extern IntPtr CreateMemoryResourceNotification(MemoryResourceNotificationType notificationType);

    [DllImport("kernel32.dll", SetLastError = true)]
    internal static extern bool QueryMemoryResourceNotification(IntPtr resourceNotificationHandle, out int resourceState);

    private static IntPtr MemoryResourceNotificationHandle;

    public static void TryReclaim()
    {
        MemoryResourceNotificationHandle = CreateMemoryResourceNotification(MemoryResourceNotificationType.LowMemoryResourceNotification);

        int sleepIntervalInMs = ReclaimIntervalInSeconds * 1000;

        while (true)
        {
            Thread.Sleep(10_000);

            bool isSuccecced = QueryMemoryResourceNotification(MemoryResourceNotificationHandle, out int memoryStatus);

            if (isSuccecced)
            {
                if (memoryStatus >= 1)
                {
                   DoReclaim();
                }

            }

        }           


    }
Lydon Ch
  • 8,637
  • 20
  • 79
  • 132