dbe81e12e7628325e3c1d646caedf02f9e427f3f
[mono.git] / mcs / class / referencesource / mscorlib / system / threading / thread.cs
1 // ==++==
2 //
3 //   Copyright (c) Microsoft Corporation.  All rights reserved.
4 //
5 // ==--==
6 //
7 // <OWNER>Microsoft</OWNER>
8 /*=============================================================================
9 **
10 ** Class: Thread
11 **
12 **
13 ** Purpose: Class for creating and managing a thread.
14 **
15 **
16 =============================================================================*/
17
18 namespace System.Threading {
19     using System.Threading;
20     using System.Runtime;
21     using System.Runtime.InteropServices;
22 #if FEATURE_REMOTING    
23     using System.Runtime.Remoting.Contexts;
24     using System.Runtime.Remoting.Messaging;
25 #endif
26     using System;
27     using System.Diagnostics;
28     using System.Security.Permissions;
29     using System.Security.Principal;
30     using System.Globalization;
31     using System.Collections.Generic;
32     using System.Runtime.Serialization;
33     using System.Runtime.CompilerServices;
34     using System.Runtime.ConstrainedExecution;
35     using System.Security;
36     using System.Runtime.Versioning;
37     using System.Diagnostics.Contracts;
38
39     internal delegate Object InternalCrossContextDelegate(Object[] args);
40
41     internal class ThreadHelper
42     {
43         [System.Security.SecuritySafeCritical]
44         static ThreadHelper() {}
45
46         Delegate _start;
47         Object _startArg = null;
48         ExecutionContext _executionContext = null;
49         internal ThreadHelper(Delegate start)
50         {
51             _start = start;
52         }
53
54         internal void SetExecutionContextHelper(ExecutionContext ec)
55         {
56             _executionContext = ec;
57         }
58
59         [System.Security.SecurityCritical]
60         static internal ContextCallback _ccb = new ContextCallback(ThreadStart_Context);
61         
62         [System.Security.SecurityCritical]
63         static private void ThreadStart_Context(Object state)
64         {
65             ThreadHelper t = (ThreadHelper)state;
66             if (t._start is ThreadStart)
67             {
68                 ((ThreadStart)t._start)();
69             }
70             else
71             {
72                 ((ParameterizedThreadStart)t._start)(t._startArg);
73             }
74         }
75
76         // call back helper
77         #if FEATURE_CORECLR
78         [System.Security.SecuritySafeCritical] // auto-generated
79         #else
80         [System.Security.SecurityCritical]
81         #endif
82         internal void ThreadStart(object obj)
83         {               
84             _startArg = obj;
85             if (_executionContext != null) 
86             {
87                 ExecutionContext.Run(_executionContext, _ccb, (Object)this);
88             }
89             else
90             {
91                 ((ParameterizedThreadStart)_start)(obj);
92             }
93         }
94
95         // call back helper
96         #if FEATURE_CORECLR
97         [System.Security.SecuritySafeCritical] // auto-generated
98         #else
99         [System.Security.SecurityCritical]
100         #endif
101         internal void ThreadStart()
102         {
103             if (_executionContext != null) 
104             {
105                 ExecutionContext.Run(_executionContext, _ccb, (Object)this);
106             }
107             else
108             {
109                 ((ThreadStart)_start)();
110             }
111         }
112     }
113 #if !MONO
114     internal struct ThreadHandle
115     {
116         private IntPtr m_ptr;
117
118         internal ThreadHandle(IntPtr pThread)
119         {
120             m_ptr = pThread;
121         }
122     }
123 #endif
124     // deliberately not [serializable]
125     [ClassInterface(ClassInterfaceType.None)]
126     [ComDefaultInterface(typeof(_Thread))]
127 [System.Runtime.InteropServices.ComVisible(true)]
128     public sealed partial class Thread : CriticalFinalizerObject
129 #if !MOBILE
130     , _Thread
131 #endif
132     {
133 #if !MONO
134         /*=========================================================================
135         ** Data accessed from managed code that needs to be defined in
136         ** ThreadBaseObject to maintain alignment between the two classes.
137         ** DON'T CHANGE THESE UNLESS YOU MODIFY ThreadBaseObject in vm\object.h
138         =========================================================================*/
139 #if FEATURE_REMOTING        
140         private Context         m_Context;
141 #endif 
142 #if !FEATURE_CORECLR
143         private ExecutionContext m_ExecutionContext;    // this call context follows the logical thread
144 #endif
145
146         private String          m_Name;
147         private Delegate        m_Delegate;             // Delegate
148         
149 #if FEATURE_LEAK_CULTURE_INFO 
150         private CultureInfo     m_CurrentCulture;
151         private CultureInfo     m_CurrentUICulture;
152 #endif
153         private Object          m_ThreadStartArg;
154
155         /*=========================================================================
156         ** The base implementation of Thread is all native.  The following fields
157         ** should never be used in the C# code.  They are here to define the proper
158         ** space so the thread object may be allocated.  DON'T CHANGE THESE UNLESS
159         ** YOU MODIFY ThreadBaseObject in vm\object.h
160         =========================================================================*/
161 #pragma warning disable 169
162 #pragma warning disable 414  // These fields are not used from managed.
163         // IntPtrs need to be together, and before ints, because IntPtrs are 64-bit
164         //  fields on 64-bit platforms, where they will be sorted together.
165                                                         
166         private IntPtr  DONT_USE_InternalThread;        // Pointer
167         private int     m_Priority;                     // INT32
168         private int     m_ManagedThreadId;              // INT32
169
170 #pragma warning restore 414
171 #pragma warning restore 169
172
173         private bool m_ExecutionContextBelongsToOuterScope;
174 #if DEBUG
175         private bool m_ForbidExecutionContextMutation;
176 #endif
177 #endif
178         /*=========================================================================
179         ** This manager is responsible for storing the global data that is
180         ** shared amongst all the thread local stores.
181         =========================================================================*/
182         static private LocalDataStoreMgr s_LocalDataStoreMgr;
183
184         /*=========================================================================
185         ** Thread-local data store
186         =========================================================================*/
187         [ThreadStatic]
188         static private LocalDataStoreHolder s_LocalDataStore;
189
190         // Do not move! Order of above fields needs to be preserved for alignment
191         // with native code
192         // See code:#threadCultureInfo
193 #if !FEATURE_LEAK_CULTURE_INFO
194         [ThreadStatic]
195         internal static CultureInfo     m_CurrentCulture;
196         [ThreadStatic]
197         internal static CultureInfo     m_CurrentUICulture;
198 #endif
199
200         static AsyncLocal<CultureInfo> s_asyncLocalCurrentCulture; 
201         static AsyncLocal<CultureInfo> s_asyncLocalCurrentUICulture;
202
203         static void AsyncLocalSetCurrentCulture(AsyncLocalValueChangedArgs<CultureInfo> args)
204         {
205 #if FEATURE_LEAK_CULTURE_INFO 
206             Thread.CurrentThread.m_CurrentCulture = args.CurrentValue;
207 #else
208             m_CurrentCulture = args.CurrentValue;
209 #endif // FEATURE_LEAK_CULTURE_INFO
210         }
211
212         static void AsyncLocalSetCurrentUICulture(AsyncLocalValueChangedArgs<CultureInfo> args)
213         {
214 #if FEATURE_LEAK_CULTURE_INFO 
215             Thread.CurrentThread.m_CurrentUICulture = args.CurrentValue;
216 #else
217             m_CurrentUICulture = args.CurrentValue;
218 #endif // FEATURE_LEAK_CULTURE_INFO
219         }
220
221 #if FEATURE_CORECLR
222         // Adding an empty default ctor for annotation purposes
223         [System.Security.SecuritySafeCritical] // auto-generated
224         internal Thread(){}
225 #endif // FEATURE_CORECLR
226
227         /*=========================================================================
228         ** Creates a new Thread object which will begin execution at
229         ** start.ThreadStart on a new thread when the Start method is called.
230         **
231         ** Exceptions: ArgumentNullException if start == null.
232         =========================================================================*/
233         [System.Security.SecuritySafeCritical]  // auto-generated
234         public Thread(ThreadStart start) {
235             if (start == null) {
236                 throw new ArgumentNullException("start");
237             }
238             Contract.EndContractBlock();
239             SetStartHelper((Delegate)start,0);  //0 will setup Thread with default stackSize
240         }
241
242         [System.Security.SecuritySafeCritical]  // auto-generated
243         public Thread(ThreadStart start, int maxStackSize) {
244             if (start == null) {
245                 throw new ArgumentNullException("start");
246             }
247             if (0 > maxStackSize)
248                 throw new ArgumentOutOfRangeException("maxStackSize",Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegNum"));
249             Contract.EndContractBlock();
250             SetStartHelper((Delegate)start, maxStackSize);
251         }
252
253         [System.Security.SecuritySafeCritical]  // auto-generated
254         public Thread(ParameterizedThreadStart start) {
255             if (start == null) {
256                 throw new ArgumentNullException("start");
257             }
258             Contract.EndContractBlock();
259             SetStartHelper((Delegate)start, 0);
260         }
261
262         [System.Security.SecuritySafeCritical]  // auto-generated
263         public Thread(ParameterizedThreadStart start, int maxStackSize) {
264             if (start == null) {
265                 throw new ArgumentNullException("start");
266             }
267             if (0 > maxStackSize)
268                 throw new ArgumentOutOfRangeException("maxStackSize",Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegNum"));
269             Contract.EndContractBlock();
270             SetStartHelper((Delegate)start, maxStackSize);
271         }
272 #if !MONO
273         [ComVisible(false)]
274         public override int GetHashCode()
275         {
276             return m_ManagedThreadId;
277         }
278
279         extern public int ManagedThreadId
280         {
281             [ResourceExposure(ResourceScope.None)]
282             [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
283             [MethodImplAttribute(MethodImplOptions.InternalCall)]
284             [System.Security.SecuritySafeCritical]  // auto-generated
285             get;
286         }
287
288         // Returns handle for interop with EE. The handle is guaranteed to be non-null.
289         internal unsafe ThreadHandle GetNativeHandle()
290         {
291             IntPtr thread = DONT_USE_InternalThread;
292
293             // This should never happen under normal circumstances. m_assembly is always assigned before it is handed out to the user.
294             // There are ways how to create an unitialized objects through remoting, etc. Avoid AVing in the EE by throwing a nice
295             // exception here.
296             if (thread.IsNull())
297                 throw new ArgumentException(null, Environment.GetResourceString("Argument_InvalidHandle"));
298
299             return new ThreadHandle(thread);
300         }
301 #endif
302
303         /*=========================================================================
304         ** Spawns off a new thread which will begin executing at the ThreadStart
305         ** method on the IThreadable interface passed in the constructor. Once the
306         ** thread is dead, it cannot be restarted with another call to Start.
307         **
308         ** Exceptions: ThreadStateException if the thread has already been started.
309         =========================================================================*/
310         [HostProtection(Synchronization=true,ExternalThreading=true)]
311         [MethodImplAttribute(MethodImplOptions.NoInlining)] // Methods containing StackCrawlMark local var has to be marked non-inlineable
312         public void Start()
313         {
314             StackCrawlMark stackMark = StackCrawlMark.LookForMyCaller;
315             Start(ref stackMark);
316         }
317
318         [HostProtection(Synchronization=true,ExternalThreading=true)]
319         [MethodImplAttribute(MethodImplOptions.NoInlining)] // Methods containing StackCrawlMark local var has to be marked non-inlineable
320         public void Start(object parameter)
321         {
322             //In the case of a null delegate (second call to start on same thread)
323             //    StartInternal method will take care of the error reporting
324             if(m_Delegate is ThreadStart)
325             {
326                 //We expect the thread to be setup with a ParameterizedThreadStart
327                 //    if this constructor is called.
328                 //If we got here then that wasn't the case
329                 throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_ThreadWrongThreadStart"));
330             }
331             m_ThreadStartArg = parameter;
332             StackCrawlMark stackMark = StackCrawlMark.LookForMyCaller;
333             Start(ref stackMark);
334         }
335
336         [System.Security.SecuritySafeCritical]
337         private void Start(ref StackCrawlMark stackMark)
338         {
339 #if FEATURE_COMINTEROP_APARTMENT_SUPPORT
340             // Eagerly initialize the COM Apartment state of the thread if we're allowed to.
341             StartupSetApartmentStateInternal();
342 #endif // FEATURE_COMINTEROP_APARTMENT_SUPPORT
343
344             // Attach current thread's security principal object to the new
345             // thread. Be careful not to bind the current thread to a principal
346             // if it's not already bound.
347             if (m_Delegate != null)
348             {
349                 // If we reach here with a null delegate, something is broken. But we'll let the StartInternal method take care of
350                 // reporting an error. Just make sure we dont try to dereference a null delegate.
351                 ThreadHelper t = (ThreadHelper)(m_Delegate.Target);
352                 ExecutionContext ec = ExecutionContext.Capture(
353                     ref stackMark,
354                     ExecutionContext.CaptureOptions.IgnoreSyncCtx);
355                 t.SetExecutionContextHelper(ec);
356             }
357 #if FEATURE_IMPERSONATION
358             IPrincipal principal = (IPrincipal)CallContext.Principal;
359 #else
360             IPrincipal principal = null;
361 #endif
362             StartInternal(principal, ref stackMark);
363         }
364
365
366 #if !FEATURE_CORECLR
367         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
368         internal ExecutionContext.Reader GetExecutionContextReader()
369         {
370             return new ExecutionContext.Reader(m_ExecutionContext);
371         }
372
373         internal bool ExecutionContextBelongsToCurrentScope
374         {
375             get { return !m_ExecutionContextBelongsToOuterScope; }
376             set { m_ExecutionContextBelongsToOuterScope = !value; }
377         }
378
379 #if !MONO && DEBUG
380         internal bool ForbidExecutionContextMutation
381         {
382             set { m_ForbidExecutionContextMutation = value; }
383         }
384 #endif
385
386         // note: please don't access this directly from mscorlib.  Use GetMutableExecutionContext or GetExecutionContextReader instead.
387         public  ExecutionContext ExecutionContext
388         {
389             [SecuritySafeCritical]
390             [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
391             get
392             {
393                 ExecutionContext result;
394                 if (this == Thread.CurrentThread)
395                     result = GetMutableExecutionContext();
396                 else
397                     result = m_ExecutionContext;
398
399                 return result;
400             }
401         }
402
403         [SecurityCritical]
404         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
405         internal ExecutionContext GetMutableExecutionContext()
406         {
407             Contract.Assert(Thread.CurrentThread == this);
408 #if !MONO && DEBUG
409             Contract.Assert(!m_ForbidExecutionContextMutation);
410 #endif
411             if (m_ExecutionContext == null)
412             {
413                 m_ExecutionContext = new ExecutionContext();
414             }
415             else if (!ExecutionContextBelongsToCurrentScope)
416             {
417                 ExecutionContext copy = m_ExecutionContext.CreateMutableCopy();
418                 m_ExecutionContext = copy;
419             }
420
421             ExecutionContextBelongsToCurrentScope = true;
422             return m_ExecutionContext;
423         }
424
425         [SecurityCritical]
426         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
427         internal void SetExecutionContext(ExecutionContext value, bool belongsToCurrentScope) 
428         {
429             m_ExecutionContext = value;
430             ExecutionContextBelongsToCurrentScope = belongsToCurrentScope;
431         }
432
433         [SecurityCritical]
434         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
435         internal void SetExecutionContext(ExecutionContext.Reader value, bool belongsToCurrentScope)
436         {
437             m_ExecutionContext = value.DangerousGetRawExecutionContext();
438             ExecutionContextBelongsToCurrentScope = belongsToCurrentScope;
439         }
440 #endif //!FEATURE_CORECLR
441
442 #if !MONO
443         [System.Security.SecurityCritical]  // auto-generated
444         [ResourceExposure(ResourceScope.None)]
445         [MethodImplAttribute(MethodImplOptions.InternalCall)]
446         private extern void StartInternal(IPrincipal principal, ref StackCrawlMark stackMark);
447 #endif
448 #if FEATURE_COMPRESSEDSTACK || MONO
449         /// <internalonly/>
450         [System.Security.SecurityCritical]  // auto-generated_required
451         [DynamicSecurityMethodAttribute()]
452         [Obsolete("Thread.SetCompressedStack is no longer supported. Please use the System.Threading.CompressedStack class")]         
453         public void SetCompressedStack( CompressedStack stack )
454         {
455             throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_ThreadAPIsNotSupported"));
456         }
457 #if !MONO
458         [System.Security.SecurityCritical]  // auto-generated
459         [ResourceExposure(ResourceScope.None)]
460         [MethodImplAttribute(MethodImplOptions.InternalCall), ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
461         internal extern IntPtr SetAppDomainStack( SafeCompressedStackHandle csHandle);
462
463         [System.Security.SecurityCritical]  // auto-generated
464         [ResourceExposure(ResourceScope.None)]
465         [MethodImplAttribute(MethodImplOptions.InternalCall), ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
466         internal extern void RestoreAppDomainStack( IntPtr appDomainStack);
467 #endif
468
469         /// <internalonly/>
470         [System.Security.SecurityCritical]  // auto-generated_required
471         [Obsolete("Thread.GetCompressedStack is no longer supported. Please use the System.Threading.CompressedStack class")]
472         public CompressedStack GetCompressedStack()
473         {
474             throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_ThreadAPIsNotSupported"));
475         }
476 #endif // #if FEATURE_COMPRESSEDSTACK
477 #if !MONO
478
479         // Helper method to get a logical thread ID for StringBuilder (for
480         // correctness) and for FileStream's async code path (for perf, to
481         // avoid creating a Thread instance).
482         [System.Security.SecurityCritical]  // auto-generated
483         [ResourceExposure(ResourceScope.None)]
484         [MethodImplAttribute(MethodImplOptions.InternalCall)]
485         internal extern static IntPtr InternalGetCurrentThread();
486
487         /*=========================================================================
488         ** Raises a ThreadAbortException in the thread, which usually
489         ** results in the thread's death. The ThreadAbortException is a special
490         ** exception that is not catchable. The finally clauses of all try
491         ** statements will be executed before the thread dies. This includes the
492         ** finally that a thread might be executing at the moment the Abort is raised.
493         ** The thread is not stopped immediately--you must Join on the
494         ** thread to guarantee it has stopped.
495         ** It is possible for a thread to do an unbounded amount of computation in
496         ** the finally's and thus indefinitely delay the threads death.
497         ** If Abort() is called on a thread that has not been started, the thread
498         ** will abort when Start() is called.
499         ** If Abort is called twice on the same thread, a DuplicateThreadAbort
500         ** exception is thrown.
501         =========================================================================*/
502
503 #if !FEATURE_CORECLR
504         [System.Security.SecuritySafeCritical]  // auto-generated
505         [SecurityPermissionAttribute(SecurityAction.Demand, ControlThread=true)]
506         public void Abort(Object stateInfo)
507         {
508             // If two aborts come at the same time, it is possible that the state info
509             //  gets set by one, and the actual abort gets delivered by another. But this
510             //  is not distinguishable by an application.
511             // The accessor helper will only set the value if it isn't already set,
512             //  and that particular bit of native code can test much faster than this
513             //  code could, because testing might cause a cross-appdomain marshalling.
514             AbortReason = stateInfo;
515
516             // Note: we demand ControlThread permission, then call AbortInternal directly
517             // rather than delegating to the Abort() function below. We do this to ensure
518             // that only callers with ControlThread are allowed to change the AbortReason
519             // of the thread. We call AbortInternal directly to avoid demanding the same
520             // permission twice.
521             AbortInternal();
522         }
523 #endif
524
525         #if FEATURE_CORECLR
526         [System.Security.SecurityCritical] // auto-generated
527         #else
528         [System.Security.SecuritySafeCritical]
529         #endif
530 #pragma warning disable 618
531         [SecurityPermissionAttribute(SecurityAction.Demand, ControlThread = true)]
532 #pragma warning restore 618
533         public void Abort()
534         {
535 #if FEATURE_LEGACYNETCF
536             if(CompatibilitySwitches.IsAppEarlierThanWindowsPhone8)
537             {
538                 System.Reflection.Assembly callingAssembly = System.Reflection.Assembly.GetCallingAssembly();
539                 if(callingAssembly != null && !callingAssembly.IsProfileAssembly)
540                 {
541                     string caller = new StackFrame(1).GetMethod().FullName;
542                     string callee = System.Reflection.MethodBase.GetCurrentMethod().FullName;
543                     throw new MethodAccessException(String.Format(
544                         CultureInfo.CurrentCulture,
545                         Environment.GetResourceString("Arg_MethodAccessException_WithCaller"),
546                         caller,
547                         callee));
548                 }
549             }
550 #endif // FEATURE_LEGACYNETCF
551             AbortInternal();
552         }
553
554         // Internal helper (since we can't place security demands on
555         // ecalls/fcalls).
556         [System.Security.SecurityCritical]  // auto-generated
557         [ResourceExposure(ResourceScope.None)]
558         [MethodImplAttribute(MethodImplOptions.InternalCall)]
559         private extern void AbortInternal();
560 #endif
561 #if (!FEATURE_CORECLR && !MONO) || MONO_FEATURE_THREAD_ABORT
562         /*=========================================================================
563         ** Resets a thread abort.
564         ** Should be called by trusted code only
565           =========================================================================*/
566         [System.Security.SecuritySafeCritical]  // auto-generated
567         [SecurityPermissionAttribute(SecurityAction.Demand, ControlThread=true)]
568         public static void ResetAbort()
569         {
570             Thread thread = Thread.CurrentThread;
571             if ((thread.ThreadState & ThreadState.AbortRequested) == 0)
572                 throw new ThreadStateException(Environment.GetResourceString("ThreadState_NoAbortRequested"));
573             thread.ResetAbortNative();
574             thread.ClearAbortReason();
575         }
576
577         [System.Security.SecurityCritical]  // auto-generated
578         [ResourceExposure(ResourceScope.None)]
579         [MethodImplAttribute(MethodImplOptions.InternalCall)]
580         private extern void ResetAbortNative();
581 #endif
582 #if (!FEATURE_CORECLR && !MONO) || MONO_FEATURE_THREAD_SUSPEND_RESUME
583         /*=========================================================================
584         ** Suspends the thread. If the thread is already suspended, this call has
585         ** no effect.
586         **
587         ** Exceptions: ThreadStateException if the thread has not been started or
588         **             it is dead.
589         =========================================================================*/
590         [System.Security.SecuritySafeCritical]  // auto-generated
591         [Obsolete("Thread.Suspend has been deprecated.  Please use other classes in System.Threading, such as Monitor, Mutex, Event, and Semaphore, to synchronize Threads or protect resources.  http://go.microsoft.com/fwlink/?linkid=14202", false)][SecurityPermission(SecurityAction.Demand, ControlThread=true)]
592         [SecurityPermission(SecurityAction.Demand, ControlThread=true)]
593         public void Suspend() { SuspendInternal(); }
594
595         // Internal helper (since we can't place security demands on
596         // ecalls/fcalls).
597         [System.Security.SecurityCritical]  // auto-generated
598         [ResourceExposure(ResourceScope.None)]
599         [MethodImplAttribute(MethodImplOptions.InternalCall)]
600         private extern void SuspendInternal();
601
602         /*=========================================================================
603         ** Resumes a thread that has been suspended.
604         **
605         ** Exceptions: ThreadStateException if the thread has not been started or
606         **             it is dead or it isn't in the suspended state.
607         =========================================================================*/
608         [System.Security.SecuritySafeCritical]  // auto-generated
609         [Obsolete("Thread.Resume has been deprecated.  Please use other classes in System.Threading, such as Monitor, Mutex, Event, and Semaphore, to synchronize Threads or protect resources.  http://go.microsoft.com/fwlink/?linkid=14202", false)]
610         [SecurityPermission(SecurityAction.Demand, ControlThread=true)]
611         public void Resume() { ResumeInternal(); }
612
613         // Internal helper (since we can't place security demands on
614         // ecalls/fcalls).
615         [System.Security.SecurityCritical]  // auto-generated
616         [ResourceExposure(ResourceScope.None)]
617         [MethodImplAttribute(MethodImplOptions.InternalCall)]
618         private extern void ResumeInternal();
619
620         /*=========================================================================
621         ** Interrupts a thread that is inside a Wait(), Sleep() or Join().  If that
622         ** thread is not currently blocked in that manner, it will be interrupted
623         ** when it next begins to block.
624         =========================================================================*/
625         [System.Security.SecuritySafeCritical]  // auto-generated
626         [SecurityPermission(SecurityAction.Demand, ControlThread=true)]
627         public void Interrupt() { InterruptInternal(); }
628
629         // Internal helper (since we can't place security demands on
630         // ecalls/fcalls).
631         [System.Security.SecurityCritical]  // auto-generated
632         [ResourceExposure(ResourceScope.None)]
633         [MethodImplAttribute(MethodImplOptions.InternalCall)]
634         private extern void InterruptInternal();
635 #endif
636
637         /*=========================================================================
638         ** Returns the priority of the thread.
639         **
640         ** Exceptions: ThreadStateException if the thread is dead.
641         =========================================================================*/
642
643         public ThreadPriority Priority {
644             [System.Security.SecuritySafeCritical]  // auto-generated
645             get { return (ThreadPriority)GetPriorityNative(); }
646             [System.Security.SecuritySafeCritical]  // auto-generated
647             [HostProtection(SelfAffectingThreading=true)]
648             set { SetPriorityNative((int)value); }
649         }
650         [System.Security.SecurityCritical]  // auto-generated
651         [ResourceExposure(ResourceScope.None)]
652         [MethodImplAttribute(MethodImplOptions.InternalCall)]
653         private extern int GetPriorityNative();
654         [System.Security.SecurityCritical]  // auto-generated
655         [ResourceExposure(ResourceScope.None)]
656         [MethodImplAttribute(MethodImplOptions.InternalCall)]
657         private extern void SetPriorityNative(int priority);
658 #if !MONO
659         /*=========================================================================
660         ** Returns true if the thread has been started and is not dead.
661         =========================================================================*/
662         public extern bool IsAlive {
663             [System.Security.SecuritySafeCritical]  // auto-generated
664             [MethodImpl(MethodImplOptions.InternalCall)]
665             get;
666         }
667
668         /*=========================================================================
669         ** Returns true if the thread is a threadpool thread.
670         =========================================================================*/
671         public extern bool IsThreadPoolThread {
672             [System.Security.SecuritySafeCritical]  // auto-generated
673             [MethodImpl(MethodImplOptions.InternalCall)]
674             get;
675         }
676 #endif
677         /*=========================================================================
678         ** Waits for the thread to die or for timeout milliseconds to elapse.
679         ** Returns true if the thread died, or false if the wait timed out. If
680         ** Timeout.Infinite is given as the parameter, no timeout will occur.
681         **
682         ** Exceptions: ArgumentException if timeout < 0.
683         **             ThreadInterruptedException if the thread is interrupted while waiting.
684         **             ThreadStateException if the thread has not been started yet.
685         =========================================================================*/
686         [System.Security.SecurityCritical]
687         [ResourceExposure(ResourceScope.None)]
688         [MethodImplAttribute(MethodImplOptions.InternalCall)]
689         private extern bool JoinInternal(int millisecondsTimeout);
690
691         [System.Security.SecuritySafeCritical]
692         [HostProtection(Synchronization=true, ExternalThreading=true)]
693         public void Join()
694         {
695             JoinInternal(Timeout.Infinite);
696         }
697
698         [System.Security.SecuritySafeCritical]
699         [HostProtection(Synchronization=true, ExternalThreading=true)]
700         public bool Join(int millisecondsTimeout)
701         {
702 #if MONO
703             if (millisecondsTimeout < Timeout.Infinite)
704                 throw new ArgumentOutOfRangeException("millisecondsTimeout", Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegOrNegative1"));
705 #endif
706             return JoinInternal(millisecondsTimeout);
707         }
708
709         [HostProtection(Synchronization=true, ExternalThreading=true)]
710         public bool Join(TimeSpan timeout)
711         {
712             long tm = (long)timeout.TotalMilliseconds;
713             if (tm < -1 || tm > (long) Int32.MaxValue)
714                 throw new ArgumentOutOfRangeException("timeout", Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegOrNegative1"));
715
716             return Join((int)tm);
717         }
718
719         /*=========================================================================
720         ** Suspends the current thread for timeout milliseconds. If timeout == 0,
721         ** forces the thread to give up the remainer of its timeslice.  If timeout
722         ** == Timeout.Infinite, no timeout will occur.
723         **
724         ** Exceptions: ArgumentException if timeout < 0.
725         **             ThreadInterruptedException if the thread is interrupted while sleeping.
726         =========================================================================*/
727         [System.Security.SecurityCritical]  // auto-generated
728         [ResourceExposure(ResourceScope.None)]
729         [MethodImplAttribute(MethodImplOptions.InternalCall)]
730         private static extern void SleepInternal(int millisecondsTimeout);
731
732         [System.Security.SecuritySafeCritical]  // auto-generated
733         public static void Sleep(int millisecondsTimeout)
734         {
735 #if MONO
736             if (millisecondsTimeout < Timeout.Infinite)
737                 throw new ArgumentOutOfRangeException("millisecondsTimeout", Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegOrNegative1"));
738 #endif
739             SleepInternal(millisecondsTimeout);
740 #if !MONO
741             // Ensure we don't return to app code when the pause is underway
742             if(AppDomainPauseManager.IsPaused)
743                 AppDomainPauseManager.ResumeEvent.WaitOneWithoutFAS();
744 #endif
745         }
746
747         public static void Sleep(TimeSpan timeout)
748         {
749             long tm = (long)timeout.TotalMilliseconds;
750             if (tm < -1 || tm > (long) Int32.MaxValue)
751                 throw new ArgumentOutOfRangeException("timeout", Environment.GetResourceString("ArgumentOutOfRange_NeedNonNegOrNegative1"));
752             Sleep((int)tm);
753         }
754
755 #if !MONO
756         /* wait for a length of time proportial to 'iterations'.  Each iteration is should
757            only take a few machine instructions.  Calling this API is preferable to coding
758            a explict busy loop because the hardware can be informed that it is busy waiting. */
759
760         [System.Security.SecurityCritical]  // auto-generated
761         [MethodImplAttribute(MethodImplOptions.InternalCall),
762          HostProtection(Synchronization=true,ExternalThreading=true),
763          ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success),
764          ResourceExposure(ResourceScope.None)]
765         private static extern void SpinWaitInternal(int iterations);
766
767         [System.Security.SecuritySafeCritical]  // auto-generated
768         [HostProtection(Synchronization=true,ExternalThreading=true),
769          ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
770         public static void SpinWait(int iterations)
771         {
772             SpinWaitInternal(iterations);
773         }
774 #endif
775         [System.Security.SecurityCritical]  // auto-generated
776         [ResourceExposure(ResourceScope.None)]
777         [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
778         [SuppressUnmanagedCodeSecurity]
779         [HostProtection(Synchronization = true, ExternalThreading = true),
780          ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
781         private static extern bool YieldInternal();
782
783         [System.Security.SecuritySafeCritical]  // auto-generated
784         [HostProtection(Synchronization = true, ExternalThreading = true),
785          ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
786         public static bool Yield()
787         {
788             return YieldInternal();
789         }
790
791 #if !MONO
792         public static Thread CurrentThread {
793             [System.Security.SecuritySafeCritical]  // auto-generated
794             [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
795             get {
796                 Contract.Ensures(Contract.Result<Thread>() != null);
797                 return GetCurrentThreadNative();
798             }
799         }
800         [System.Security.SecurityCritical]  // auto-generated
801         [ResourceExposure(ResourceScope.None)]
802         [MethodImplAttribute(MethodImplOptions.InternalCall), ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
803         private static extern Thread GetCurrentThreadNative();
804 #endif
805         [System.Security.SecurityCritical]  // auto-generated
806         private void SetStartHelper(Delegate start, int maxStackSize)
807         {
808 #if MONO
809             maxStackSize = GetProcessDefaultStackSize(maxStackSize);
810 #else
811 #if FEATURE_CORECLR
812             // We only support default stacks in CoreCLR
813             Contract.Assert(maxStackSize == 0);
814 #else
815             // Only fully-trusted code is allowed to create "large" stacks.  Partial-trust falls back to
816             // the default stack size.
817             ulong defaultStackSize = GetProcessDefaultStackSize();
818
819             if ((ulong)(uint)maxStackSize > defaultStackSize)
820             {
821                 try
822                 {
823                     SecurityPermission.Demand(PermissionType.FullTrust);
824                 }
825                 catch (SecurityException)
826                 {
827                     maxStackSize = (int)Math.Min(defaultStackSize, (ulong)(uint)int.MaxValue);
828                 }
829             }
830 #endif
831 #endif
832
833             ThreadHelper threadStartCallBack = new ThreadHelper(start);
834             if(start is ThreadStart)
835             {
836                 SetStart(new ThreadStart(threadStartCallBack.ThreadStart), maxStackSize);
837             }
838             else
839             {
840                 SetStart(new ParameterizedThreadStart(threadStartCallBack.ThreadStart), maxStackSize);
841             }                
842         }
843 #if !MONO
844         [SecurityCritical]
845         [ResourceExposure(ResourceScope.None)]
846         [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
847         [SuppressUnmanagedCodeSecurity]
848         private static extern ulong GetProcessDefaultStackSize();
849
850         /*=========================================================================
851         ** PRIVATE Sets the IThreadable interface for the thread. Assumes that
852         ** start != null.
853         =========================================================================*/
854         [System.Security.SecurityCritical]  // auto-generated
855         [ResourceExposure(ResourceScope.None)]
856         [MethodImplAttribute(MethodImplOptions.InternalCall)]
857         private extern void SetStart(Delegate start, int maxStackSize);
858
859         /*=========================================================================
860         ** Clean up the thread when it goes away.
861         =========================================================================*/
862         [System.Security.SecuritySafeCritical]  // auto-generated
863         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
864         ~Thread()
865         {
866             // Delegate to the unmanaged portion.
867             InternalFinalize();
868         }
869
870         [System.Security.SecurityCritical]  // auto-generated
871         [ResourceExposure(ResourceScope.None)]
872         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
873         [MethodImplAttribute(MethodImplOptions.InternalCall)]
874         private extern void InternalFinalize();
875
876 #if FEATURE_COMINTEROP
877         [System.Security.SecurityCritical]  // auto-generated
878         [ResourceExposure(ResourceScope.None)]
879         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
880         [MethodImplAttribute(MethodImplOptions.InternalCall)]
881         public extern void DisableComObjectEagerCleanup();
882 #endif //FEATURE_COMINTEROP
883
884         /*=========================================================================
885         ** Return whether or not this thread is a background thread.  Background
886         ** threads do not affect when the Execution Engine shuts down.
887         **
888         ** Exceptions: ThreadStateException if the thread is dead.
889         =========================================================================*/
890         public bool IsBackground {
891             [System.Security.SecuritySafeCritical]  // auto-generated
892             get { return IsBackgroundNative(); }
893             [System.Security.SecuritySafeCritical]  // auto-generated
894             [HostProtection(SelfAffectingThreading=true)]
895             set { SetBackgroundNative(value); }
896         }
897         [System.Security.SecurityCritical]  // auto-generated
898         [ResourceExposure(ResourceScope.None)]
899         [MethodImplAttribute(MethodImplOptions.InternalCall)]
900         private extern bool IsBackgroundNative();
901         [System.Security.SecurityCritical]  // auto-generated
902         [ResourceExposure(ResourceScope.None)]
903         [MethodImplAttribute(MethodImplOptions.InternalCall)]
904         private extern void SetBackgroundNative(bool isBackground);
905
906
907         /*=========================================================================
908         ** Return the thread state as a consistent set of bits.  This is more
909         ** general then IsAlive or IsBackground.
910         =========================================================================*/
911         public ThreadState ThreadState {
912             [System.Security.SecuritySafeCritical]  // auto-generated
913             get { return (ThreadState)GetThreadStateNative(); }
914         }
915
916         [System.Security.SecurityCritical]  // auto-generated
917         [ResourceExposure(ResourceScope.None)]
918         [MethodImplAttribute(MethodImplOptions.InternalCall)]
919         private extern int GetThreadStateNative();
920
921 #if FEATURE_COMINTEROP_APARTMENT_SUPPORT
922         /*=========================================================================
923         ** An unstarted thread can be marked to indicate that it will host a
924         ** single-threaded or multi-threaded apartment.
925         **
926         ** Exceptions: ArgumentException if state is not a valid apartment state
927         **             (ApartmentSTA or ApartmentMTA).
928         =========================================================================*/
929         [Obsolete("The ApartmentState property has been deprecated.  Use GetApartmentState, SetApartmentState or TrySetApartmentState instead.", false)]
930         public ApartmentState ApartmentState
931         {
932             [System.Security.SecuritySafeCritical]  // auto-generated
933             get
934             {
935                 return (ApartmentState)GetApartmentStateNative();
936             }
937
938             [System.Security.SecuritySafeCritical]  // auto-generated
939             [HostProtection(Synchronization=true, SelfAffectingThreading=true)]
940             set
941             {
942                 SetApartmentStateNative((int)value, true);
943             }
944         }
945
946         [System.Security.SecuritySafeCritical]  // auto-generated
947         public ApartmentState GetApartmentState()
948         {
949             return (ApartmentState)GetApartmentStateNative();
950         }
951
952         [System.Security.SecuritySafeCritical]  // auto-generated
953         [HostProtection(Synchronization=true, SelfAffectingThreading=true)]
954         public bool TrySetApartmentState(ApartmentState state)
955         {
956             return SetApartmentStateHelper(state, false);
957         }
958
959         [System.Security.SecuritySafeCritical]  // auto-generated
960         [HostProtection(Synchronization=true, SelfAffectingThreading=true)]
961         public void SetApartmentState(ApartmentState state)
962         {
963             bool result = SetApartmentStateHelper(state, true);
964             if (!result)
965                 throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_ApartmentStateSwitchFailed"));
966         }
967
968         [System.Security.SecurityCritical]  // auto-generated
969         private bool SetApartmentStateHelper(ApartmentState state, bool fireMDAOnMismatch)
970         {
971             ApartmentState retState = (ApartmentState)SetApartmentStateNative((int)state, fireMDAOnMismatch);
972
973             // Special case where we pass in Unknown and get back MTA.
974             //  Once we CoUninitialize the thread, the OS will still
975             //  report the thread as implicitly in the MTA if any
976             //  other thread in the process is CoInitialized.
977             if ((state == System.Threading.ApartmentState.Unknown) && (retState == System.Threading.ApartmentState.MTA))
978                 return true;
979             
980             if (retState != state)
981                 return false;
982
983             return true;            
984         }
985
986         [System.Security.SecurityCritical]  // auto-generated
987         [ResourceExposure(ResourceScope.None)]
988         [MethodImplAttribute(MethodImplOptions.InternalCall)]
989         private extern int GetApartmentStateNative();
990         [System.Security.SecurityCritical]  // auto-generated
991         [ResourceExposure(ResourceScope.None)]
992         [MethodImplAttribute(MethodImplOptions.InternalCall)]
993         private extern int SetApartmentStateNative(int state, bool fireMDAOnMismatch);
994         [System.Security.SecurityCritical]  // auto-generated
995         [ResourceExposure(ResourceScope.None)]
996         [MethodImplAttribute(MethodImplOptions.InternalCall)]
997         private extern void StartupSetApartmentStateInternal();
998 #endif // FEATURE_COMINTEROP_APARTMENT_SUPPORT
999 #endif
1000         /*=========================================================================
1001         ** Allocates an un-named data slot. The slot is allocated on ALL the
1002         ** threads.
1003         =========================================================================*/
1004         [HostProtection(SharedState=true, ExternalThreading=true)]
1005         public static LocalDataStoreSlot AllocateDataSlot()
1006         {
1007             return LocalDataStoreManager.AllocateDataSlot();
1008         }
1009
1010         /*=========================================================================
1011         ** Allocates a named data slot. The slot is allocated on ALL the
1012         ** threads.  Named data slots are "public" and can be manipulated by
1013         ** anyone.
1014         =========================================================================*/
1015         [HostProtection(SharedState=true, ExternalThreading=true)]
1016         public static LocalDataStoreSlot AllocateNamedDataSlot(String name)
1017         {
1018             return LocalDataStoreManager.AllocateNamedDataSlot(name);
1019         }
1020
1021         /*=========================================================================
1022         ** Looks up a named data slot. If the name has not been used, a new slot is
1023         ** allocated.  Named data slots are "public" and can be manipulated by
1024         ** anyone.
1025         =========================================================================*/
1026         [HostProtection(SharedState=true, ExternalThreading=true)]
1027         public static LocalDataStoreSlot GetNamedDataSlot(String name)
1028         {
1029             return LocalDataStoreManager.GetNamedDataSlot(name);
1030         }
1031
1032         /*=========================================================================
1033         ** Frees a named data slot. The slot is allocated on ALL the
1034         ** threads.  Named data slots are "public" and can be manipulated by
1035         ** anyone.
1036         =========================================================================*/
1037         [HostProtection(SharedState=true, ExternalThreading=true)]
1038         public static void FreeNamedDataSlot(String name)
1039         {
1040             LocalDataStoreManager.FreeNamedDataSlot(name);
1041         }
1042
1043         /*=========================================================================
1044         ** Retrieves the value from the specified slot on the current thread, for that thread's current domain.
1045         =========================================================================*/
1046         [HostProtection(SharedState=true, ExternalThreading=true)]
1047         [ResourceExposure(ResourceScope.AppDomain)]
1048         public static Object GetData(LocalDataStoreSlot slot)
1049         {
1050             LocalDataStoreHolder dls = s_LocalDataStore;
1051             if (dls == null)
1052             {
1053                 // Make sure to validate the slot even if we take the quick path
1054                 LocalDataStoreManager.ValidateSlot(slot);
1055                 return null;
1056             }
1057
1058             return dls.Store.GetData(slot);
1059         }
1060
1061         /*=========================================================================
1062         ** Sets the data in the specified slot on the currently running thread, for that thread's current domain.
1063         =========================================================================*/
1064         [HostProtection(SharedState=true, ExternalThreading=true)]
1065         [ResourceExposure(ResourceScope.AppDomain)]
1066         public static void SetData(LocalDataStoreSlot slot, Object data)
1067         {
1068             LocalDataStoreHolder dls = s_LocalDataStore;
1069
1070             // Create new DLS if one hasn't been created for this domain for this thread
1071             if (dls == null) {
1072                 dls = LocalDataStoreManager.CreateLocalDataStore();
1073                 s_LocalDataStore = dls;
1074             }
1075
1076             dls.Store.SetData(slot, data);
1077         }
1078 #if !MONO
1079
1080         // #threadCultureInfo
1081         //
1082         // Background:
1083         // In the desktop runtime, we allow a thread's cultures to travel with the thread
1084         // across AppDomain boundaries. Furthermore we update the native thread with the
1085         // culture of the managed thread. Because of security concerns and potential SxS
1086         // effects, in Silverlight we are making the changes listed below. 
1087         // 
1088         // Silverlight Changes:
1089         // - thread instance member cultures (CurrentCulture and CurrentUICulture) 
1090         //   confined within AppDomains
1091         // - changes to these properties don't affect the underlying native thread
1092         //
1093         // Ifdef:
1094         // FEATURE_LEAK_CULTURE_INFO      : CultureInfos can leak across AppDomains, not
1095         //                                  enabled in Silverlight
1096         // 
1097         // Implementation notes:
1098         // In Silverlight, culture members thread static (per Thread, per AppDomain). 
1099         //
1100         // Quirks:
1101         // An interesting side-effect of isolating cultures within an AppDomain is that we
1102         // now need to special case resource lookup for mscorlib, which transitions to the 
1103         // default domain to lookup resources. See Environment.cs for more details.
1104         // 
1105 #if FEATURE_LEAK_CULTURE_INFO
1106         [System.Security.SecurityCritical]  // auto-generated
1107         [ResourceExposure(ResourceScope.None)]
1108         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1109         static extern private bool nativeGetSafeCulture(Thread t, int appDomainId, bool isUI, ref CultureInfo safeCulture);
1110 #endif // FEATURE_LEAK_CULTURE_INFO
1111
1112         // As the culture can be customized object then we cannot hold any 
1113         // reference to it before we check if it is safe because the app domain 
1114         // owning this customized culture may get unloaded while executing this 
1115         // code. To achieve that we have to do the check using nativeGetSafeCulture 
1116         // as the thread cannot get interrupted during the FCALL. 
1117         // If the culture is safe (not customized or created in current app domain) 
1118         // then the FCALL will return a reference to that culture otherwise the 
1119         // FCALL will return failure. In case of failure we'll return the default culture.
1120         // If the app domain owning a customized culture that is set to teh thread and this
1121         // app domain get unloaded there is a code to clean up the culture from the thread
1122         // using the code in AppDomain::ReleaseDomainStores.
1123
1124         public CultureInfo CurrentUICulture {
1125             get {
1126                 Contract.Ensures(Contract.Result<CultureInfo>() != null);
1127 #if FEATURE_APPX
1128                 if(AppDomain.IsAppXModel()) {
1129                     return CultureInfo.GetCultureInfoForUserPreferredLanguageInAppX() ?? GetCurrentUICultureNoAppX();
1130                 } 
1131                 else 
1132 #endif
1133                 {
1134                     return GetCurrentUICultureNoAppX();
1135                 }
1136             }
1137
1138             [System.Security.SecuritySafeCritical]  // auto-generated
1139             [HostProtection(ExternalThreading=true)]
1140             set {
1141                 if (value == null) {
1142                     throw new ArgumentNullException("value");
1143                 }
1144                 Contract.EndContractBlock();
1145
1146                 //If they're trying to use a Culture with a name that we can't use in resource lookup,
1147                 //don't even let them set it on the thread.
1148                 CultureInfo.VerifyCultureName(value, true);
1149
1150                 // If you add more pre-conditions to this method, check to see if you also need to 
1151                 // add them to CultureInfo.DefaultThreadCurrentUICulture.set.
1152
1153 #if FEATURE_LEAK_CULTURE_INFO
1154                 if (nativeSetThreadUILocale(value.SortName) == false)
1155                 {
1156                     throw new ArgumentException(Environment.GetResourceString("Argument_InvalidResourceCultureName", value.Name));
1157                 }
1158                 value.StartCrossDomainTracking();
1159 #else
1160                 if (m_CurrentUICulture == null && m_CurrentCulture == null)
1161                     nativeInitCultureAccessors();
1162 #endif
1163
1164 #if FEATURE_LEGACYNETCF
1165                 if (CompatibilitySwitches.IsAppEarlierThanWindowsPhone8)
1166                 {
1167                     //
1168                     // NetCF had a 
1169
1170
1171
1172
1173
1174                     CultureInfo.SetCurrentUICultureQuirk(value);
1175                     return;
1176                 }
1177 #endif
1178                 if (!AppContextSwitches.NoAsyncCurrentCulture)
1179                 {
1180                     if (s_asyncLocalCurrentUICulture == null)
1181                     {
1182                         Interlocked.CompareExchange(ref s_asyncLocalCurrentUICulture, new AsyncLocal<CultureInfo>(AsyncLocalSetCurrentUICulture), null);
1183                     }
1184
1185                     // this one will set m_CurrentUICulture too
1186                     s_asyncLocalCurrentUICulture.Value = value;
1187                 }
1188                 else
1189                 {
1190                     m_CurrentUICulture = value;
1191                 }
1192             }
1193         }
1194
1195 #if FEATURE_LEAK_CULTURE_INFO
1196         [System.Security.SecuritySafeCritical]  // auto-generated
1197 #endif
1198         internal CultureInfo GetCurrentUICultureNoAppX() {
1199
1200             Contract.Ensures(Contract.Result<CultureInfo>() != null);
1201
1202             // Fetch a local copy of m_CurrentUICulture to 
1203             // avoid ----s that malicious user can introduce
1204             if (m_CurrentUICulture == null) {
1205                 CultureInfo appDomainDefaultUICulture = CultureInfo.DefaultThreadCurrentUICulture;
1206                 return (appDomainDefaultUICulture != null ? appDomainDefaultUICulture : CultureInfo.UserDefaultUICulture);
1207             }
1208
1209 #if FEATURE_LEAK_CULTURE_INFO
1210             CultureInfo culture = null;
1211
1212             if (!nativeGetSafeCulture(this, GetDomainID(), true, ref culture) || culture == null) {
1213                 return CultureInfo.UserDefaultUICulture;
1214             }
1215                 
1216             return culture;
1217 #else
1218             return m_CurrentUICulture;
1219 #endif
1220         }
1221
1222         // This returns the exposed context for a given context ID.
1223 #if FEATURE_LEAK_CULTURE_INFO
1224         [System.Security.SecurityCritical]  // auto-generated
1225         [ResourceExposure(ResourceScope.None)]
1226         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1227         static extern private bool nativeSetThreadUILocale(String locale);
1228 #endif
1229
1230         // As the culture can be customized object then we cannot hold any 
1231         // reference to it before we check if it is safe because the app domain 
1232         // owning this customized culture may get unloaded while executing this 
1233         // code. To achieve that we have to do the check using nativeGetSafeCulture 
1234         // as the thread cannot get interrupted during the FCALL. 
1235         // If the culture is safe (not customized or created in current app domain) 
1236         // then the FCALL will return a reference to that culture otherwise the 
1237         // FCALL will return failure. In case of failure we'll return the default culture.
1238         // If the app domain owning a customized culture that is set to teh thread and this
1239         // app domain get unloaded there is a code to clean up the culture from the thread
1240         // using the code in AppDomain::ReleaseDomainStores.
1241
1242         public CultureInfo CurrentCulture {
1243             get {
1244                 Contract.Ensures(Contract.Result<CultureInfo>() != null);
1245
1246 #if FEATURE_APPX
1247                 if(AppDomain.IsAppXModel()) {
1248                     return CultureInfo.GetCultureInfoForUserPreferredLanguageInAppX() ?? GetCurrentCultureNoAppX();
1249                 } 
1250                 else 
1251 #endif
1252                 {
1253                     return GetCurrentCultureNoAppX();
1254                 }
1255             }
1256
1257             [System.Security.SecuritySafeCritical]  // auto-generated
1258 #if FEATURE_LEAK_CULTURE_INFO
1259             [SecurityPermission(SecurityAction.Demand, ControlThread = true)]
1260 #endif
1261             set {
1262                 if (null==value) {
1263                     throw new ArgumentNullException("value");
1264                 }
1265                 Contract.EndContractBlock();
1266
1267                 // If you add more pre-conditions to this method, check to see if you also need to 
1268                 // add them to CultureInfo.DefaultThreadCurrentCulture.set.
1269
1270 #if FEATURE_LEAK_CULTURE_INFO
1271                 //If we can't set the nativeThreadLocale, we'll just let it stay
1272                 //at whatever value it had before.  This allows people who use
1273                 //just managed code not to be limited by the underlying OS.
1274                 CultureInfo.nativeSetThreadLocale(value.SortName);
1275                 value.StartCrossDomainTracking();
1276 #else
1277                 if (m_CurrentCulture == null && m_CurrentUICulture == null)
1278                     nativeInitCultureAccessors();
1279 #endif
1280
1281 #if FEATURE_LEGACYNETCF
1282                 if (CompatibilitySwitches.IsAppEarlierThanWindowsPhone8)
1283                 {
1284                     // See comment in CurrentUICulture setter
1285                     CultureInfo.SetCurrentCultureQuirk(value);
1286                     return;
1287                 }
1288 #endif
1289                 if (!AppContextSwitches.NoAsyncCurrentCulture)
1290                 {
1291                     if (s_asyncLocalCurrentCulture == null)
1292                     {
1293                         Interlocked.CompareExchange(ref s_asyncLocalCurrentCulture, new AsyncLocal<CultureInfo>(AsyncLocalSetCurrentCulture), null);
1294                     }
1295                     // this one will set m_CurrentCulture too
1296                     s_asyncLocalCurrentCulture.Value = value;
1297                 }
1298                 else
1299                 {
1300                     m_CurrentCulture = value;
1301                 }
1302             }
1303         }
1304
1305 #if FEATURE_LEAK_CULTURE_INFO
1306         [System.Security.SecuritySafeCritical]  // auto-generated
1307 #endif
1308         private CultureInfo GetCurrentCultureNoAppX() {
1309
1310             Contract.Ensures(Contract.Result<CultureInfo>() != null);
1311
1312             // Fetch a local copy of m_CurrentCulture to 
1313             // avoid ----s that malicious user can introduce
1314             if (m_CurrentCulture == null) {
1315                 CultureInfo appDomainDefaultCulture =  CultureInfo.DefaultThreadCurrentCulture;
1316                 return (appDomainDefaultCulture != null ? appDomainDefaultCulture : CultureInfo.UserDefaultCulture);
1317             }
1318
1319 #if FEATURE_LEAK_CULTURE_INFO
1320             CultureInfo culture = null;
1321               
1322             if (!nativeGetSafeCulture(this, GetDomainID(), false, ref culture) || culture == null) {
1323                 return CultureInfo.UserDefaultCulture;
1324             }
1325                 
1326             return culture;
1327 #else
1328             return m_CurrentCulture;
1329 #endif
1330
1331         }
1332
1333 #if! FEATURE_LEAK_CULTURE_INFO
1334         [System.Security.SecurityCritical]  // auto-generated
1335         [ResourceExposure(ResourceScope.None)]
1336         [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
1337         [SuppressUnmanagedCodeSecurity]
1338         private static extern void nativeInitCultureAccessors();
1339 #endif
1340
1341         /*=============================================================*/
1342
1343         /*======================================================================
1344         **  Current thread context is stored in a slot in the thread local store
1345         **  CurrentContext gets the Context from the slot.
1346         ======================================================================*/
1347 #if FEATURE_REMOTING
1348         public static Context CurrentContext
1349         {
1350             [System.Security.SecurityCritical]  // auto-generated_required
1351             get
1352             {
1353                 return CurrentThread.GetCurrentContextInternal();
1354             }
1355         }
1356
1357         [System.Security.SecurityCritical]  // auto-generated
1358         internal Context GetCurrentContextInternal()
1359         {
1360             if (m_Context == null)
1361             {
1362                 m_Context = Context.DefaultContext;
1363             }
1364             return m_Context;
1365         }
1366 #endif        
1367
1368
1369 #if FEATURE_IMPERSONATION
1370         // Get and set thread's current principal (for role based security).
1371         public static IPrincipal CurrentPrincipal
1372         {
1373             [System.Security.SecuritySafeCritical]  // auto-generated
1374             get
1375             {
1376                 lock (CurrentThread)
1377                 {
1378                     IPrincipal principal = (IPrincipal)
1379                         CallContext.Principal;
1380                     if (principal == null)
1381                     {
1382                         principal = GetDomain().GetThreadPrincipal();
1383                         CallContext.Principal = principal;
1384                     }
1385                     return principal;
1386                 }
1387             }
1388
1389             [System.Security.SecuritySafeCritical]  // auto-generated
1390             [SecurityPermissionAttribute(SecurityAction.Demand, Flags=SecurityPermissionFlag.ControlPrincipal)]
1391             set
1392             {
1393                 CallContext.Principal = value;
1394             }
1395         }
1396
1397         // Private routine called from unmanaged code to set an initial
1398         // principal for a newly created thread.
1399         [System.Security.SecurityCritical]  // auto-generated
1400         private void SetPrincipalInternal(IPrincipal principal)
1401         {
1402             GetMutableExecutionContext().LogicalCallContext.SecurityData.Principal = principal;
1403         }
1404 #endif // FEATURE_IMPERSONATION
1405
1406 #if FEATURE_REMOTING   
1407
1408         // This returns the exposed context for a given context ID.
1409         [System.Security.SecurityCritical]  // auto-generated
1410         [ResourceExposure(ResourceScope.None)]
1411         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1412         internal static extern Context GetContextInternal(IntPtr id);
1413
1414         [System.Security.SecurityCritical]  // auto-generated
1415         [ResourceExposure(ResourceScope.None)]
1416         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1417         internal extern Object InternalCrossContextCallback(Context ctx, IntPtr ctxID, Int32 appDomainID, InternalCrossContextDelegate ftnToCall, Object[] args);
1418
1419         [System.Security.SecurityCritical]  // auto-generated
1420         internal Object InternalCrossContextCallback(Context ctx, InternalCrossContextDelegate ftnToCall, Object[] args)
1421         {
1422             return InternalCrossContextCallback(ctx, ctx.InternalContextID, 0, ftnToCall, args);
1423         }
1424
1425         // CompleteCrossContextCallback is called by the EE after transitioning to the requested context
1426         private static Object CompleteCrossContextCallback(InternalCrossContextDelegate ftnToCall, Object[] args)
1427         {
1428             return ftnToCall(args);
1429         }
1430 #endif // FEATURE_REMOTING
1431
1432         /*======================================================================
1433         ** Returns the current domain in which current thread is running.
1434         ======================================================================*/
1435
1436         [System.Security.SecurityCritical]  // auto-generated
1437         [ResourceExposure(ResourceScope.None)]
1438         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1439         private static extern AppDomain GetDomainInternal();
1440         [System.Security.SecurityCritical]  // auto-generated
1441         [ResourceExposure(ResourceScope.None)]
1442         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1443         private static extern AppDomain GetFastDomainInternal();
1444
1445         [System.Security.SecuritySafeCritical]  // auto-generated
1446         public static AppDomain GetDomain()
1447         {
1448             Contract.Ensures(Contract.Result<AppDomain>() != null);
1449
1450
1451             AppDomain ad;
1452             ad = GetFastDomainInternal();
1453             if (ad == null)
1454                 ad = GetDomainInternal();
1455
1456 #if FEATURE_REMOTING        
1457             Contract.Assert(CurrentThread.m_Context == null || CurrentThread.m_Context.AppDomain == ad, "AppDomains on the managed & unmanaged threads should match");
1458 #endif
1459             return ad;
1460         }
1461
1462
1463         /*
1464          *  This returns a unique id to identify an appdomain.
1465          */
1466         public static int GetDomainID()
1467         {
1468             return GetDomain().GetId();
1469         }
1470
1471
1472         // Retrieves the name of the thread.
1473         //
1474         public  String Name {
1475             get {
1476                 return m_Name;
1477
1478             }
1479             [System.Security.SecuritySafeCritical]  // auto-generated
1480             [HostProtection(ExternalThreading=true)]
1481             set {
1482                 lock(this) {
1483                     if (m_Name != null)
1484                         throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_WriteOnce"));
1485                     m_Name = value;
1486
1487                     InformThreadNameChange(GetNativeHandle(), value, (value != null) ? value.Length : 0);
1488                 }
1489             }
1490         }
1491
1492         [System.Security.SecurityCritical]  // auto-generated
1493         [ResourceExposure(ResourceScope.None)]
1494         [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
1495         [SuppressUnmanagedCodeSecurity]
1496         private static extern void InformThreadNameChange(ThreadHandle t, String name, int len);
1497
1498         internal Object AbortReason {
1499             [System.Security.SecurityCritical]  // auto-generated
1500             get {
1501                 object result = null;
1502                 try
1503                 {
1504                     result = GetAbortReason();
1505                 }
1506                 catch (Exception e)
1507                 {
1508                     throw new InvalidOperationException(Environment.GetResourceString("InvalidOperation_ExceptionStateCrossAppDomain"), e);
1509                 }
1510                 return result;
1511             }
1512             [System.Security.SecurityCritical]  // auto-generated
1513             set { SetAbortReason(value); }
1514         }
1515
1516         /*
1517          *  This marks the beginning of a critical code region.
1518          */
1519         [System.Security.SecuritySafeCritical]  // auto-generated
1520         [HostProtection(Synchronization=true, ExternalThreading=true)]
1521         [ResourceExposure(ResourceScope.None)]
1522         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1523         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
1524         public static extern void BeginCriticalRegion();
1525
1526         /*
1527          *  This marks the end of a critical code region.
1528          */
1529         [System.Security.SecuritySafeCritical]  // auto-generated
1530         [HostProtection(Synchronization=true, ExternalThreading=true)]
1531         [ResourceExposure(ResourceScope.None)]
1532         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1533         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
1534         public static extern void EndCriticalRegion();
1535
1536         /*
1537          *  This marks the beginning of a code region that requires thread affinity.
1538          */
1539         [System.Security.SecurityCritical]  // auto-generated_required
1540         [ResourceExposure(ResourceScope.None)]
1541         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1542         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
1543         public static extern void BeginThreadAffinity();
1544
1545         /*
1546          *  This marks the end of a code region that requires thread affinity.
1547          */
1548         [System.Security.SecurityCritical]  // auto-generated_required
1549         [ResourceExposure(ResourceScope.None)]
1550         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1551         [ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
1552         public static extern void EndThreadAffinity();
1553
1554         /*=========================================================================
1555         ** Volatile Read & Write and MemoryBarrier methods.
1556         ** Provides the ability to read and write values ensuring that the values
1557         ** are read/written each time they are accessed.
1558         =========================================================================*/
1559
1560         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1561         public static byte VolatileRead(ref byte address)
1562         {
1563             byte ret = address;
1564             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1565             return ret;
1566         }
1567
1568         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1569         public static short VolatileRead(ref short address)
1570         {
1571             short ret = address;
1572             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1573             return ret;
1574         }
1575
1576         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1577         public static int VolatileRead(ref int address)
1578         {
1579             int ret = address;
1580             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1581             return ret;
1582         }
1583
1584         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1585         public static long VolatileRead(ref long address)
1586         {
1587             long ret = address;
1588             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1589             return ret;
1590         }
1591
1592         [CLSCompliant(false)]
1593         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1594         public static sbyte VolatileRead(ref sbyte address)
1595         {
1596             sbyte ret = address;
1597             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1598             return ret;
1599         }
1600
1601         [CLSCompliant(false)]
1602         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1603         public static ushort VolatileRead(ref ushort address)
1604         {
1605             ushort ret = address;
1606             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1607             return ret;
1608         }
1609
1610         [CLSCompliant(false)]
1611         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1612         public static uint VolatileRead(ref uint address)
1613         {
1614             uint ret = address;
1615             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1616             return ret;
1617         }
1618
1619         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1620         public static IntPtr VolatileRead(ref IntPtr address)
1621         {
1622             IntPtr ret = address;
1623             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1624             return ret;
1625         }
1626
1627         [CLSCompliant(false)]
1628         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1629         public static UIntPtr VolatileRead(ref UIntPtr address)
1630         {
1631             UIntPtr ret = address;
1632             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1633             return ret;
1634         }
1635
1636         [CLSCompliant(false)]
1637         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1638         public static ulong VolatileRead(ref ulong address)
1639         {
1640             ulong ret = address;
1641             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1642             return ret;
1643         }
1644
1645         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1646         public static float VolatileRead(ref float address)
1647         {
1648             float ret = address;
1649             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1650             return ret;
1651         }
1652
1653         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1654         public static double VolatileRead(ref double address)
1655         {
1656             double ret = address;
1657             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1658             return ret;
1659         }
1660
1661         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1662         public static Object VolatileRead(ref Object address)
1663         {
1664             Object ret = address;
1665             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1666             return ret;
1667         }
1668
1669         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1670         public static void VolatileWrite(ref byte address, byte value)
1671         {
1672             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1673             address = value;
1674         }
1675
1676         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1677         public static void VolatileWrite(ref short address, short value)
1678         {
1679             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1680             address = value;
1681         }
1682
1683         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1684         public static void VolatileWrite(ref int address, int value)
1685         {
1686             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1687             address = value;
1688         }
1689
1690         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1691         public static void VolatileWrite(ref long address, long value)
1692         {
1693             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1694             address = value;
1695         }
1696
1697         [CLSCompliant(false)]
1698         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1699         public static void VolatileWrite(ref sbyte address, sbyte value)
1700         {
1701             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1702             address = value;
1703         }
1704
1705         [CLSCompliant(false)]
1706         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1707         public static void VolatileWrite(ref ushort address, ushort value)
1708         {
1709             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1710             address = value;
1711         }
1712
1713         [CLSCompliant(false)]
1714         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1715         public static void VolatileWrite(ref uint address, uint value)
1716         {
1717             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1718             address = value;
1719         }
1720
1721         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1722         public static void VolatileWrite(ref IntPtr address, IntPtr value)
1723         {
1724             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1725             address = value;
1726         }
1727
1728         [CLSCompliant(false)]
1729         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1730         public static void VolatileWrite(ref UIntPtr address, UIntPtr value)
1731         {
1732             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1733             address = value;
1734         }
1735
1736         [CLSCompliant(false)]
1737         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1738         public static void VolatileWrite(ref ulong address, ulong value)
1739         {
1740             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1741             address = value;
1742         }
1743
1744         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1745         public static void VolatileWrite(ref float address, float value)
1746         {
1747             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1748             address = value;
1749         }
1750
1751         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1752         public static void VolatileWrite(ref double address, double value)
1753         {
1754             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1755             address = value;
1756         }
1757
1758         [MethodImplAttribute(MethodImplOptions.NoInlining)] // disable optimizations
1759         public static void VolatileWrite(ref Object address, Object value)
1760         {
1761             MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way.
1762             address = value;
1763         }
1764 #endif
1765         [System.Security.SecuritySafeCritical]  // auto-generated
1766         [ResourceExposure(ResourceScope.None)]
1767         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1768         public static extern void MemoryBarrier();
1769
1770         private static LocalDataStoreMgr LocalDataStoreManager
1771         {
1772             get 
1773             {
1774                 if (s_LocalDataStoreMgr == null)
1775                 {
1776                     Interlocked.CompareExchange(ref s_LocalDataStoreMgr, new LocalDataStoreMgr(), null);    
1777                 }
1778
1779                 return s_LocalDataStoreMgr;
1780             }
1781         }
1782
1783 #if !FEATURE_CORECLR && !MOBILE
1784         void _Thread.GetTypeInfoCount(out uint pcTInfo)
1785         {
1786             throw new NotImplementedException();
1787         }
1788
1789         void _Thread.GetTypeInfo(uint iTInfo, uint lcid, IntPtr ppTInfo)
1790         {
1791             throw new NotImplementedException();
1792         }
1793
1794         void _Thread.GetIDsOfNames([In] ref Guid riid, IntPtr rgszNames, uint cNames, uint lcid, IntPtr rgDispId)
1795         {
1796             throw new NotImplementedException();
1797         }
1798
1799         void _Thread.Invoke(uint dispIdMember, [In] ref Guid riid, uint lcid, short wFlags, IntPtr pDispParams, IntPtr pVarResult, IntPtr pExcepInfo, IntPtr puArgErr)
1800         {
1801             throw new NotImplementedException();
1802         }
1803 #endif
1804
1805 #if !MONO
1806         // Helper function to set the AbortReason for a thread abort.
1807         //  Checks that they're not alredy set, and then atomically updates
1808         //  the reason info (object + ADID).
1809         [System.Security.SecurityCritical]  // auto-generated
1810         [ResourceExposure(ResourceScope.None)]
1811         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1812         internal extern void SetAbortReason(Object o);
1813     
1814         // Helper function to retrieve the AbortReason from a thread
1815         //  abort.  Will perform cross-AppDomain marshalling if the object
1816         //  lives in a different AppDomain from the requester.
1817         [System.Security.SecurityCritical]  // auto-generated
1818         [ResourceExposure(ResourceScope.None)]
1819         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1820         internal extern Object GetAbortReason();
1821     
1822         // Helper function to clear the AbortReason.  Takes care of
1823         //  AppDomain related cleanup if required.
1824         [System.Security.SecurityCritical]  // auto-generated
1825         [ResourceExposure(ResourceScope.None)]
1826         [MethodImplAttribute(MethodImplOptions.InternalCall)]
1827         internal extern void ClearAbortReason();
1828 #endif
1829
1830     } // End of class Thread
1831
1832     // declaring a local var of this enum type and passing it by ref into a function that needs to do a
1833     // stack crawl will both prevent inlining of the calle and pass an ESP point to stack crawl to
1834     // Declaring these in EH clauses is illegal; they must declared in the main method body
1835     [Serializable]
1836     internal enum StackCrawlMark
1837     {
1838         LookForMe = 0,
1839         LookForMyCaller = 1,
1840         LookForMyCallersCaller = 2,
1841         LookForThread = 3
1842     }
1843
1844 }