title: Anyway to know when a pooled thread (or ThreadStatic member) is destroyed?
body: <p>I need to add a third party component to one of our products (which is a windows service that can run 24/7).<br>
  The 3PC is a .net library that sits on some hard core C++ loveliness for manipulating images.<br>
  The 3PC requires that <em>Initialize</em> and <em>Teardown</em> routines are called for every thread it runs on.<br>
  This is fine where we use it in our older software, but this product was written with the .Net thread pool, and pooled workers will exercise the 3PC. I can't figure out how to safely call the <em>Initialize</em> and <em>Teardown</em> routines.</p>
  
  <p>The closest I got was when initializing a ThreadStatic member, to call the 3PC <code>Initialize</code> method, however I can't manage to call the <code>Teardown</code> on the same thread the <code>Initialize</code> was called on.</p>
  
  <p>If I wrap the <code>Initialize</code> and <code>Teardown</code> in an object, with the <code>Teardown</code> called in the objects Finalize method, then the <code>Teardown</code> will be called by the GC's own Finalize thread, not the <em>thread</em> the object is <em>static</em> to (not to mention the fact that there's no guarantee the Finalizer will ever run).</p>
  
  <p>Obviously I'm worried about leaked resources as the the thread pool <em>manages</em> threads under the covers, <strong>I have no idea if or when threads will be destroyed or created</strong>, so I've no idea how much the Service could leak over a period of time.</p>
  
  <p>Anyone any ideas? Anything I've missed? Anything else to try?<br>
  Thanks</p>
  
  <p><strong>Update</strong>  </p>
  
  <p>Q: <em>What does Teardown do?</em>  </p>
  
  <p>I'm assuming it "Releases some memory", but I honestly have no idea. I tried splunking through the assembly with Reflector but it quickly drops from IL into native machine code. I'm going on the (3rd) party line that this must be done. </p>
  
  <p>It definitely is a subsystem tear down thing.</p>
  
  <p>Also, several years ago we discovered a bug around this component in another Product. The Initializer wasn't being called for every thread which resulted in some very rarely seen <em>Undefined behaviour</em>.</p>