none
RDP Client (IMsRdpClientNonScriptable) SendKey Error RRS feed

  • Question

  • Im trying to sendkeys to an remotedesktop using the interface IMsRdpClientNonScriptable (more info here IMsRdpClientNonScriptable::SendKeys Method)
    But somehow the AXIMP.exe fails to make the correct SendKeys method as defined by microsoft (see link above).
    microsoft states that the sendkeys method should be native like this:

    HRESULT SendKeys(
     [in] LONG numKeys,
     [in] VARIANT_BOOL *pbArrayKeyUp,
     [in] LONG *plKeyData
    );
    
    

    I would argue that this correctly translated to C# would be like this:

    int SendKeys(int numKeys, ref bool[] pbArrayKeyUp, ref int[] plKeyData)
    

    But the AXIMP.EXE translates this into this:

    void SendKeys(int numKeys, ref bool pbArrayKeyUp, ref int plKeyData);
    

    I cant seem to get this to work. so I've been searing the web for a solution without success!!
    I found that another guy had the same issue aximp.exe generates incorrect wrapper method for IMsRdpClientNonScriptable::SendKeys but no solution was found here either. hmmm

    OK so here ones and for all; "Does anyone have a working C# or VB.Net code that can send key strokes to the remote desktop. ???"

    This code fails with the following (HRESULT E_FAIL at MSTSCLib.IMsRdpClientNonScriptable.SendKeys(Int32 numKeys, Boolean& pbArrayKeyUp, Int32& plKeyData)):

        public void SendKeys(IMsRdpClientNonScriptable rdpNonScript, Keys[] keys)
        {
          try
          {
            if (null != rdpNonScript)
            {
              int arrayIndex = 0;
              int[] plKeyData = new int[20];
              bool[] pbArrayKeyUp = new bool[20];
              for (int i = 0; i < keys.Length; i++)
              {
                plKeyData[arrayIndex] = (int)keys[i];
                pbArrayKeyUp[arrayIndex] = false;
                arrayIndex++;
              }
              for (int i = keys.Length - 1; i >= 0; i--)
              {
                plKeyData[arrayIndex] = (int)keys[i];
                pbArrayKeyUp[arrayIndex] = true;
                arrayIndex++;
              }
    
              rdpNonScript.SendKeys(keys.Length * 2, ref pbArrayKeyUp[0], ref plKeyData[0]);
            }
          }
          catch (Exception ex)
          {
            MessageBox.Show(ex.Message + Environment.NewLine + Environment.NewLine + ex.StackTrace);
          }
        }
    

    With great code, comes great complexity, so keep it simple stupid...
    • Moved by Figo Fei Wednesday, September 15, 2010 5:33 AM (From:Visual C# General)
    Tuesday, September 14, 2010 10:01 AM

Answers

All replies

  • Moved to CLR forum for interop problem.

    Thanks for your understanding.


    Figo Fei
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com 


    Please remember to mark the replies as answers if they help and unmark them if they provide no help.
    Wednesday, September 15, 2010 5:32 AM
  •  

    Hi Paw,

     

    I'm sorry, but as Alvin mentioned in the post, we can disassemble the generated interop dll into an il file, then modify il instructions manually:

    change  "[in] bool& pbArrayKeyUp," to "[in] bool[] marshal([+0]) pbArrayKeyUp,",

    change  "[in] int32& plKeyData) runtime managed internalcall" to "[in] int32[] marshal([+0]) plKeyData) runtime managed internalcall"


    Sincerely,
    Eric
    MSDN Subscriber Support in Forum
    If you have any feedback of our support, please contact msdnmg@microsoft.com.
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.
    Welcome to the All-In-One Code Framework! If you have any feedback, please tell us.
    Thursday, September 16, 2010 8:55 AM
  • Hey Eryang

    Thanks for your reply. I dont know how to modify and IL, so can you point to an article that shows me how to. im pretty good into the DllImport and reflector, so if i have to i could do that way, but that just to me seems like a long way to go, for such a small detail.

     

    regards
    Paw


    With great code, comes great complexity, so keep it simple stupid...
    Thursday, September 16, 2010 10:53 AM
  •  

    Hi Paw,

    We can use ILDasm.exe to disassemble an assembly into an IL file, modify the IL file and then re-assemble the IL file into an assembly using ILAsm.exe, this blog shows how to use ILDasm and ILAsm, you may want to have a read.


    Sincerely,
    Eric
    MSDN Subscriber Support in Forum
    If you have any feedback of our support, please contact msdnmg@microsoft.com.
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.
    Welcome to the All-In-One Code Framework! If you have any feedback, please tell us.
    • Marked as answer by Paw Jershauge Friday, September 17, 2010 6:28 AM
    Friday, September 17, 2010 12:54 AM
  • Thanks ones again Eryang!

    I will try my best to get this to work. if not, i know where to find you ;o)

    Best regards

    Paw


    With great code, comes great complexity, so keep it simple stupid...
    Friday, September 17, 2010 6:29 AM
  • Hi again Eryang

    So now I have decompiled and compiled the Interop.MSTSCLib.dll so it has the correct sendkeys method implemented eg:

    void SendKeys(int numKeys, bool[] pbArrayKeyUp, int[] plKeyData);

    but i still get the error:

    Message: the call to an COM-component returned the error HRESULT E_FAIL. (please note that this is an translated message as im not running the framework in english ;o))
    ErrorCode: -2147467259
    Stack
       at MSTSCLib.IMsRdpClientNonScriptable.SendKeys(Int32 numKeys, Boolean[] pbArrayKeyUp, Int32[] plKeyData)
       at RDPTest.Form1.button1_Click(Object sender, EventArgs e) in Form1.cs:linje 51
       at System.Windows.Forms.Control.OnClick(EventArgs e)
       at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
       at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
       at System.Windows.Forms.Control.WndProc(Message& m)
       at System.Windows.Forms.ButtonBase.WndProc(Message& m)
       at System.Windows.Forms.Button.WndProc(Message& m)
       at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
       at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
       at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
       at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(Int32 dwComponentID, Int32 reason, Int32 pvLoopData)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
       at RDPTest.Program.Main() in Program.cs:linje 17
       at System.AppDomain._nExecuteAssembly(Assembly assembly, String[] args)
       at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
       at System.Threading.ThreadHelper.ThreadStart()

    When i do this:

    SendKeys(6, new bool[] { false, false, false, true, true, true }, new int[] { (int)Keys.ControlKey, (int)Keys.Alt, (int)Keys.End, (int)Keys.End, (int)Keys.Alt, (int)Keys.ControlKey }); 
    
    

    Do u have any suggestions ???

    • Edited by Paw Jershauge Friday, September 17, 2010 8:46 AM Fault in the translation of the HTML code implemented by Microsoft
    Friday, September 17, 2010 8:42 AM
  • Hi again Eryang

    So now I have decompiled and compiled the Interop.MSTSCLib.dll so it has the correct sendkeys method implemented eg:

    void SendKeys(int numKeys, bool[] pbArrayKeyUp, int[] plKeyData);
    

    but i still get the error:

    Message: the call to an COM-component returned the error HRESULT E_FAIL. (please note that this is an translated message as im not running the framework in english ;o))
    ErrorCode: -2147467259
    Stack
       at MSTSCLib.IMsRdpClientNonScriptable.SendKeys(Int32 numKeys, Boolean[] pbArrayKeyUp, Int32[] plKeyData)
     

    Do u have any suggestions ???

    Hi, i had the same problem. You have to set this setting before connecting:

    rdp.AdvancedSettings.allowBackgroundInput = 1;

    I posted my solution in this thread:

    http://social.msdn.microsoft.com/Forums/windowsdesktop/en-US/9095625c-4361-4e0b-bfcf-be15550b60a8/imsrdpclientnonscriptablesendkeys?forum=windowsgeneraldevelopmentissues&prof=required

    I hope it helps


    • Edited by 0x6b6f6e737469 Wednesday, September 10, 2014 5:01 PM typo
    • Proposed as answer by 0x6b6f6e737469 Wednesday, September 10, 2014 9:33 PM
    Wednesday, September 10, 2014 5:00 PM