You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

71 lines
2.9 KiB

  1. using System;
  2. using System.Collections;
  3. using System.Runtime.InteropServices;
  4. using System.IO;
  5. using System.Text;
  6. using Microsoft.Win32.SafeHandles;
  7. namespace Windows
  8. {
  9. class GuiConsole
  10. {
  11. public static void CreateConsole()
  12. {
  13. if (hasConsole)
  14. return;
  15. if (oldOut == IntPtr.Zero)
  16. oldOut = GetStdHandle( -11 );
  17. if (! AllocConsole())
  18. throw new Exception("AllocConsole() failed");
  19. conOut = CreateFile( "CONOUT$", 0x40000000, 2, IntPtr.Zero, 3, 0, IntPtr.Zero );
  20. if (! SetStdHandle(-11, conOut))
  21. throw new Exception("SetStdHandle() failed");
  22. StreamToConsole();
  23. hasConsole = true;
  24. }
  25. public static void ReleaseConsole()
  26. {
  27. if (! hasConsole)
  28. return;
  29. if (! CloseHandle(conOut))
  30. throw new Exception("CloseHandle() failed");
  31. conOut = IntPtr.Zero;
  32. if (! FreeConsole())
  33. throw new Exception("FreeConsole() failed");
  34. if (! SetStdHandle(-11, oldOut))
  35. throw new Exception("SetStdHandle() failed");
  36. StreamToConsole();
  37. hasConsole = false;
  38. }
  39. private static void StreamToConsole()
  40. {
  41. Stream cstm = Console.OpenStandardOutput();
  42. StreamWriter cstw = new StreamWriter( cstm, Encoding.Default );
  43. cstw.AutoFlush = true;
  44. Console.SetOut( cstw );
  45. Console.SetError( cstw );
  46. }
  47. private static bool hasConsole = false;
  48. private static IntPtr conOut;
  49. private static IntPtr oldOut;
  50. [DllImport("kernel32.dll", SetLastError=true)]
  51. private static extern bool AllocConsole();
  52. [DllImport("kernel32.dll", SetLastError=false)]
  53. private static extern bool FreeConsole();
  54. [DllImport("kernel32.dll", SetLastError=true)]
  55. private static extern IntPtr GetStdHandle( int nStdHandle );
  56. [DllImport("kernel32.dll", SetLastError=true)]
  57. private static extern bool SetStdHandle(int nStdHandle, IntPtr hConsoleOutput);
  58. [DllImport("kernel32.dll", CharSet=CharSet.Auto, SetLastError=true)]
  59. private static extern IntPtr CreateFile(
  60. string fileName,
  61. int desiredAccess,
  62. int shareMode,
  63. IntPtr securityAttributes,
  64. int creationDisposition,
  65. int flagsAndAttributes,
  66. IntPtr templateFile );
  67. [DllImport("kernel32.dll", ExactSpelling=true, SetLastError=true)]
  68. private static extern bool CloseHandle(IntPtr handle);
  69. }
  70. }