Discussion Groups

Ikon notification sounds quit working

This question is answered

We use our Ikons with an application that creates OS notifications and plays a .wav file to alert the operator.   We have found the sound quits after approximately 150 notifications.  The device will not play any sound file until it is warm booted.  This issue causes some devices to quit after only 2 hours.  It is impractical to reboot this often so we need to find a solution.

The device does not seem to be out of memory since all the other functions are still operating and MCC reports plenty of memory available.  These IKONs are WM6.1 Classic devices.  We know this process can work since we ran a similar app on our old WAP devices using WM2003 second edition and did not experience any limitations.

This appears to be  an issue with wmplayer.exe locking up due to a resource constraint but I've not had much luck pinpointing what is going wrong and how to fix.

Any ideas for a work around or how to fix with registry or other settings?

Verified Answer
  • I thought I'd reply to update anyone that finds this post with what the real problem and fix was.  It took opening a case with Microsoft to find the answer but it works!  Smile

    In order to "Clean up" after notifications properly you have to add 2 registry settings

    [HKEY_CURRENT_USER\controlpanel\notifications]
    “MuteSoundOnClose”=dword:1
     
    [HKEY_CURRENT_USER\ControlPanel\Notifications]
    "AlertInterrupt"=dword:00000001.

    Here is what was reported to me regarding "AlertInterrupt":

    This issue was seen on your setup due to large number of notifications your application is creating and playing continuously. Due to architecture of the shell notifications, each notification is played in separate sound script and the script thread does not exit immediately after sound is played. This is causing the OOM behavior you are seeing on your devices. With AlertInterrupt registry keys, previous event notifications threads will be stopped before starting a new one and that is resolving this issue for you. This registry key is documented under “Phone Registry Settings” topic in WM OEM documentation.

    Here is the info on "MuteSoundOnClose":

    MuteSoundOnClose registry key is used to send WAV_CLOSE to sound script after the notification bubble is dismissed by the user.  This is useful to stop notification sound in case when notification sound is long and user has already dismissed the notification.

    This was not documented.  MS said they would put in a documentation request.

    So, This solved my case and I hope it helps someone else...

     

