S
S
stronciy2011-05-11 17:34:52
.NET
stronciy, 2011-05-11 17:34:52

Get in .NET string from C++ dll

SW. specialists need help, two weeks are thrown out of life, so

there is a dll written in C ++ with very simple content. Question, how to call this function in .NET and get the result of its work? The question is not as simple as it seems, if you do return("bla bla bla") in C ++, then everything works fine, as soon as stdout appears, then nightmares begin. As a result of digging the network through Google, I found almost what I needed , they work as it should, but !!! works once, when you call it again, it will hang ... Thank you in advance for your help.

void IsolatedFunction()
{

cout << "Redirected string1" << endl << "Redirected string2" << endl;

}





Answer the question

In order to leave comments, you need to log in

2 answer(s)
E
ertaquo, 2011-05-11
@ertaquo

Try not to create an instance of AnonymousPipeServerStream several times, but create it once and call SetStdHandle once, then calling server.Flush();, then the function from the dll and reading from the pipe. In general, something like this (I did not check the performance):

Copy Source | Copy HTML
  1. public static class ConsoleOutRedirector
  2. {
  3.     #region Constants
  4.  
  5.     private const Int32 STD_OUTPUT_HANDLE = -11;
  6.  
  7.     #endregion
  8.  
  9.     #region Externals
  10.  
  11.     [DllImport("Kernel32.dll")]
  12.     extern static Boolean SetStdHandle(Int32 nStdHandle, SafeHandleZeroOrMinusOneIsInvalid handle);
  13.     [DllImport("Kernel32.dll")]
  14.     extern static SafeFileHandle GetStdHandle(Int32 nStdHandle);
  15.  
  16.     #endregion
  17.  
  18.     #region Variables
  19.  
  20.     private static AnonymousPipeServerStream server = new AnonymousPipeServerStream(PipeDirection.Out);
  21.     private static client = new AnonymousPipeClientStream(PipeDirection.In, server.ClientSafePipeHandle);
  22.     private static bool First = true;
  23.  
  24.     #endregion
  25.  
  26.     #region Methods
  27.  
  28.     public static String GetOutput(Action action)
  29.     {
  30.         Debug.Assert(action != null);
  31.  
  32.         using (server)
  33.         {
  34.             if (First)
  35.             {
  36.                 var defaultHandle = GetStdHandle(STD_OUTPUT_HANDLE);
  37.  
  38.                 Debug.Assert(!defaultHandle.IsInvalid);
  39.                 Debug.Assert(SetStdHandle(STD_OUTPUT_HANDLE, server.SafePipeHandle));
  40.                 try
  41.                 {
  42.                     action();
  43.                 }
  44.                 finally
  45.                 {
  46.                     Debug.Assert(SetStdHandle(STD_OUTPUT_HANDLE, defaultHandle));
  47.                 }
  48.  
  49.                 First = false;
  50.             }
  51.  
  52.             server.Flush();
  53.             client.Flush();
  54.  
  55.             using (client)
  56.             {
  57.                 using (var reader = new StreamReader(client))
  58.                 {
  59.                     using (var writer = new StringWriter())
  60.                     {
  61.                         while (reader.Peek() != -1)
  62.                         {
  63.                             writer.Write(Convert.ToChar(reader.Read()));
  64.                         }
  65.                         return writer.ToString();
  66.                     }
  67.                 }
  68.             }
  69.         }
  70.     }
  71.  
  72.     #endregion
  73. }
  74.  

E
ertaquo, 2011-05-11
@ertaquo

And if something like this ( source ), without problems with SetStdHandle and pipes? Unfortunately, I know C# pretty badly, so I can only advise at random =\

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question