title: Access Violation with P/Invoke SendMessage and Message.GetLParam
body: <p>I get an <strong>intermittent</strong> error when calling Message.GetLParam, getting messages sent between processes.
  I have two processes, both written in C# (.Net 3.5). I am using the Win32 function SendMessage() to send data from one process (the source) to the other (the target). The target process's main window (it's a Windows Forms app) overrides the WndProc() function to receive messages.
  The source process locates the other by using the Process.GetProcessesByName() function, then using the Process.MainWindowHandle to get the window handle that I want to send the message to. The code of the source looks like this:</p>
  
  <pre><code>Process[] procs = Process.GetProcessesByName("MyTargetProcess");
  if (procs != null 
      &amp;&amp; procs.Length &gt; 0)
  {
      IntPtr win = procs[0].MainWindowHandle;
      var someData = new Win32.COPYDATASTRUCT   // This is a struct that I defined
      {
      // Initialize fields of the struct
      };
      Win32.SendMessage(win,
          Win32.MyMsgCode,    // my custom message
          IntPtr.Zero,    // wParam = 0
          ref someData);
  }
  </code></pre>
  
  <p>The target process code looks like this:</p>
  
  <pre><code>protected override void WndProc(ref System.Windows.Forms.Message m)
  {
      if (m.Msg == Win32.MyMsgCode)
      {
      Win32.COPYDATASTRUCT ds;
          try
          {
              ds = (Win32.COPYDATASTRUCT)m.GetLParam(typeof(Win32.COPYDATASTRUCT));
          }
          catch (Exception ex)
          {
              log.ErrorFormat("Got exception in WndProc", ex);
          }
          // Do something with the message
          ....
  }
  </code></pre>
  
  <p>Win32 is a static class I defined that gets all my P/Invoke definitions.
  I do not understand why I am catching an AccessViolationException in WndProc.
  Does anybody have an idea why? and why it only happens some of the time?</p>
  
  <p>Thanks for your attention!</p>
  
  <p>-------------------------------- EDIT ------------------------------------------
  Another thing that baffles me: the COPYDATASTRUCT is declared as</p>
  
  <pre><code>public static readonly int WM_COPYDATA = 0x004a;
  [StructLayout(LayoutKind.Sequential)]
  public struct COPYDATASTRUCT
  {
      // Specifies data to be passed to the receiving application.
      public string dwData;
      // Specifies the size, in bytes, of the data pointed to by the lpData member. 
      public int cbData;
      // Pointer to data to be passed to the receiving application. This member can be NULL.                 
      public string lpData;
  }
  </code></pre>
  
  <p>It is initialized like this:</p>
  
  <pre><code>string payload = " some data ";
  var someData = new Win32.COPYDATASTRUCT   // This is a struct that I defined
  {
      dwData = "bogusData",
      cbData = sizeof(char) * payload.Length,
      lpData = payload
  };
  </code></pre>
  
  <p>And in target code, I always receive dwData = null.</p>
  
  <p>----------------------- 2nd edit --------------------------------------
  I just tried with adding the zero terminator, and I still get the error. 
  If I change the marshalling code to do my own marshalling as in </p>
  
  <pre><code>IntPtr pcds = Marshal.AllocHGlobal(Marshal.SizeOf(someData));
  Marshal.StructureToPtr(someData, pcds, true);
  Win32.SendMessage(win, (uint)Win32.WM_COPYDATA, IntPtr.Zero, pcds);
  </code></pre>
  
  <p>Then the error happens ALL THE TIME! However, if I repeat the GetLParam() call in the catch block, it succeeds almost all the time, on the 2nd try.</p>