All Replies
  • Good morning Dan,

    Dan Despres
    We use our Ikons with an application that creates OS notifications and plays a .wav file to alert the operator.

    Can you please provide us additional details about the above?

    E.g.
    How is this done programmatically?
    Is the application calling the Microsoft PlaySound, ShellExecuteEx or SHNotificationAdd API?

    Kind regards,
    Jacques

  • Jacques,

            We set the notifications to play sounds by updating the registry to enable sounds for notifications and setting the sound to be played.  The OS takes over from there and provides the functionality.  We use a shell function SHNotificationAdd to set the notification.

     

     

  • I am not the developer but here is the section of the program that seems to call the notification:

     

    API.SHNOTIFICATIONDATA nf =

    new API.SHNOTIFICATIONDATA();

    FreeStringPointer(nf.pszTitle);

    FreeStringPointer(nf.pszHTML);

    nf.cbStruct = (

    uint)Marshal.SizeOf(nf);

    nf.pszTitle = StringToPointer(title);

    nf.pszHTML = StringToPointer(html);

    nf.hicon = appIcon;

    nf.clsid = appGuid;

    nf.hwndSink = msgWindow.Hwnd;

    nf.csDuration = (

    uint) numShowNotifyTime.Value;

    nf.dwID = currAlertID;

    if (ckbMessageOnAlert.Checked)

    nf.npPriority = API.SHNP_PRIORITY_INFORM;

    else

    nf.npPriority = API.SHNP_PRIORITY_ICONIC;

    if (message.Force)

    nf.grfFlags += API.SHNP_FLAGS_FORCEMSG;

    if (message.Priority)

    nf.grfFlags += API.SHNP_FLAGS_CRITICAL;

    if (API.SHNotificationAdd(ref nf) == 0)

    {

    lock (queue)

    {

    queue.Add(nf.dwID);

    labQueue.Text = queue.Count.ToString();

    }

    }

    FreeStringPointer(nf.pszHTML);

    FreeStringPointer(nf.pszTitle);

    Thread.Sleep(500);

    }

    private void RemoveNotification(uint id)

    {

    Guid pass = appGuid;

    if (API.SHNotificationRemove(ref pass, id) == 0)

    {

    lock (queue)

    {

    queue.Remove(id);

    labQueue.Text = queue.Count.ToString();

    }

    }

    }

  • Jacques,

    Any Ideas I can pursue on this issue?  Does the OS have a method (other that reboot) to restore the sound function or is this a solution only found programatically?

  • Good morning Dan,

    Few words to bring to your attention that I managed to observe / reproduce the problem you reported.
    As it stands, I am tempted to believe that we are facing a "Out Of Memory" issue.

    Let me carry on my investigations and get back to you.
    Kind regards,

    Jacques

  • Good afternoon Dan,

    As stated earlier this morning, the SHNotificationAdd API seems to leak some memory every time it plays the wave file, which file name and path information is stored in the [HKEY_CURRENT_USER\ControlPanel\Notifications\Default] "Wave" REG_SZ registry key.

    Indeed, as I launched the below attached Visual Studio 2008 C++ SHNotification Demo.exe program, which simply keeps calling the SHNotificationAdd and SHNotificationRemove APIs until the Stop SHNotification Demo.exe program is executed, I started to receive the below debug info:

    Load module: SHNotification Demo.exe
    Load module: commctrl.dll.0409.MUI
    Load module: commctrl.dll
    Load module: aygshell.dll
    Load module: ossvcs.dll
    Load module: coredll.dll.0409.MUI
    Load module: ole32.dll
    Load module: coredll.dll

      +-----------------------------------------------> Iteration #
      |     +-----------------------------------------> Current memory load (%)
      |     |        +--------------------------------> Physical memory available 
      |     |        |                                  (bytes)

      |     |        |                 +--------------> Name of the API called
      |     |        |                 |           +--> Returned value (0 = SUCCESS)
      |     |        |                 |           | 
    [000] [32% - 0x0494C000]    SHNotificationAdd: 0

    [000] [32% - 0x04949000] SHNotificationRemove: 0
    [001] [32% - 0x04949000]    SHNotificationAdd: 0
    [001] [32% - 0x04947000] SHNotificationRemove: 0
    [002] [32% - 0x04947000]    SHNotificationAdd: 0
    [002] [32% - 0x04945000] SHNotificationRemove: 0
    [003] [32% - 0x04945000]    SHNotificationAdd: 0
    [003] [32% - 0x04943000] SHNotificationRemove: 0
    [004] [32% - 0x04943000]    SHNotificationAdd: 0
    [004] [32% - 0x04941000] SHNotificationRemove: 0

    As you can see, on every SHNotificationAdd call the amount of available physical memory slowly but surely decreases.

    As the SHNotification Demo.exe program reached iteration #130, I noticed that
    » although the SHNotificationAdd API still returned SUCCESS, I could no longer hear the sound notification
    » the amount of available physical memory stopped decreasing

    [131] [34% - 0x047F1000]    SHNotificationAdd: 0
    [131] [34% - 0x047F1000] SHNotificationRemove: 0
    [132] [34% - 0x047F1000]    SHNotificationAdd: 0
    [132] [34% - 0x047F1000] SHNotificationRemove: 0
    [133] [34% - 0x047F1000]    SHNotificationAdd: 0
    [133] [34% - 0x047F1000] SHNotificationRemove: 0
    [134] [34% - 0x047F1000]    SHNotificationAdd: 0
    [134] [34% - 0x047F1000] SHNotificationRemove: 0
    [135] [34% - 0x047F1000]    SHNotificationAdd: 0
    [135] [34% - 0x047F1000] SHNotificationRemove: 0
    [136] [34% - 0x047F1000]    SHNotificationAdd: 0
    [136] [34% - 0x047F1000] SHNotificationRemove: 0
    [137] [34% - 0x047F1000]    SHNotificationAdd: 0
    [137] [34% - 0x047F1000] SHNotificationRemove: 0
    [138] [34% - 0x047F1000]    SHNotificationAdd: 0
    [138] [34% - 0x047F1000] SHNotificationRemove: 0
    [139] [34% - 0x047F1000]    SHNotificationAdd: 0
    [139] [34% - 0x047F1000] SHNotificationRemove: 0

    At this stage, I opened up File Explorer and got the below warning / error message as I tried to play the \Windows\Alarm2.wav file

    --

    This said, to overcome this issue, I went ahead and changed the SHNotification Demo.exe program as follows:

    » added the SHNF_SILENT flag to the grfFlags member of the SHNOTIFICATIONDATA structure
    » let the program call the PlaySound API right after calling the SHNotificationAdd API

    As illustrated below, no memory is consumed every time the SHNotificationAdd API is called

    Load module: SHNotification Demo.exe
    Load module: commctrl.dll.0409.MUI
    Load module: commctrl.dll
    Load module: aygshell.dll
    Load module: ossvcs.dll
    Load module: coredll.dll.0409.MUI
    Load module: ole32.dll
    Load module: coredll.dll
    [000] [33% - 0x048F4000]    SHNotificationAdd: 0

    [000] [33% - 0x048F4000] SHNotificationRemove: 0
    [001] [33% - 0x048F4000]    SHNotificationAdd: 0
    [001] [33% - 0x048F4000] SHNotificationRemove: 0
    [002] [33% - 0x048F4000]    SHNotificationAdd: 0
    [002] [33% - 0x048F4000] SHNotificationRemove: 0
    [003] [33% - 0x048F4000]    SHNotificationAdd: 0
    [003] [33% - 0x048F4000] SHNotificationRemove: 0
    [004] [33% - 0x048F4000]    SHNotificationAdd: 0
    [004] [33% - 0x048F4000] SHNotificationRemove: 0
    [005] [33% - 0x048F4000]    SHNotificationAdd: 0
    [005] [33% - 0x048F4000] SHNotificationRemove: 0

    [...]

    [297] [33% - 0x048F4000]    SHNotificationAdd: 0
    [297] [33% - 0x048F4000] SHNotificationRemove: 0
    [298] [33% - 0x048F4000]    SHNotificationAdd: 0
    [298] [33% - 0x048F4000] SHNotificationRemove: 0
    [299] [33% - 0x048F4000]    SHNotificationAdd: 0
    [299] [33% - 0x048F4000] SHNotificationRemove: 0
    [300] [33% - 0x048F4000]    SHNotificationAdd: 0
    [300] [33% - 0x048F4000] SHNotificationRemove: 0
    [301] [33% - 0x048F4000]    SHNotificationAdd: 0
    [301] [33% - 0x048F4000] SHNotificationRemove: 0

    [...]

    [485] [33% - 0x048F4000]    SHNotificationAdd: 0
    [485] [33% - 0x048F4000] SHNotificationRemove: 0
    [486] [33% - 0x048F4000]    SHNotificationAdd: 0
    [486] [33% - 0x048F4000] SHNotificationRemove: 0
    [487] [33% - 0x048F4000]    SHNotificationAdd: 0
    [487] [33% - 0x048F4000] SHNotificationRemove: 0
    [488] [33% - 0x048F4000]    SHNotificationAdd: 0
    The thread 'WaitForExitEventThread' (0x65ca50aa) has exited with code 0 (0x0).
    [488] [33% - 0x048F5000] SHNotificationRemove: 0
    Unload module: commctrl.dll
    Unload module: aygshell.dll
    Unload module: ossvcs.dll
    Unload module: ole32.dll
    The program '[0xE5C769D6] SHNotification Demo.exe' has exited with code 0 (0x0).

    --

    If interested, here follows the solution I quickly putted together and used to conduct my tests:

      VS2008 C++ SHNotification [DEMO] Solution (compressed)

    I do hope this helps.
    Kind regards,

    Jacques

    Ref: SCR-35699

  • Hi Jacques,

    Very interesting!

    Is this memory leak reported somewhere?

     

  • Alert Heap Dump 400 alerts Managed Memory.txt

    Jacques,

    We've tried your suggested solution inside our code but have been unsuccessful in our attempts to remedy this issue.   We've found an interesting work around other than reboot that, while impractical for regular use, is an interesting clue.  Once the sound quits the user can navigate to "Sounds and Notifications" in the settings menu.  If you attempt to stop and start a sound from the notifications tab, the ability of the device to play sound recovers and runs for another 130-150 notifications. 

    Using the Playsound API in our program still allows the sounds to quit.  The device will still give an out of memory error even though the physical memory has quite a bit remaining, the application heap and GC heap are very low in usage, and all memory usage with native and managed is less than 3MB at peak.  We've used the .NET CF Power Toys to try to profile the code and have ruled out leaks being caused by managed code.  We took a snapshot of the performance counters and GC heap while the device was in this "out of memory" state and executed our work around, created another snapshot of the GC heap and the program informed us that there were no changes, but our sound returned.  Breaking the code into segments (Mocking the web service, calling PlaySound thousands of times, adding notifications thousands of times) has not rendered a reliable way to reproduce the error.

    We are at a loss for further paths to follow.  Any experience with why another application might free the sounds and why we could not "see" a memory problem even though the device reports it?  I've attached the Power Toys snapshot files for what they are worth.  The first attachment is the managed memory object list and another post will be the actual heap dump.

     

  • Alert Heap Dump 400 alerts.txt

    Here is the actual heap dump from the device that quit making sound....

  • I thought I'd reply to update anyone that finds this post with what the real problem and fix was.  It took opening a case with Microsoft to find the answer but it works!  Smile

    In order to "Clean up" after notifications properly you have to add 2 registry settings

    [HKEY_CURRENT_USER\controlpanel\notifications]
    “MuteSoundOnClose”=dword:1
     
    [HKEY_CURRENT_USER\ControlPanel\Notifications]
    "AlertInterrupt"=dword:00000001.

    Here is what was reported to me regarding "AlertInterrupt":

    This issue was seen on your setup due to large number of notifications your application is creating and playing continuously. Due to architecture of the shell notifications, each notification is played in separate sound script and the script thread does not exit immediately after sound is played. This is causing the OOM behavior you are seeing on your devices. With AlertInterrupt registry keys, previous event notifications threads will be stopped before starting a new one and that is resolving this issue for you. This registry key is documented under “Phone Registry Settings” topic in WM OEM documentation.

    Here is the info on "MuteSoundOnClose":

    MuteSoundOnClose registry key is used to send WAV_CLOSE to sound script after the notification bubble is dismissed by the user.  This is useful to stop notification sound in case when notification sound is long and user has already dismissed the notification.

    This was not documented.  MS said they would put in a documentation request.

    So, This solved my case and I hope it helps someone else...