title: Invoke callback into VB6 from native C DLL
body: <p>I am trying to get a native C function to invoke a callback in a VB6 application.  In VB, the code looks like this:</p>
  
  
  
  <pre><code>Private Declare Sub StartUp Lib "library.dll" (ByVal cbAddress As Long)
  
  Public Sub MySub
      Call StartUp(AddressOf MyCallback)
  End Sub
  
  Public Sub MyCallback(ByVal str As String)
  ' Use str in UI
  End Sub
  </code></pre>
  
  <p>When I run this from the VB6 IDE everything works great: the callback is invoked and I can use the <code>str</code> parameter no problem.  However, when I compile the VB6 application into an exe, the application will crash when the callback is invoked.  From what I can tell in my Googling it seems this is a threading issue of some sort.  Some people suggest using the Win32 <code>SendMessage</code> to avoid this threading issue somehow.  I can't quite figure out how to do this.  Would I call <code>SendMessage</code> in my callback?  How would I receive this message on the main thread?  Also, how would I pass my string into SendMessage?</p>
  
  <p>Edit: I just found this:
  <a href="https://stackoverflow.com/questions/1239317/vb6-application-works-in-the-ide-but-the-executable-crashes">Vb6 application works in the IDE but the executable crashes</a></p>
  
  <p>However, my initial questions still remain.</p>
  
  <p>Edit2: I should have included in the C code as well.  This is how the callback is defined and called:</p>
  
  
  
  <pre><code>typedef void (__stdcall *FUNCPTR)(BSTR);
  int wslen = MultiByteToWideChar(CP_ACP, 0, cstr, strlen(cstr), 0, 0);
  BSTR bstr = SysAllocStringLen(0, wslen);
  MultiByteToWideChar(CP_ACP, 0, cstr, strlen(cstr), bstr, wslen);
  ((FUNCPTR) _cbAddress)(bstr);
  SysFreeString(bstr);
  </code></pre>
  
  <p>Again, this works fine when invoked from the IDE...</p>