Posted By

jimfred on 09/04/09


Tagged


Versions (?)

Who likes this?

4 people have marked this snippet as a favorite

umang_nine
khouser
skivsoft
danfinrud55


C#, single-instance-check using mutex. Implements a static function to be called in Program::Main().


 / Published in: C#
 

URL: http://www.hanselman.com/blog/TheWeeklySourceCode31SingleInstanceWinFormsAndMicrosoftVisualBasicdll.aspx

Scott Hanselman describes a method of using VB libraries to handle single-instance checking to prevent multiple instances of an app from starting. A mutex seems to be a simpler solution.\r\n\r\nAdd this class as a sibling to Main and then, inside Main, call this static member: SingleInstanceCheck.Check();

  1. Example usage:
  2. static void Main()
  3. {
  4. SingleInstanceCheck.Check();
  5. ...
  6.  
  7.  
  8.  
  9. Implementation:
  10.  
  11. /// <summary>
  12. /// This checks for another instance of an app.
  13. /// Use inside Main() by calling SingleInstanceCheck.Check();
  14. /// Include this class as a sibling to Main's class.
  15. /// If another instance of the app is detected,
  16. /// - A message box appears.
  17. /// - 'this' instance calls Exit.
  18. /// </summary>
  19. /// <example>
  20. /// static void Main()
  21. /// {
  22. /// MyApp.SingleInstanceCheck.Check();
  23. /// Application.EnableVisualStyles();
  24. /// Application.SetCompatibleTextRenderingDefault(false);
  25. /// Application.Run(new Form1());
  26. /// }
  27. /// </example>
  28. public static class SingleInstanceCheck
  29. {
  30. [DllImport("user32.dll")]
  31. [return: MarshalAs(UnmanagedType.Bool)]
  32. static extern bool SetForegroundWindow(IntPtr hWnd);
  33.  
  34. static public void Check()
  35. {
  36. // http://snipplr.com/view/19272/ - C#, single-instance-check using mutex
  37. // http://iridescence.no/post/CreatingaSingleInstanceApplicationinC.aspx
  38. bool isOwnedHere = false;
  39. appStartMutex = new System.Threading.Mutex(
  40. true,
  41. Application.ProductName,
  42. out isOwnedHere
  43. );
  44.  
  45. if (!isOwnedHere) // if owned by other process.
  46. {
  47. string message = string.Format("There is already a copy of the application {0} running.\n\nClick cancel to exit.", Application.ProductName);
  48.  
  49. DialogResult x = MessageBox.Show(message, Application.ProductName + " already running", MessageBoxButtons.OKCancel);
  50.  
  51. if (x == DialogResult.Cancel) // Cancel, but show the already-existing process.
  52. {
  53. Process me = Process.GetCurrentProcess();
  54. foreach (Process process in Process.GetProcessesByName(me.ProcessName)) // Debug note: Set Enable the Visual Studio Hosting Process = false.
  55. {
  56. if (process.Id != me.Id) // If the ProcessName matches but the Id doesn't, it's another instance of mine.
  57. {
  58. SetForegroundWindow(process.MainWindowHandle);
  59. break;
  60. }
  61. }
  62. Environment.Exit(0); // This will kill my instance.
  63. }
  64. }
  65. }
  66.  
  67. // volatile is intended to prevent GC. Otherwise, GC.KeepAlive(appStartMutex) might be needed.
  68. // This appears to be a concern in In release builds but not debug builds.
  69. static volatile System.Threading.Mutex appStartMutex;
  70.  
  71. }

Report this snippet  

You need to login to post a comment.