5 // Dietmar Maurer (dietmar@ximian.com)
6 // Gonzalo Paniagua Javier (gonzalo@ximian.com)
8 // (C) Ximian, Inc. http://www.ximian.com
9 // (C) 2004,2005 Novell, Inc. (http://www.novell.com)
10 // Copyright 2013 Xamarin Inc. (http://www.xamarin.com)
12 // Permission is hereby granted, free of charge, to any person obtaining
13 // a copy of this software and associated documentation files (the
14 // "Software"), to deal in the Software without restriction, including
15 // without limitation the rights to use, copy, modify, merge, publish,
16 // distribute, sublicense, and/or sell copies of the Software, and to
17 // permit persons to whom the Software is furnished to do so, subject to
18 // the following conditions:
20 // The above copyright notice and this permission notice shall be
21 // included in all copies or substantial portions of the Software.
23 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
26 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
27 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
28 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
29 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32 using System.Diagnostics;
34 using System.Runtime.CompilerServices;
35 using System.Runtime.InteropServices;
36 using System.Security;
37 using System.Security.Permissions;
42 public static partial class Console
45 private class WindowsConsole
47 public static bool ctrlHandlerAdded = false;
48 private delegate bool WindowsCancelHandler (int keyCode);
49 private static WindowsCancelHandler cancelHandler = new WindowsCancelHandler (DoWindowsConsoleCancelEvent);
51 [DllImport ("kernel32.dll", CharSet=CharSet.Auto, ExactSpelling=true)]
52 private static extern int GetConsoleCP ();
53 [DllImport ("kernel32.dll", CharSet=CharSet.Auto, ExactSpelling=true)]
54 private static extern int GetConsoleOutputCP ();
56 [DllImport ("kernel32.dll", CharSet=CharSet.Auto, ExactSpelling=true)]
57 private static extern bool SetConsoleCtrlHandler (WindowsCancelHandler handler, bool addHandler);
59 // Only call the event handler if Control-C was pressed (code == 0), nothing else
60 private static bool DoWindowsConsoleCancelEvent (int keyCode)
63 DoConsoleCancelEvent ();
67 [MethodImpl (MethodImplOptions.NoInlining)]
68 public static int GetInputCodePage ()
70 return GetConsoleCP ();
73 [MethodImpl (MethodImplOptions.NoInlining)]
74 public static int GetOutputCodePage ()
76 return GetConsoleOutputCP ();
79 public static void AddCtrlHandler ()
81 SetConsoleCtrlHandler (cancelHandler, true);
82 ctrlHandlerAdded = true;
85 public static void RemoveCtrlHandler ()
87 SetConsoleCtrlHandler (cancelHandler, false);
88 ctrlHandlerAdded = false;
93 internal static TextWriter stdout;
94 private static TextWriter stderr;
95 private static TextReader stdin;
99 if (Environment.IsRunningOnWindows) {
101 // On Windows, follow the Windows tradition
104 // should never happen since Moonlight does not run on windows
105 inputEncoding = outputEncoding = Encoding.Default;
108 inputEncoding = Encoding.GetEncoding (WindowsConsole.GetInputCodePage ());
109 outputEncoding = Encoding.GetEncoding (WindowsConsole.GetOutputCodePage ());
110 // ArgumentException and NotSupportedException can be thrown as well
112 // FIXME: I18N assemblies are not available when compiling mcs
113 // Use Latin 1 as it is fast and UTF-8 is never used as console code page
114 inputEncoding = outputEncoding = Encoding.Default;
119 // On Unix systems (128), do not output the
120 // UTF-8 ZWNBSP (zero-width non-breaking space).
123 EncodingHelper.InternalCodePage (ref code_page);
125 if (code_page != -1 && ((code_page & 0x0fffffff) == 3 // UTF8Encoding.UTF8_CODE_PAGE
126 || ((code_page & 0x10000000) != 0)))
127 inputEncoding = outputEncoding = EncodingHelper.UTF8Unmarked;
129 inputEncoding = outputEncoding = Encoding.Default;
132 SetupStreams (inputEncoding, outputEncoding);
135 static void SetupStreams (Encoding inputEncoding, Encoding outputEncoding)
138 if (!Environment.IsRunningOnWindows && ConsoleDriver.IsConsole) {
139 stdin = new CStreamReader (OpenStandardInput (0), inputEncoding);
140 stdout = TextWriter.Synchronized (new CStreamWriter (OpenStandardOutput (0), outputEncoding, true) { AutoFlush = true });
141 stderr = TextWriter.Synchronized (new CStreamWriter (OpenStandardError (0), outputEncoding, true) { AutoFlush = true });
145 stdin = TextReader.Synchronized (new UnexceptionalStreamReader (OpenStandardInput (0), inputEncoding));
148 stdout = new NSLogWriter ();
149 stderr = new NSLogWriter ();
151 stdout = TextWriter.Synchronized (new UnexceptionalStreamWriter (OpenStandardOutput (0), outputEncoding) { AutoFlush = true });
152 stderr = TextWriter.Synchronized (new UnexceptionalStreamWriter (OpenStandardError (0), outputEncoding) { AutoFlush = true });
155 if (LogcatTextWriter.IsRunningOnAndroid ()) {
156 stdout = TextWriter.Synchronized (new LogcatTextWriter ("mono-stdout", stdout));
157 stderr = TextWriter.Synchronized (new LogcatTextWriter ("mono-stderr", stderr));
163 GC.SuppressFinalize (stdout);
164 GC.SuppressFinalize (stderr);
165 GC.SuppressFinalize (stdin);
168 public static TextWriter Error {
174 public static TextWriter Out {
180 public static TextReader In {
186 private static Stream Open (IntPtr handle, FileAccess access, int bufferSize)
189 // TODO: Should use __ConsoleStream from reference sources
190 return new FileStream (handle, access, false, bufferSize, false, true);
191 } catch (IOException) {
196 public static Stream OpenStandardError ()
198 return OpenStandardError (0);
201 // calling any FileStream constructor with a handle normally
202 // requires permissions UnmanagedCode permissions. In this
203 // case we assert this permission so the console can be used
204 // in partial trust (i.e. without having UnmanagedCode).
205 [SecurityPermission (SecurityAction.Assert, UnmanagedCode = true)]
206 public static Stream OpenStandardError (int bufferSize)
208 return Open (MonoIO.ConsoleError, FileAccess.Write, bufferSize);
211 public static Stream OpenStandardInput ()
213 return OpenStandardInput (0);
216 // calling any FileStream constructor with a handle normally
217 // requires permissions UnmanagedCode permissions. In this
218 // case we assert this permission so the console can be used
219 // in partial trust (i.e. without having UnmanagedCode).
220 [SecurityPermission (SecurityAction.Assert, UnmanagedCode = true)]
221 public static Stream OpenStandardInput (int bufferSize)
223 return Open (MonoIO.ConsoleInput, FileAccess.Read, bufferSize);
226 public static Stream OpenStandardOutput ()
228 return OpenStandardOutput (0);
231 // calling any FileStream constructor with a handle normally
232 // requires permissions UnmanagedCode permissions. In this
233 // case we assert this permission so the console can be used
234 // in partial trust (i.e. without having UnmanagedCode).
235 [SecurityPermission (SecurityAction.Assert, UnmanagedCode = true)]
236 public static Stream OpenStandardOutput (int bufferSize)
238 return Open (MonoIO.ConsoleOutput, FileAccess.Write, bufferSize);
241 [SecurityPermission (SecurityAction.Demand, UnmanagedCode = true)]
242 public static void SetError (TextWriter newError)
244 if (newError == null)
245 throw new ArgumentNullException ("newError");
250 [SecurityPermission (SecurityAction.Demand, UnmanagedCode = true)]
251 public static void SetIn (TextReader newIn)
254 throw new ArgumentNullException ("newIn");
259 [SecurityPermission (SecurityAction.Demand, UnmanagedCode = true)]
260 public static void SetOut (TextWriter newOut)
263 throw new ArgumentNullException ("newOut");
268 public static void Write (bool value)
270 stdout.Write (value);
273 public static void Write (char value)
275 stdout.Write (value);
278 public static void Write (char[] buffer)
280 stdout.Write (buffer);
283 public static void Write (decimal value)
285 stdout.Write (value);
288 public static void Write (double value)
290 stdout.Write (value);
293 public static void Write (int value)
295 stdout.Write (value);
298 public static void Write (long value)
300 stdout.Write (value);
303 public static void Write (object value)
305 stdout.Write (value);
308 public static void Write (float value)
310 stdout.Write (value);
313 public static void Write (string value)
315 stdout.Write (value);
318 [CLSCompliant (false)]
319 public static void Write (uint value)
321 stdout.Write (value);
324 [CLSCompliant (false)]
325 public static void Write (ulong value)
327 stdout.Write (value);
330 public static void Write (string format, object arg0)
332 stdout.Write (format, arg0);
335 public static void Write (string format, params object[] arg)
338 stdout.Write (format);
340 stdout.Write (format, arg);
343 public static void Write (char[] buffer, int index, int count)
345 stdout.Write (buffer, index, count);
348 public static void Write (string format, object arg0, object arg1)
350 stdout.Write (format, arg0, arg1);
353 public static void Write (string format, object arg0, object arg1, object arg2 )
355 stdout.Write (format, arg0, arg1, arg2);
358 [CLSCompliant (false)]
359 public static void Write (string format, object arg0, object arg1, object arg2, object arg3, __arglist)
361 ArgIterator iter = new ArgIterator (__arglist);
362 int argCount = iter.GetRemainingCount();
364 object[] args = new object [argCount + 4];
369 for (int i = 0; i < argCount; i++) {
370 TypedReference typedRef = iter.GetNextArg ();
371 args [i + 4] = TypedReference.ToObject (typedRef);
374 stdout.Write (String.Format (format, args));
377 public static void WriteLine ()
382 public static void WriteLine (bool value)
384 stdout.WriteLine (value);
387 public static void WriteLine (char value)
389 stdout.WriteLine (value);
392 public static void WriteLine (char[] buffer)
394 stdout.WriteLine (buffer);
397 public static void WriteLine (decimal value)
399 stdout.WriteLine (value);
402 public static void WriteLine (double value)
404 stdout.WriteLine (value);
407 public static void WriteLine (int value)
409 stdout.WriteLine (value);
412 public static void WriteLine (long value)
414 stdout.WriteLine (value);
417 public static void WriteLine (object value)
419 stdout.WriteLine (value);
422 public static void WriteLine (float value)
424 stdout.WriteLine (value);
427 public static void WriteLine (string value)
429 stdout.WriteLine (value);
432 [CLSCompliant (false)]
433 public static void WriteLine (uint value)
435 stdout.WriteLine (value);
438 [CLSCompliant (false)]
439 public static void WriteLine (ulong value)
441 stdout.WriteLine (value);
444 public static void WriteLine (string format, object arg0)
446 stdout.WriteLine (format, arg0);
449 public static void WriteLine (string format, params object[] arg)
452 stdout.WriteLine (format);
454 stdout.WriteLine (format, arg);
457 public static void WriteLine (char[] buffer, int index, int count)
459 stdout.WriteLine (buffer, index, count);
462 public static void WriteLine (string format, object arg0, object arg1)
464 stdout.WriteLine (format, arg0, arg1);
467 public static void WriteLine (string format, object arg0, object arg1, object arg2)
469 stdout.WriteLine (format, arg0, arg1, arg2);
472 [CLSCompliant (false)]
473 public static void WriteLine (string format, object arg0, object arg1, object arg2, object arg3, __arglist)
475 ArgIterator iter = new ArgIterator (__arglist);
476 int argCount = iter.GetRemainingCount();
478 object[] args = new object [argCount + 4];
483 for (int i = 0; i < argCount; i++) {
484 TypedReference typedRef = iter.GetNextArg ();
485 args [i + 4] = TypedReference.ToObject (typedRef);
488 stdout.WriteLine (String.Format (format, args));
492 public static int Read ()
494 if ((stdin is CStreamReader) && ConsoleDriver.IsConsole) {
495 return ConsoleDriver.Read ();
497 return stdin.Read ();
501 public static string ReadLine ()
503 if ((stdin is CStreamReader) && ConsoleDriver.IsConsole) {
504 return ConsoleDriver.ReadLine ();
506 return stdin.ReadLine ();
510 public static int Read ()
512 return stdin.Read ();
515 public static string ReadLine ()
517 return stdin.ReadLine ();
522 // FIXME: Console should use these encodings when changed
523 static Encoding inputEncoding;
524 static Encoding outputEncoding;
526 public static Encoding InputEncoding {
527 get { return inputEncoding; }
529 inputEncoding = value;
530 SetupStreams (inputEncoding, outputEncoding);
534 public static Encoding OutputEncoding {
535 get { return outputEncoding; }
537 outputEncoding = value;
538 SetupStreams (inputEncoding, outputEncoding);
543 public static ConsoleColor BackgroundColor {
544 get { return ConsoleDriver.BackgroundColor; }
545 set { ConsoleDriver.BackgroundColor = value; }
548 public static int BufferHeight {
549 get { return ConsoleDriver.BufferHeight; }
550 [MonoLimitation ("Implemented only on Windows")]
551 set { ConsoleDriver.BufferHeight = value; }
554 public static int BufferWidth {
555 get { return ConsoleDriver.BufferWidth; }
556 [MonoLimitation ("Implemented only on Windows")]
557 set { ConsoleDriver.BufferWidth = value; }
560 [MonoLimitation ("Implemented only on Windows")]
561 public static bool CapsLock {
562 get { return ConsoleDriver.CapsLock; }
565 public static int CursorLeft {
566 get { return ConsoleDriver.CursorLeft; }
567 set { ConsoleDriver.CursorLeft = value; }
570 public static int CursorTop {
571 get { return ConsoleDriver.CursorTop; }
572 set { ConsoleDriver.CursorTop = value; }
575 public static int CursorSize {
576 get { return ConsoleDriver.CursorSize; }
577 set { ConsoleDriver.CursorSize = value; }
580 public static bool CursorVisible {
581 get { return ConsoleDriver.CursorVisible; }
582 set { ConsoleDriver.CursorVisible = value; }
585 public static ConsoleColor ForegroundColor {
586 get { return ConsoleDriver.ForegroundColor; }
587 set { ConsoleDriver.ForegroundColor = value; }
590 public static bool KeyAvailable {
591 get { return ConsoleDriver.KeyAvailable; }
594 public static int LargestWindowHeight {
595 get { return ConsoleDriver.LargestWindowHeight; }
598 public static int LargestWindowWidth {
599 get { return ConsoleDriver.LargestWindowWidth; }
602 [MonoLimitation ("Only works on windows")]
603 public static bool NumberLock {
604 get { return ConsoleDriver.NumberLock; }
607 public static string Title {
608 get { return ConsoleDriver.Title; }
609 set { ConsoleDriver.Title = value; }
612 public static bool TreatControlCAsInput {
613 get { return ConsoleDriver.TreatControlCAsInput; }
614 set { ConsoleDriver.TreatControlCAsInput = value; }
617 [MonoLimitation ("Only works on windows")]
618 public static int WindowHeight {
619 get { return ConsoleDriver.WindowHeight; }
620 set { ConsoleDriver.WindowHeight = value; }
623 [MonoLimitation ("Only works on windows")]
624 public static int WindowLeft {
625 get { return ConsoleDriver.WindowLeft; }
626 set { ConsoleDriver.WindowLeft = value; }
629 [MonoLimitation ("Only works on windows")]
630 public static int WindowTop {
631 get { return ConsoleDriver.WindowTop; }
632 set { ConsoleDriver.WindowTop = value; }
635 [MonoLimitation ("Only works on windows")]
636 public static int WindowWidth {
637 get { return ConsoleDriver.WindowWidth; }
638 set { ConsoleDriver.WindowWidth = value; }
641 public static bool IsErrorRedirected {
643 return ConsoleDriver.IsErrorRedirected;
647 public static bool IsOutputRedirected {
649 return ConsoleDriver.IsOutputRedirected;
653 public static bool IsInputRedirected {
655 return ConsoleDriver.IsInputRedirected;
659 public static void Beep ()
664 public static void Beep (int frequency, int duration)
666 if (frequency < 37 || frequency > 32767)
667 throw new ArgumentOutOfRangeException ("frequency");
670 throw new ArgumentOutOfRangeException ("duration");
672 ConsoleDriver.Beep (frequency, duration);
675 public static void Clear ()
677 ConsoleDriver.Clear ();
680 [MonoLimitation ("Implemented only on Windows")]
681 public static void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight,
682 int targetLeft, int targetTop)
684 ConsoleDriver.MoveBufferArea (sourceLeft, sourceTop, sourceWidth, sourceHeight, targetLeft, targetTop);
687 [MonoLimitation ("Implemented only on Windows")]
688 public static void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight,
689 int targetLeft, int targetTop, Char sourceChar,
690 ConsoleColor sourceForeColor, ConsoleColor sourceBackColor)
692 ConsoleDriver.MoveBufferArea (sourceLeft, sourceTop, sourceWidth, sourceHeight, targetLeft, targetTop,
693 sourceChar, sourceForeColor, sourceBackColor);
696 public static ConsoleKeyInfo ReadKey ()
698 return ReadKey (false);
701 public static ConsoleKeyInfo ReadKey (bool intercept)
703 return ConsoleDriver.ReadKey (intercept);
706 public static void ResetColor ()
708 ConsoleDriver.ResetColor ();
711 [MonoLimitation ("Only works on windows")]
712 public static void SetBufferSize (int width, int height)
714 ConsoleDriver.SetBufferSize (width, height);
717 public static void SetCursorPosition (int left, int top)
719 ConsoleDriver.SetCursorPosition (left, top);
722 public static void SetWindowPosition (int left, int top)
724 ConsoleDriver.SetWindowPosition (left, top);
727 public static void SetWindowSize (int width, int height)
729 ConsoleDriver.SetWindowSize (width, height);
732 static ConsoleCancelEventHandler cancel_event;
733 public static event ConsoleCancelEventHandler CancelKeyPress {
735 if (ConsoleDriver.Initialized == false)
736 ConsoleDriver.Init ();
738 cancel_event += value;
740 if (Environment.IsRunningOnWindows && !WindowsConsole.ctrlHandlerAdded)
741 WindowsConsole.AddCtrlHandler();
744 if (ConsoleDriver.Initialized == false)
745 ConsoleDriver.Init ();
747 cancel_event -= value;
749 if (cancel_event == null && Environment.IsRunningOnWindows)
751 // Need to remove our hook if there's nothing left in the event
752 if (WindowsConsole.ctrlHandlerAdded)
753 WindowsConsole.RemoveCtrlHandler();
758 delegate void InternalCancelHandler ();
760 #pragma warning disable 414
762 // Used by console-io.c
764 static readonly InternalCancelHandler cancel_handler = new InternalCancelHandler (DoConsoleCancelEvent);
765 #pragma warning restore 414
767 internal static void DoConsoleCancelEvent ()
770 if (cancel_event != null) {
771 ConsoleCancelEventArgs args = new ConsoleCancelEventArgs (ConsoleSpecialKey.ControlC);
772 Delegate [] delegates = cancel_event.GetInvocationList ();
773 foreach (ConsoleCancelEventHandler d in delegates){
775 // Sender is always null here.
777 } catch {} // Ignore any exception.
783 Environment.Exit (58);
786 // largely inspired by https://github.com/dotnet/corefx/blob/be8d2ce3964968cec9322a64211e37682085db70/src/System.Console/src/System/ConsolePal.WinRT.cs, because it's a similar platform where a console might not be available
788 // provide simply color tracking that allows round-tripping
789 internal const ConsoleColor UnknownColor = (ConsoleColor)(-1);
790 private static ConsoleColor s_trackedForegroundColor = UnknownColor;
791 private static ConsoleColor s_trackedBackgroundColor = UnknownColor;
793 public static ConsoleColor ForegroundColor
797 return s_trackedForegroundColor;
801 lock (Console.Out) // synchronize with other writers
803 s_trackedForegroundColor = value;
808 public static ConsoleColor BackgroundColor
812 return s_trackedBackgroundColor;
816 lock (Console.Out) // synchronize with other writers
818 s_trackedBackgroundColor = value;
823 public static int BufferWidth
825 get { throw new PlatformNotSupportedException (); }
826 set { throw new PlatformNotSupportedException (); }
829 public static int BufferHeight
831 get { throw new PlatformNotSupportedException (); }
832 set { throw new PlatformNotSupportedException (); }
835 public static bool CapsLock { get { throw new PlatformNotSupportedException (); } }
837 public static int CursorLeft
839 get { throw new PlatformNotSupportedException (); }
840 set { throw new PlatformNotSupportedException (); }
843 public static int CursorTop
845 get { throw new PlatformNotSupportedException (); }
846 set { throw new PlatformNotSupportedException (); }
849 public static int CursorSize
852 set { throw new PlatformNotSupportedException(); }
855 public static bool CursorVisible
857 get { throw new PlatformNotSupportedException (); }
858 set { throw new PlatformNotSupportedException (); }
861 public static bool KeyAvailable { get { throw new PlatformNotSupportedException (); } }
863 public static int LargestWindowWidth
865 get { throw new PlatformNotSupportedException (); }
866 set { throw new PlatformNotSupportedException (); }
869 public static int LargestWindowHeight
871 get { throw new PlatformNotSupportedException (); }
872 set { throw new PlatformNotSupportedException (); }
875 public static bool NumberLock { get { throw new PlatformNotSupportedException (); } }
877 public static string Title
879 get { throw new PlatformNotSupportedException (); }
880 set { throw new PlatformNotSupportedException (); }
883 public static bool TreatControlCAsInput
885 get { throw new PlatformNotSupportedException (); }
886 set { throw new PlatformNotSupportedException (); }
889 public static int WindowHeight
891 get { throw new PlatformNotSupportedException (); }
892 set { throw new PlatformNotSupportedException (); }
895 public static int WindowLeft
898 set { throw new PlatformNotSupportedException (); }
901 public static int WindowTop
904 set { throw new PlatformNotSupportedException (); }
907 public static int WindowWidth
909 get { throw new PlatformNotSupportedException (); }
910 set { throw new PlatformNotSupportedException (); }
913 public static bool IsErrorRedirected { get { throw new PlatformNotSupportedException (); } }
915 public static bool IsInputRedirected { get { throw new PlatformNotSupportedException (); } }
917 public static bool IsOutputRedirected { get { throw new PlatformNotSupportedException (); } }
919 public static void Beep () { throw new PlatformNotSupportedException (); }
921 public static void Beep (int frequency, int duration) { throw new PlatformNotSupportedException (); }
923 public static void Clear () { throw new PlatformNotSupportedException (); }
925 public static void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight, int targetLeft, int targetTop) { throw new PlatformNotSupportedException(); }
927 public static void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight, int targetLeft, int targetTop, char sourceChar, ConsoleColor sourceForeColor, ConsoleColor sourceBackColor) { throw new PlatformNotSupportedException(); }
930 public static ConsoleKeyInfo ReadKey ()
932 return ReadKey (false);
935 public static ConsoleKeyInfo ReadKey (bool intercept) { throw new PlatformNotSupportedException (); }
937 public static void ResetColor ()
939 lock (Console.Out) // synchronize with other writers
941 s_trackedForegroundColor = UnknownColor;
942 s_trackedBackgroundColor = UnknownColor;
946 public static void SetBufferSize (int width, int height) { throw new PlatformNotSupportedException (); }
948 public static void SetCursorPosition (int left, int top) { throw new PlatformNotSupportedException (); }
950 public static void SetWindowPosition (int left, int top) { throw new PlatformNotSupportedException (); }
952 public static void SetWindowSize (int width, int height) { throw new PlatformNotSupportedException (); }
954 public static event ConsoleCancelEventHandler CancelKeyPress {
956 throw new PlatformNotSupportedException ();
959 throw new PlatformNotSupportedException ();