2 // ProcessTest.cs - NUnit Test Cases for System.Diagnostics.Process
5 // Gert Driesen (drieseng@users.sourceforge.net)
6 // Robert Jordan <robertj@gmx.net>
8 // (C) 2007 Gert Driesen
12 using System.ComponentModel;
13 using System.Diagnostics;
16 using System.Threading;
17 using System.Runtime.InteropServices;
19 using NUnit.Framework;
21 namespace MonoTests.System.Diagnostics
24 public class ProcessTest
27 public void GetProcessById_MachineName_Null ()
30 Process.GetProcessById (1, (string) null);
32 } catch (ArgumentNullException ex) {
33 Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
34 Assert.IsNotNull (ex.Message, "#3");
35 Assert.IsNotNull (ex.ParamName, "#4");
36 Assert.AreEqual ("machineName", ex.ParamName, "#5");
37 Assert.IsNull (ex.InnerException, "#6");
42 public void GetProcesses_MachineName_Null ()
45 Process.GetProcesses ((string) null);
47 } catch (ArgumentNullException ex) {
48 Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
49 Assert.IsNotNull (ex.Message, "#3");
50 Assert.IsNotNull (ex.ParamName, "#4");
51 Assert.AreEqual ("machineName", ex.ParamName, "#5");
52 Assert.IsNull (ex.InnerException, "#6");
56 [Test] // Covers #26363
57 [NUnit.Framework.Category ("MobileNotWorking")]
58 public void GetProcesses_StartTime ()
60 foreach (var p in Process.GetProcesses ()) {
61 if (!p.HasExited && p.StartTime.Year < 1800)
62 Assert.Fail ("Process should not be started since the 18th century.");
67 public void PriorityClass_NotStarted ()
69 Process process = new Process ();
71 process.PriorityClass = ProcessPriorityClass.Normal;
73 } catch (InvalidOperationException ex) {
74 // No process is associated with this object
75 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#A2");
76 Assert.IsNull (ex.InnerException, "#A3");
77 Assert.IsNotNull (ex.Message, "#A4");
81 Assert.Fail ("#B1:" + process.PriorityClass);
82 } catch (InvalidOperationException ex) {
83 // No process is associated with this object
84 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#B2");
85 Assert.IsNull (ex.InnerException, "#B3");
86 Assert.IsNotNull (ex.Message, "#B4");
91 public void PriorityClass_Invalid ()
93 Process process = new Process ();
95 process.PriorityClass = (ProcessPriorityClass) 666;
97 } catch (InvalidEnumArgumentException ex) {
98 Assert.AreEqual (typeof (InvalidEnumArgumentException), ex.GetType (), "#2");
99 Assert.IsNull (ex.InnerException, "#3");
100 Assert.IsNotNull (ex.Message, "#4");
101 Assert.IsTrue (ex.Message.IndexOf ("666") != -1, "#5");
102 Assert.IsTrue (ex.Message.IndexOf (typeof (ProcessPriorityClass).Name) != -1, "#6");
103 Assert.IsNotNull (ex.ParamName, "#7");
104 Assert.AreEqual ("value", ex.ParamName, "#8");
108 #if MONO_FEATURE_PROCESS_START
110 public void Start1_FileName_Empty ()
112 Process process = new Process ();
113 process.StartInfo = new ProcessStartInfo (string.Empty);
116 process.StartInfo.UseShellExecute = false;
120 } catch (InvalidOperationException ex) {
121 // Cannot start process because a file name has
123 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#A2");
124 Assert.IsNull (ex.InnerException, "#A3");
125 Assert.IsNotNull (ex.Message, "#A4");
129 process.StartInfo.UseShellExecute = true;
133 } catch (InvalidOperationException ex) {
134 // Cannot start process because a file name has
136 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#B2");
137 Assert.IsNull (ex.InnerException, "#B3");
138 Assert.IsNotNull (ex.Message, "#B4");
143 public void Start1_FileName_InvalidPathCharacters ()
146 // on unix, all characters are allowed
147 Assert.Ignore ("Running on Unix.");
149 string systemDir = Environment.GetFolderPath (Environment.SpecialFolder.System);
150 string exe = "\"" + Path.Combine (systemDir, "calc.exe") + "\"";
152 Process process = new Process ();
153 process.StartInfo = new ProcessStartInfo (exe);
156 process.StartInfo.UseShellExecute = false;
157 Assert.IsTrue (process.Start ());
161 process.StartInfo.UseShellExecute = true;
162 Assert.IsTrue (process.Start ());
167 public void Start1_FileName_NotFound ()
169 Process process = new Process ();
170 string exe = RunningOnUnix ? exe = "/usr/bin/shouldnoteverexist"
171 : @"c:\shouldnoteverexist.exe";
173 // absolute path, no shell
174 process.StartInfo = new ProcessStartInfo (exe);
175 process.StartInfo.UseShellExecute = false;
179 } catch (Win32Exception ex) {
180 // The system cannot find the file specified
181 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#A2");
182 Assert.AreEqual (-2147467259, ex.ErrorCode, "#A3");
183 Assert.IsNull (ex.InnerException, "#A4");
184 Assert.IsNotNull (ex.Message, "#A5");
185 Assert.AreEqual (2, ex.NativeErrorCode, "#A6");
188 // relative path, no shell
189 process.StartInfo.FileName = "shouldnoteverexist.exe";
190 process.StartInfo.UseShellExecute = false;
194 } catch (Win32Exception ex) {
195 // The system cannot find the file specified
196 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#B2");
197 Assert.AreEqual (-2147467259, ex.ErrorCode, "#B3");
198 Assert.IsNull (ex.InnerException, "#B4");
199 Assert.IsNotNull (ex.Message, "#B5");
200 Assert.AreEqual (2, ex.NativeErrorCode, "#B6");
204 Assert.Ignore ("On Unix and Mac OS X, we try " +
205 "to open any file (using xdg-open, ...)" +
206 " and we do not report an exception " +
209 // absolute path, shell
210 process.StartInfo.FileName = exe;
211 process.StartInfo.UseShellExecute = true;
215 } catch (Win32Exception ex) {
216 // The system cannot find the file specified
217 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#C2");
218 Assert.AreEqual (-2147467259, ex.ErrorCode, "#C3");
219 Assert.IsNull (ex.InnerException, "#C4");
220 Assert.IsNotNull (ex.Message, "#C5");
221 Assert.AreEqual (2, ex.NativeErrorCode, "#C6");
224 // relative path, shell
225 process.StartInfo.FileName = "shouldnoteverexist.exe";
226 process.StartInfo.UseShellExecute = true;
230 } catch (Win32Exception ex) {
231 // The system cannot find the file specified
232 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#D2");
233 Assert.AreEqual (-2147467259, ex.ErrorCode, "#D3");
234 Assert.IsNull (ex.InnerException, "#D4");
235 Assert.IsNotNull (ex.Message, "#D5");
236 Assert.AreEqual (2, ex.NativeErrorCode, "#D6");
241 public void Start1_FileName_Null ()
243 Process process = new Process ();
244 process.StartInfo = new ProcessStartInfo ((string) null);
247 process.StartInfo.UseShellExecute = false;
251 } catch (InvalidOperationException ex) {
252 // Cannot start process because a file name has
254 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#A2");
255 Assert.IsNull (ex.InnerException, "#A3");
256 Assert.IsNotNull (ex.Message, "#A4");
260 process.StartInfo.UseShellExecute = true;
264 } catch (InvalidOperationException ex) {
265 // Cannot start process because a file name has
267 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#B2");
268 Assert.IsNull (ex.InnerException, "#B3");
269 Assert.IsNotNull (ex.Message, "#B4");
274 public void Start1_FileName_Whitespace ()
276 Process process = new Process ();
277 process.StartInfo = new ProcessStartInfo (" ");
278 process.StartInfo.UseShellExecute = false;
282 } catch (Win32Exception ex) {
283 // The system cannot find the file specified
284 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#2");
285 Assert.AreEqual (-2147467259, ex.ErrorCode, "#3");
286 Assert.IsNull (ex.InnerException, "#4");
287 Assert.IsNotNull (ex.Message, "#5");
288 // TODO: On windows we get ACCESS_DENIED (5) instead of FILE_NOT_FOUND (2) and .NET
289 // gives ERROR_INVALID_PARAMETER (87). See https://bugzilla.xamarin.com/show_bug.cgi?id=44514
290 Assert.IsTrue (ex.NativeErrorCode == 2 || ex.NativeErrorCode == 5 || ex.NativeErrorCode == 87, "#6");
294 [Test] // Start (ProcessStartInfo)
295 public void Start2_FileName_Empty ()
297 ProcessStartInfo startInfo = new ProcessStartInfo (string.Empty);
300 startInfo.UseShellExecute = false;
302 Process.Start (startInfo);
304 } catch (InvalidOperationException ex) {
305 // Cannot start process because a file name has
307 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#A2");
308 Assert.IsNull (ex.InnerException, "#A3");
309 Assert.IsNotNull (ex.Message, "#A4");
313 startInfo.UseShellExecute = true;
315 Process.Start (startInfo);
317 } catch (InvalidOperationException ex) {
318 // Cannot start process because a file name has
320 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#B2");
321 Assert.IsNull (ex.InnerException, "#B3");
322 Assert.IsNotNull (ex.Message, "#B4");
326 [Test] // Start (ProcessStartInfo)
327 public void Start2_FileName_NotFound ()
329 ProcessStartInfo startInfo = new ProcessStartInfo ();
330 string exe = RunningOnUnix ? exe = "/usr/bin/shouldnoteverexist"
331 : @"c:\shouldnoteverexist.exe";
333 // absolute path, no shell
334 startInfo.FileName = exe;
335 startInfo.UseShellExecute = false;
337 Process.Start (startInfo);
339 } catch (Win32Exception ex) {
340 // The system cannot find the file specified
341 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#A2");
342 Assert.AreEqual (-2147467259, ex.ErrorCode, "#A3");
343 Assert.IsNull (ex.InnerException, "#A4");
344 Assert.IsNotNull (ex.Message, "#A5");
345 Assert.AreEqual (2, ex.NativeErrorCode, "#A6");
348 // relative path, no shell
349 startInfo.FileName = "shouldnoteverexist.exe";
350 startInfo.UseShellExecute = false;
352 Process.Start (startInfo);
354 } catch (Win32Exception ex) {
355 // The system cannot find the file specified
356 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#B2");
357 Assert.AreEqual (-2147467259, ex.ErrorCode, "#B3");
358 Assert.IsNull (ex.InnerException, "#B4");
359 Assert.IsNotNull (ex.Message, "#B5");
360 Assert.AreEqual (2, ex.NativeErrorCode, "#B6");
364 Assert.Ignore ("On Unix and Mac OS X, we try " +
365 "to open any file (using xdg-open, ...)" +
366 " and we do not report an exception " +
369 // absolute path, shell
370 startInfo.FileName = exe;
371 startInfo.UseShellExecute = true;
373 Process.Start (startInfo);
375 } catch (Win32Exception ex) {
376 // The system cannot find the file specified
377 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#C2");
378 Assert.AreEqual (-2147467259, ex.ErrorCode, "#C3");
379 Assert.IsNull (ex.InnerException, "#C4");
380 Assert.IsNotNull (ex.Message, "#C5");
381 Assert.AreEqual (2, ex.NativeErrorCode, "#C6");
384 // relative path, shell
385 startInfo.FileName = "shouldnoteverexist.exe";
386 startInfo.UseShellExecute = true;
388 Process.Start (startInfo);
390 } catch (Win32Exception ex) {
391 // The system cannot find the file specified
392 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#D2");
393 Assert.AreEqual (-2147467259, ex.ErrorCode, "#D3");
394 Assert.IsNull (ex.InnerException, "#D4");
395 Assert.IsNotNull (ex.Message, "#D5");
396 Assert.AreEqual (2, ex.NativeErrorCode, "#D6");
400 [Test] // Start (ProcessStartInfo)
401 public void Start2_FileName_Null ()
403 ProcessStartInfo startInfo = new ProcessStartInfo ((string) null);
406 startInfo.UseShellExecute = false;
408 Process.Start (startInfo);
410 } catch (InvalidOperationException ex) {
411 // Cannot start process because a file name has
413 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#A2");
414 Assert.IsNull (ex.InnerException, "#A3");
415 Assert.IsNotNull (ex.Message, "#A4");
419 startInfo.UseShellExecute = true;
421 Process.Start (startInfo);
423 } catch (InvalidOperationException ex) {
424 // Cannot start process because a file name has
426 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#B2");
427 Assert.IsNull (ex.InnerException, "#B3");
428 Assert.IsNotNull (ex.Message, "#B4");
432 [Test] // Start (ProcessStartInfo)
433 public void Start2_FileName_Whitespace ()
435 ProcessStartInfo startInfo = new ProcessStartInfo (" ");
436 startInfo.UseShellExecute = false;
438 Process.Start (startInfo);
440 } catch (Win32Exception ex) {
441 // The system cannot find the file specified
442 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#2");
443 Assert.AreEqual (-2147467259, ex.ErrorCode, "#3");
444 Assert.IsNull (ex.InnerException, "#4");
445 Assert.IsNotNull (ex.Message, "#5");
446 // TODO: On windows we get ACCESS_DENIED (5) instead of FILE_NOT_FOUND (2) and .NET
447 // gives ERROR_INVALID_PARAMETER (87). See https://bugzilla.xamarin.com/show_bug.cgi?id=44514
448 Assert.IsTrue (ex.NativeErrorCode == 2 || ex.NativeErrorCode == 5 || ex.NativeErrorCode == 87, "#6");
452 [Test] // Start (ProcessStartInfo)
453 public void Start2_StartInfo_Null ()
456 Process.Start ((ProcessStartInfo) null);
458 } catch (ArgumentNullException ex) {
459 Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
460 Assert.IsNull (ex.InnerException, "#3");
461 Assert.IsNotNull (ex.Message, "#4");
462 Assert.IsNotNull (ex.ParamName, "#5");
463 Assert.AreEqual ("startInfo", ex.ParamName, "#6");
467 [Test] // Start (string)
468 public void Start3_FileName_Empty ()
471 Process.Start (string.Empty);
473 } catch (InvalidOperationException ex) {
474 // Cannot start process because a file name has
476 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#2");
477 Assert.IsNull (ex.InnerException, "#3");
478 Assert.IsNotNull (ex.Message, "#4");
482 [Test] // Start (string)
483 public void Start3_FileName_NotFound ()
486 Assert.Ignore ("On Unix and Mac OS X, we try " +
487 "to open any file (using xdg-open, ...)" +
488 " and we do not report an exception " +
491 string exe = @"c:\shouldnoteverexist.exe";
493 // absolute path, no shell
497 } catch (Win32Exception ex) {
498 // The system cannot find the file specified
499 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#A2");
500 Assert.AreEqual (-2147467259, ex.ErrorCode, "#A3");
501 Assert.IsNull (ex.InnerException, "#A4");
502 Assert.IsNotNull (ex.Message, "#A5");
503 Assert.AreEqual (2, ex.NativeErrorCode, "#A6");
506 // relative path, no shell
508 Process.Start ("shouldnoteverexist.exe");
510 } catch (Win32Exception ex) {
511 // The system cannot find the file specified
512 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#B2");
513 Assert.AreEqual (-2147467259, ex.ErrorCode, "#B3");
514 Assert.IsNull (ex.InnerException, "#B4");
515 Assert.IsNotNull (ex.Message, "#B5");
516 Assert.AreEqual (2, ex.NativeErrorCode, "#B6");
520 [Test] // Start (string)
521 public void Start3_FileName_Null ()
524 Process.Start ((string) null);
526 } catch (InvalidOperationException ex) {
527 // Cannot start process because a file name has
529 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#2");
530 Assert.IsNull (ex.InnerException, "#3");
531 Assert.IsNotNull (ex.Message, "#4");
535 [Test] // Start (string, string)
536 public void Start4_Arguments_Null ()
539 Assert.Ignore ("On Unix and Mac OS X, we try " +
540 "to open any file (using xdg-open, ...)" +
541 " and we do not report an exception " +
544 string exe = @"c:\shouldnoteverexist.exe";
547 Process.Start ("whatever.exe", (string) null);
549 } catch (Win32Exception ex) {
550 // The system cannot find the file specified
551 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#B2");
552 Assert.AreEqual (-2147467259, ex.ErrorCode, "#B3");
553 Assert.IsNull (ex.InnerException, "#B4");
554 Assert.IsNotNull (ex.Message, "#B5");
555 Assert.AreEqual (2, ex.NativeErrorCode, "#B6");
559 [Test] // Start (string, string)
560 public void Start4_FileName_Empty ()
563 Process.Start (string.Empty, string.Empty);
565 } catch (InvalidOperationException ex) {
566 // Cannot start process because a file name has
568 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#2");
569 Assert.IsNull (ex.InnerException, "#3");
570 Assert.IsNotNull (ex.Message, "#4");
574 [Test] // Start (string, string)
575 public void Start4_FileName_NotFound ()
578 Assert.Ignore ("On Unix and Mac OS X, we try " +
579 "to open any file (using xdg-open, ...)" +
580 " and we do not report an exception " +
583 string exe = @"c:\shouldnoteverexist.exe";
585 // absolute path, no shell
587 Process.Start (exe, string.Empty);
589 } catch (Win32Exception ex) {
590 // The system cannot find the file specified
591 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#A2");
592 Assert.AreEqual (-2147467259, ex.ErrorCode, "#A3");
593 Assert.IsNull (ex.InnerException, "#A4");
594 Assert.IsNotNull (ex.Message, "#A5");
595 Assert.AreEqual (2, ex.NativeErrorCode, "#A6");
598 // relative path, no shell
600 Process.Start ("shouldnoteverexist.exe", string.Empty);
602 } catch (Win32Exception ex) {
603 // The system cannot find the file specified
604 Assert.AreEqual (typeof (Win32Exception), ex.GetType (), "#B2");
605 Assert.AreEqual (-2147467259, ex.ErrorCode, "#B3");
606 Assert.IsNull (ex.InnerException, "#B4");
607 Assert.IsNotNull (ex.Message, "#B5");
608 Assert.AreEqual (2, ex.NativeErrorCode, "#B6");
613 public void Start_UseShellExecuteWithEmptyUserName ()
616 Assert.Ignore ("On Unix and Mac OS X, we try " +
617 "to open any file (using xdg-open, ...)" +
618 " and we do not report an exception " +
621 string exe = @"c:\shouldnoteverexist.exe";
624 Process p = new Process ();
625 p.StartInfo.FileName = exe;
626 p.StartInfo.UseShellExecute = true;
627 p.StartInfo.UserName = "";
630 } catch (InvalidOperationException) {
632 } catch (Win32Exception) {
636 Process p = new Process ();
637 p.StartInfo.FileName = exe;
638 p.StartInfo.UseShellExecute = true;
639 p.StartInfo.UserName = null;
642 } catch (InvalidOperationException) {
644 } catch (Win32Exception) {
648 [Test] // Start (string, string)
649 public void Start4_FileName_Null ()
652 Process.Start ((string) null, string.Empty);
654 } catch (InvalidOperationException ex) {
655 // Cannot start process because a file name has
657 Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#2");
658 Assert.IsNull (ex.InnerException, "#3");
659 Assert.IsNotNull (ex.Message, "#4");
664 public void StartInfo ()
666 ProcessStartInfo startInfo = new ProcessStartInfo ();
668 Process p = new Process ();
669 Assert.IsNotNull (p.StartInfo, "#A1");
670 p.StartInfo = startInfo;
671 Assert.AreSame (startInfo, p.StartInfo, "#A2");
675 public void StartInfo_Null ()
677 Process p = new Process ();
681 } catch (ArgumentNullException ex) {
682 Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
683 Assert.IsNull (ex.InnerException, "#3");
684 Assert.IsNotNull (ex.Message, "#4");
685 Assert.IsNotNull (ex.ParamName, "#5");
686 Assert.AreEqual ("value", ex.ParamName, "#6");
691 [NUnit.Framework.Category ("NotDotNet")]
692 [NUnit.Framework.Category ("MobileNotWorking")]
693 public void TestRedirectedOutputIsAsync ()
695 // Test requires cygwin, so we just bail out for now.
696 if (Path.DirectorySeparatorChar == '\\')
697 Assert.Ignore ("Test requires cygwin.");
699 Process p = new Process ();
700 p.StartInfo = new ProcessStartInfo ("/bin/sh", "-c \"sleep 2; echo hello\"");
701 p.StartInfo.RedirectStandardOutput = true;
702 p.StartInfo.UseShellExecute = false;
705 Stream stdout = p.StandardOutput.BaseStream;
707 byte [] buffer = new byte [200];
709 // start async Read operation
710 DateTime start = DateTime.Now;
711 IAsyncResult ar = stdout.BeginRead (buffer, 0, buffer.Length,
712 new AsyncCallback (Read), stdout);
714 Assert.IsTrue ((DateTime.Now - start).TotalMilliseconds < 1000, "#01 BeginRead was not async");
716 Assert.AreEqual (0, p.ExitCode, "#02 script failure");
719 ar.AsyncWaitHandle.WaitOne (2000, false);
720 if (bytesRead < "hello".Length)
721 Assert.Fail ("#03 got {0} bytes", bytesRead);
722 Assert.AreEqual ("hello", Encoding.Default.GetString (buffer, 0, 5), "#04");
726 void Read (IAsyncResult ar)
728 Stream stm = (Stream) ar.AsyncState;
729 bytesRead = stm.EndRead (ar);
732 static bool RunningOnUnix {
734 int p = (int)Environment.OSVersion.Platform;
735 return ((p == 128) || (p == 4) || (p == 6));
739 public int bytesRead = -1;
742 [NUnit.Framework.Category ("MobileNotWorking")]
743 // This was for bug #459450
744 public void TestEventRaising ()
746 EventWaitHandle errorClosed = new ManualResetEvent(false);
747 EventWaitHandle outClosed = new ManualResetEvent(false);
748 EventWaitHandle exited = new ManualResetEvent(false);
750 Process p = new Process();
752 p.StartInfo = GetCrossPlatformStartInfo ();
753 p.StartInfo.UseShellExecute = false;
754 p.StartInfo.RedirectStandardOutput = true;
755 p.StartInfo.RedirectStandardError = true;
756 p.StartInfo.RedirectStandardInput = false;
757 p.OutputDataReceived += (object sender, DataReceivedEventArgs e) => {
758 if (e.Data == null) {
763 p.ErrorDataReceived += (object sender, DataReceivedEventArgs e) => {
764 if (e.Data == null) {
769 p.Exited += (object sender, EventArgs e) => {
773 p.EnableRaisingEvents = true;
777 p.BeginErrorReadLine();
778 p.BeginOutputReadLine();
780 Console.WriteLine("started, waiting for handles");
781 bool r = WaitHandle.WaitAll(new WaitHandle[] { errorClosed, outClosed, exited }, 10000, false);
783 Assert.AreEqual (true, r, "Null Argument Events Raised");
787 [NUnit.Framework.Category ("MobileNotWorking")]
788 public void TestEnableEventsAfterExitedEvent ()
790 Process p = new Process ();
792 p.StartInfo = GetCrossPlatformStartInfo ();
793 p.StartInfo.UseShellExecute = false;
794 p.StartInfo.RedirectStandardOutput = true;
795 p.StartInfo.RedirectStandardError = true;
797 var exitedCalledCounter = 0;
798 var exited = new ManualResetEventSlim ();
799 p.Exited += (object sender, EventArgs e) => {
800 exitedCalledCounter++;
801 Assert.IsTrue (p.HasExited);
805 p.EnableRaisingEvents = true;
808 p.BeginErrorReadLine ();
809 p.BeginOutputReadLine ();
813 Assert.AreEqual (1, exitedCalledCounter);
815 Assert.AreEqual (1, exitedCalledCounter);
819 [NUnit.Framework.Category ("MobileNotWorking")]
820 public void TestEnableEventsBeforeExitedEvent ()
822 Process p = new Process ();
824 p.StartInfo = GetCrossPlatformStartInfo ();
825 p.StartInfo.UseShellExecute = false;
826 p.StartInfo.RedirectStandardOutput = true;
827 p.StartInfo.RedirectStandardError = true;
829 p.EnableRaisingEvents = true;
831 var exitedCalledCounter = 0;
832 var exited = new ManualResetEventSlim ();
833 p.Exited += (object sender, EventArgs e) => {
834 exitedCalledCounter++;
835 Assert.IsTrue (p.HasExited);
840 p.BeginErrorReadLine ();
841 p.BeginOutputReadLine ();
844 Assert.IsTrue (exited.Wait (10000));
845 Assert.AreEqual (1, exitedCalledCounter);
847 Assert.AreEqual (1, exitedCalledCounter);
851 [NUnit.Framework.Category ("MobileNotWorking")]
852 public void TestDisableEventsBeforeExitedEvent ()
854 Process p = new Process ();
856 p.StartInfo = GetCrossPlatformStartInfo ();
857 p.StartInfo.UseShellExecute = false;
858 p.StartInfo.RedirectStandardOutput = true;
859 p.StartInfo.RedirectStandardError = true;
861 p.EnableRaisingEvents = false;
863 ManualResetEvent mre = new ManualResetEvent (false);
864 p.Exited += (object sender, EventArgs e) => {
869 p.BeginErrorReadLine ();
870 p.BeginOutputReadLine ();
873 Assert.IsFalse (mre.WaitOne (1000));
876 ProcessStartInfo GetCrossPlatformStartInfo ()
881 path = "/system/bin/ls";
885 return new ProcessStartInfo (path, "/");
887 return new ProcessStartInfo ("help", "");
890 ProcessStartInfo GetEchoCrossPlatformStartInfo ()
895 path = "/system/bin/cat";
899 return new ProcessStartInfo (path);
901 var psi = new ProcessStartInfo ("findstr");
902 psi.Arguments = "\"^\"";
906 #endif // MONO_FEATURE_PROCESS_START
909 public void ProcessName_NotStarted ()
911 Process p = new Process ();
914 String.IsNullOrEmpty (p.ProcessName);
915 } catch (Exception ex) {
919 Assert.IsNotNull (e, "ProcessName should raise if process was not started");
921 //msg should be "No process is associated with this object"
922 Assert.AreEqual (e.GetType (), typeof (InvalidOperationException),
923 "exception should be IOE, I got: " + e.GetType ().Name);
925 Assert.IsNull (e.InnerException, "IOE inner exception should be null");
928 #if MONO_FEATURE_PROCESS_START
930 [NUnit.Framework.Category ("MobileNotWorking")]
931 public void ProcessName_AfterExit ()
933 Process p = new Process ();
934 p.StartInfo = GetCrossPlatformStartInfo ();
935 p.StartInfo.UseShellExecute = false;
936 p.StartInfo.RedirectStandardOutput = true;
937 p.StartInfo.RedirectStandardError = true;
939 p.BeginErrorReadLine();
940 p.BeginOutputReadLine();
942 String.IsNullOrEmpty (p.ExitCode + "");
946 String.IsNullOrEmpty (p.ProcessName);
947 } catch (Exception ex) {
951 Assert.IsNotNull (e, "ProcessName should raise if process was finished");
953 //msg should be "Process has exited, so the requested information is not available"
954 Assert.AreEqual (e.GetType (), typeof (InvalidOperationException),
955 "exception should be IOE, I got: " + e.GetType ().Name);
957 Assert.IsNull (e.InnerException, "IOE inner exception should be null");
959 #endif // MONO_FEATURE_PROCESS_START
962 public void Handle_ThrowsOnNotStarted ()
964 Process p = new Process ();
967 Assert.Fail ("Handle should throw for unstated procs, but returned " + x);
968 } catch (InvalidOperationException) {
973 public void HasExitedCurrent () {
974 Assert.IsFalse (Process.GetCurrentProcess ().HasExited);
977 #if MONO_FEATURE_PROCESS_START
979 [NUnit.Framework.Category ("MobileNotWorking")]
980 public void DisposeWithDisposedStreams ()
982 var psi = GetCrossPlatformStartInfo ();
983 psi.RedirectStandardInput = true;
984 psi.RedirectStandardOutput = true;
985 psi.UseShellExecute = false;
987 var p = Process.Start (psi);
988 p.StandardInput.BaseStream.Dispose ();
989 p.StandardOutput.BaseStream.Dispose ();
994 [NUnit.Framework.Category ("MobileNotWorking")]
995 public void StandardInputWrite ()
997 var psi = GetEchoCrossPlatformStartInfo ();
998 psi.RedirectStandardInput = true;
999 psi.RedirectStandardOutput = true;
1000 psi.UseShellExecute = false;
1002 using (var p = Process.Start (psi)) {
1004 p.OutputDataReceived += (s, e) => {};
1005 p.BeginOutputReadLine ();
1007 for (int i = 0; i < 1024 * 9; ++i) {
1008 p.StandardInput.Write ('x');
1009 if (i > 0 && i % 128 == 0)
1010 p.StandardInput.WriteLine ();
1013 p.StandardInput.Close ();
1018 #endif // MONO_FEATURE_PROCESS_START
1021 public void Modules () {
1022 var modules = Process.GetCurrentProcess ().Modules;
1023 foreach (var a in AppDomain.CurrentDomain.GetAssemblies ()) {
1025 var name = a.GetName ();
1027 StringBuilder sb = new StringBuilder ();
1028 sb.AppendFormat ("Could not found: {0} {1}\n", name.Name, name.Version);
1029 sb.AppendLine ("Looked in modules:");
1031 foreach (var o in modules) {
1032 var m = (ProcessModule) o;
1034 sb.AppendFormat (" {0} {1}.{2}.{3}\n", m.FileName.ToString (),
1035 m.FileVersionInfo.FileMajorPart,
1036 m.FileVersionInfo.FileMinorPart,
1037 m.FileVersionInfo.FileBuildPart);
1039 if (!m.FileName.StartsWith ("[In Memory] " + name.Name))
1042 var fv = m.FileVersionInfo;
1043 if (fv.FileBuildPart != name.Version.Build ||
1044 fv.FileMinorPart != name.Version.Minor ||
1045 fv.FileMajorPart != name.Version.Major)
1051 Assert.IsTrue (found, sb.ToString ());
1055 #if MONO_FEATURE_PROCESS_START
1057 [NUnit.Framework.Category ("MobileNotWorking")]
1058 [ExpectedException (typeof (InvalidOperationException))]
1059 public void TestDoubleBeginOutputReadLine ()
1061 using (Process p = new Process ()) {
1062 p.StartInfo = GetCrossPlatformStartInfo ();
1063 p.StartInfo.UseShellExecute = false;
1064 p.StartInfo.RedirectStandardOutput = true;
1065 p.StartInfo.RedirectStandardError = true;
1069 p.BeginOutputReadLine ();
1070 p.BeginOutputReadLine ();
1077 [NUnit.Framework.Category ("MobileNotWorking")]
1078 [ExpectedException (typeof (InvalidOperationException))]
1079 public void TestDoubleBeginErrorReadLine ()
1081 using (Process p = new Process ()) {
1082 p.StartInfo = GetCrossPlatformStartInfo ();
1083 p.StartInfo.UseShellExecute = false;
1084 p.StartInfo.RedirectStandardOutput = true;
1085 p.StartInfo.RedirectStandardError = true;
1089 p.BeginErrorReadLine ();
1090 p.BeginErrorReadLine ();
1097 [NUnit.Framework.Category ("MobileNotWorking")]
1098 public void TestExitedRaisedTooSoon ()
1101 Assert.Ignore ("using sleep command, only available on unix");
1105 using (Process p = Process.Start("sleep", sleeptime.ToString ())) {
1106 ManualResetEvent mre = new ManualResetEvent (false);
1108 p.EnableRaisingEvents = true;
1109 p.Exited += (sender, e) => {
1113 Assert.IsFalse (mre.WaitOne ((sleeptime - 2) * 1000), "Exited triggered before the process returned");
1116 #endif // MONO_FEATURE_PROCESS_START
1119 public void GetProcessesByName()
1121 // This should return Process[0] or a Process[] with all the "foo" programs running
1122 Process.GetProcessesByName ("foo");
1126 [ExpectedException(typeof(InvalidOperationException))]
1127 public void HigherPrivilegeProcessName ()
1130 Assert.Ignore ("accessing pid 1, only available on unix");
1132 string v = Process.GetProcessById (1).ProcessName;
1136 public void NonChildProcessWaitForExit ()
1139 Assert.Ignore ("accessing parent pid, only available on unix");
1141 using (Process process = Process.GetProcessById (getppid ()))
1142 using (ManualResetEvent mre = new ManualResetEvent (false))
1144 Assert.IsFalse (process.WaitForExit (10), "#1");
1145 Assert.IsFalse (process.HasExited, "#2");
1146 Assert.Throws<InvalidOperationException>(delegate { int exitCode = process.ExitCode; }, "#3");
1148 process.Exited += (s, e) => mre.Set ();
1149 process.EnableRaisingEvents = true;
1150 Assert.IsFalse (mre.WaitOne (100), "#4");
1152 Assert.IsFalse (process.WaitForExit (10), "#5");
1153 Assert.IsFalse (process.HasExited, "#6");
1154 Assert.Throws<InvalidOperationException>(delegate { int exitCode = process.ExitCode; }, "#7");
1159 public void NonChildProcessName ()
1162 Assert.Ignore ("accessing parent pid, only available on unix");
1164 using (Process process = Process.GetProcessById (getppid ()))
1166 string pname = process.ProcessName;
1167 Assert.IsNotNull (pname, "#1");
1168 AssertHelper.IsNotEmpty (pname, "#2");
1173 public void NonChildProcessId ()
1176 Assert.Ignore ("accessing parent pid, only available on unix");
1179 using (Process process = Process.GetProcessById (ppid = getppid ()))
1181 int pid = process.Id;
1182 Assert.AreEqual (ppid, pid, "#1");
1183 AssertHelper.Greater (pid, 0, "#2");
1187 [DllImport ("libc")]
1188 static extern int getppid();