Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. C#
  4. Where do I release my object's expensive resources, if not in the destructor?

Where do I release my object's expensive resources, if not in the destructor?

Scheduled Pinned Locked Moved C#
questioncomsysadminhelpannouncement
14 Posts 6 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • J Offline
    J Offline
    JoeRip
    wrote on last edited by
    #1

    I have an object that creates an expensive COM object as soon as my object's Constructor is called. This COM object is treated as a private field in my object. My object is then responsible releasing that COM object. Not releasing it is expensive and problematic. So I put the release code for the COM object in my object's destructor, assuming my object's destructor would be called as soon as my object was set to NULL or went out of scope. However, this is not the case. My object's destructor is not called until the garbage collector runs. This is a problem. I need my object to release the COM object as soon as it's not needed anymore. If I don't, there are problems with the COM server application - ie, it won't close, etc. How can I insure that my object releases the COM object as soon as my object is set to null, or goes out of scope? Where do I put the COM release code?

    C A 2 Replies Last reply
    0
    • J JoeRip

      I have an object that creates an expensive COM object as soon as my object's Constructor is called. This COM object is treated as a private field in my object. My object is then responsible releasing that COM object. Not releasing it is expensive and problematic. So I put the release code for the COM object in my object's destructor, assuming my object's destructor would be called as soon as my object was set to NULL or went out of scope. However, this is not the case. My object's destructor is not called until the garbage collector runs. This is a problem. I need my object to release the COM object as soon as it's not needed anymore. If I don't, there are problems with the COM server application - ie, it won't close, etc. How can I insure that my object releases the COM object as soon as my object is set to null, or goes out of scope? Where do I put the COM release code?

      C Offline
      C Offline
      Christian Graus
      wrote on last edited by
      #2

      You can't. You can use the dispose/finalise mechanism to let your users call Dispose to close it, or for finalise to do it when the object is GC, if dispose was not called. Welcome to garbage collection.

      Christian Graus No longer a Microsoft MVP, but still happy to answer your questions.

      J 2 Replies Last reply
      0
      • C Christian Graus

        You can't. You can use the dispose/finalise mechanism to let your users call Dispose to close it, or for finalise to do it when the object is GC, if dispose was not called. Welcome to garbage collection.

        Christian Graus No longer a Microsoft MVP, but still happy to answer your questions.

        J Offline
        J Offline
        JoeRip
        wrote on last edited by
        #3

        Well, that's painful. Thanks for the quick answer, though.

        1 Reply Last reply
        0
        • C Christian Graus

          You can't. You can use the dispose/finalise mechanism to let your users call Dispose to close it, or for finalise to do it when the object is GC, if dispose was not called. Welcome to garbage collection.

          Christian Graus No longer a Microsoft MVP, but still happy to answer your questions.

          J Offline
          J Offline
          JoeRip
          wrote on last edited by
          #4

          This suggests, then, that I shouldn't even bother putting the COM release code in my destructor, right? The COM object will be released anyway when my object gets GC'ed, correct?

          G C S 3 Replies Last reply
          0
          • J JoeRip

            This suggests, then, that I shouldn't even bother putting the COM release code in my destructor, right? The COM object will be released anyway when my object gets GC'ed, correct?

            G Offline
            G Offline
            Guffa
            wrote on last edited by
            #5

            Any object that uses any unmanaged resources should implement the IDisposable interface, so that the resources can be released in a controlled manner. You have no control over when the object is garbage collected, and there is actually no guarantee that the object is ever garbage collected.

            Despite everything, the person most likely to be fooling you next is yourself.

            J 1 Reply Last reply
            0
            • G Guffa

              Any object that uses any unmanaged resources should implement the IDisposable interface, so that the resources can be released in a controlled manner. You have no control over when the object is garbage collected, and there is actually no guarantee that the object is ever garbage collected.

              Despite everything, the person most likely to be fooling you next is yourself.

              J Offline
              J Offline
              JoeRip
              wrote on last edited by
              #6

              "Yes, but then I wouldn't be watching TV. You can see my dilemma, right?" Sigh.

              F 1 Reply Last reply
              0
              • J JoeRip

                This suggests, then, that I shouldn't even bother putting the COM release code in my destructor, right? The COM object will be released anyway when my object gets GC'ed, correct?

                C Offline
                C Offline
                Christian Graus
                wrote on last edited by
                #7

                Wrong. Non-managed resources, need to be dealt with in your code. The idea is you impliment IDisposable, so the user can call Dispose to force cleanup, but write code that does the cleanup if Dispose has not been called.

                Christian Graus No longer a Microsoft MVP, but still happy to answer your questions.

                1 Reply Last reply
                0
                • J JoeRip

                  I have an object that creates an expensive COM object as soon as my object's Constructor is called. This COM object is treated as a private field in my object. My object is then responsible releasing that COM object. Not releasing it is expensive and problematic. So I put the release code for the COM object in my object's destructor, assuming my object's destructor would be called as soon as my object was set to NULL or went out of scope. However, this is not the case. My object's destructor is not called until the garbage collector runs. This is a problem. I need my object to release the COM object as soon as it's not needed anymore. If I don't, there are problems with the COM server application - ie, it won't close, etc. How can I insure that my object releases the COM object as soon as my object is set to null, or goes out of scope? Where do I put the COM release code?

                  A Offline
                  A Offline
                  Alan Balkany
                  wrote on last edited by
                  #8

                  After nulling all references to the COM object, you can call GC.Collect () to force garbage collection. See ms-help://MS.VSCC.v80/MS.MSDN.v80/MS.NETDEVFX.v20.en/cpref2/html/O_T_System_GC_Collect.htm

                  J S 2 Replies Last reply
                  0
                  • J JoeRip

                    "Yes, but then I wouldn't be watching TV. You can see my dilemma, right?" Sigh.

                    F Offline
                    F Offline
                    Frank Horn
                    wrote on last edited by
                    #9

                    I have this problem with Enterprise Architect (modelling software from Sparx). The program exposes a COM automation interface for add ins, and when you write an add in with C# it can happen that the application refuses to close because your add in's COM reference which has not been garbage collected. Sparx recommends to call GC.Collect() and GC.WaitForPendingFinalizers(). Maybe you can do this in your Dispose() method after releasing the COM reference. It's often said one should not call the GC methods for performance reasons, but when it's about releasing a big COM object they're probably justified.

                    1 Reply Last reply
                    0
                    • A Alan Balkany

                      After nulling all references to the COM object, you can call GC.Collect () to force garbage collection. See ms-help://MS.VSCC.v80/MS.MSDN.v80/MS.NETDEVFX.v20.en/cpref2/html/O_T_System_GC_Collect.htm

                      J Offline
                      J Offline
                      JoeRip
                      wrote on last edited by
                      #10

                      yes, that's how I release the COM object in my destructor. But that's not the question here. The point is, unless my client (who created my object) calls Garbage Collection explicitly, my destructor won't be called in a timely fashion.

                      A S 2 Replies Last reply
                      0
                      • J JoeRip

                        yes, that's how I release the COM object in my destructor. But that's not the question here. The point is, unless my client (who created my object) calls Garbage Collection explicitly, my destructor won't be called in a timely fashion.

                        A Offline
                        A Offline
                        Alan Balkany
                        wrote on last edited by
                        #11

                        Maybe you could figure out when the client is done with the object. Is there a method in the object that is called as a final operation? If so, you could invoke garbage collection at that point. Or (depending on the particular usage pattern) you might be able to detect when the client is X seconds away from not needing the object, and set a timer to force garbage collection after X+1 seconds.

                        1 Reply Last reply
                        0
                        • A Alan Balkany

                          After nulling all references to the COM object, you can call GC.Collect () to force garbage collection. See ms-help://MS.VSCC.v80/MS.MSDN.v80/MS.NETDEVFX.v20.en/cpref2/html/O_T_System_GC_Collect.htm

                          S Offline
                          S Offline
                          Scott Dorman
                          wrote on last edited by
                          #12

                          Calling GC.Collect() directly is generally a bad idea.

                          Scott Dorman

                          Microsoft® MVP - Visual C# | MCPD President - Tampa Bay IASA [Blog][Articles][Forum Guidelines]


                          Hey, hey, hey. Don't be mean. We don't have to be mean because, remember, no matter where you go, there you are. - Buckaroo Banzai

                          1 Reply Last reply
                          0
                          • J JoeRip

                            This suggests, then, that I shouldn't even bother putting the COM release code in my destructor, right? The COM object will be released anyway when my object gets GC'ed, correct?

                            S Offline
                            S Offline
                            Scott Dorman
                            wrote on last edited by
                            #13

                            As Guffa pointed out, the GC has no knowledge of how to release unmanaged memory, which includes COM objects. It expects that your managed class will provide the necessary logic to free those resources during GC by implementing IDisposable.

                            Scott Dorman

                            Microsoft® MVP - Visual C# | MCPD President - Tampa Bay IASA [Blog][Articles][Forum Guidelines]


                            Hey, hey, hey. Don't be mean. We don't have to be mean because, remember, no matter where you go, there you are. - Buckaroo Banzai

                            1 Reply Last reply
                            0
                            • J JoeRip

                              yes, that's how I release the COM object in my destructor. But that's not the question here. The point is, unless my client (who created my object) calls Garbage Collection explicitly, my destructor won't be called in a timely fashion.

                              S Offline
                              S Offline
                              Scott Dorman
                              wrote on last edited by
                              #14

                              JoeRip wrote:

                              The point is, unless my client (who created my object) calls Garbage Collection explicitly, my destructor won't be called in a timely fashion.

                              That's one of the drawbacks to a garbage collected runtime. The idea is that you implement the IDispsoable interface (actually, the Dispose pattern[^]) which tells the GC how to release your unmanaged memory and signals to the caller (client) that they should call Dispose() when they are done using your object. If you need a stronger assurance that your resources get cleaned up then you can implement a finalizer (see the above reference article for issues/concerns about implementing finalizers) and if you absolutely need to guarantee the finalizer gets called you need use a "critical finalizable object" and inherit from CriticalFinalizerObject.

                              Scott Dorman

                              Microsoft® MVP - Visual C# | MCPD President - Tampa Bay IASA [Blog][Articles][Forum Guidelines]


                              Hey, hey, hey. Don't be mean. We don't have to be mean because, remember, no matter where you go, there you are. - Buckaroo Banzai

                              1 Reply Last reply
                              0
                              Reply
                              • Reply as topic
                              Log in to reply
                              • Oldest to Newest
                              • Newest to Oldest
                              • Most Votes


                              • Login

                              • Don't have an account? Register

                              • Login or register to search.
                              • First post
                                Last post
                              0
                              • Categories
                              • Recent
                              • Tags
                              • Popular
                              • World
                              • Users
                              • Groups