locked
Memory Leak with BitmapEncoder->SetPixelData(..., Platform::Array<BYTE>^)??

    Question

  • Any one observed memory leak with the function. I am allocating memory for the Platform::Array when I pass it to 'SetPixelData' it is not getting released. When I run this in a loop, I can clearly see memory build up.

    Any workaround for this?

    Thanks

    __PB

    Monday, March 26, 2012 6:43 PM

All replies

  • Hi,

    Please share concrete code snippets and memory allocation graph related to this function call for further analysis. Memory leak depends on how you allocate and release memory in your context.


    Best wishes,


    Robin [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    Tuesday, March 27, 2012 1:45 PM
    Moderator
  • Robin

            Thanks for your reply. If you look at the signature of the function it takes in "Platform::Array<BYTE>^" as a parameter. All I do is create something like Platform::Array<BYTE>^ byteArray = ref new ....  I pass this to 'SetPixelData of BitmapEncoder'. Since this is managed C++ code I expect it to be garbage collected, but I do see memory growth and eventually out of memory exception in my APP.

            For complete code look at my other post Issue with File Handle. In this code almost towards the end of it I allocate memory for the Byte Array etc. Let me know if you find issue with the code.

    Thanks

    PB

    Tuesday, March 27, 2012 4:25 PM
  • Hi,

    When you use "ref new" to create object, the object is NOT garbage collected. It's different from "gc new". Otherwise, you need not to call delete explicitly on the object. It will be destroyed deterministically when the last remaining copy of it goes out of scope. It means that its lifetime is controlled by referencing count mechanism. At the lowest level, it is basically a COM object owned by a smart pointer.

    So the memory growth is probably not caused by memory leak. You can try to provide better algorithm to avoid out of memory exception in your code.

    Please refer to Windows Runtime objects and ref new for more details.


    Best wishes,


    Robin [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    Wednesday, March 28, 2012 9:30 AM
    Moderator
  • Thanks Robin,

            Got the 'ref new' stuff. Still I think my 'ref new' object is passed to the 'SetPixelData(...)' it is not releasing the reference count. The reason for my suspicion is, this is the only big chunk of memory I am allocating and passing. When I just allocate this memory and do not pass it to 'SetPixelData' I do not see the memory growth.

            With my code I do see memory growth, I am using 'smart pointers etc'. What do you mean by 'better algorithm' to avoid memory growth? Can you give some more tips so that I can figure out exactly what's going on there.

    Thanks

    PB

    Wednesday, March 28, 2012 4:24 PM
  • Hi PB,

    Are you flushing the BitmapEncoder by calling BitmapEncoder->FlushAsync()? I think this should save the data from each pixel buffer and then release references to those obects.

    Wednesday, March 28, 2012 9:16 PM
  • Jason,

          I do flush the BitmapEncoder using FlushAsync, in fact I can see changes to my pictures after FlushAsync. But memory never get released. I run my function in a loop for on 30 pictures which are 3.5k x 2.5k pixels (approx) each. I start with a 1.9GB RAM and it goes to 2.5GB and then never returns back to that level (1.9GB). When I try to rerun this loop again I get out of memory exception.

          You can view my code Issue with File Handle here, it is a big function, but look towards the end of it you will find 'FlushAsync' call.

          I looked at my code again, as far as I know there are two places I have huge chunk of memory, one is from IWicBitMapLock object (I think I do not have control over this chunk), the other is Platform::Array<BYTE>^ that I pass to SetPixelData(...).

          If you need fully working test case let me know, I can share my solution and other code.

    Thank you very much for the help

    PB


    • Edited by __PB Thursday, March 29, 2012 4:06 AM
    Thursday, March 29, 2012 4:03 AM
  • I think you may need to delete the BitmapEncoder object. It looks like you are successfully releasing the file stream that way, so I think it makes sense to release the BitmapEncoder that way. Have you tried that?
    Thursday, March 29, 2012 5:51 AM
  • Jason,

           Thank you, I did try deleting 'BitMapEncoder' using 'delete encoder' even though it did not make sense to me. It did NOT work. I kind of learned that with consumer preview build you can delete some objects, but I think BitMapEncoder is not one of those types.

           I think the problem is with reference counting, objects are getting deleted except the big chunk that is passed to SetPixelData.

    Thank you

    PB

    Thursday, March 29, 2012 6:46 AM
  • I am looking into this further and will let you know when I find out something.
    Friday, March 30, 2012 5:08 AM
  • PB,

    Have you looked at the PixelDataProvider class? http://msdn.microsoft.com/en-us/library/windows/apps/windows.graphics.imaging.pixeldataprovider.aspx

    I am told this class correctly releases memory after opening an image stream.

    I am still looking into the memory issue and hope to have something on it soon.

    Friday, March 30, 2012 9:22 PM
  • Jason,

           Will play with PixelDataProvider and let you know.

           If BitmapEncoder releases the memory, then it may be related to async stuff. Thanks for looking into this.

    PB

    Monday, April 2, 2012 3:49 PM
  • Not a problem.

    I was also told that since you are already using Direct2D to open and manipulate the image file, then you can just use Direct2D to encode it instead of using the WinRT wrapper class. That may help simplify your code a little.

    Here is a sample that looks like it does this: http://code.msdn.microsoft.com/windowsapps/SaveAsImageFile-68073cb0

    Monday, April 2, 2012 6:20 PM
  • I tried doing Direct2D encode, but got into some other issues which I could not figure out the reason. Here is my other forum post that describes the issue (My Other issue). I agree with pure Direct2D code looks much neater, but there is an issue with File Creation etc, when using Direct2D I was not able to create files in standard folder (pictures, videos etc). I had to create a file in App temporary folder and copy it to standard folders after the processing is done (if possible take a look at my other post you can see what I am doing there).

    Thanks

    PB


    • Edited by __PB Tuesday, April 3, 2012 3:54 PM
    Tuesday, April 3, 2012 3:53 PM
  • I have memory leak with BitmapEncoder Save method in C#... Is there a solution?
    Wednesday, March 13, 2013 4:47 PM