2 using System.Diagnostics;
3 using System.Threading;
4 using System.Runtime.CompilerServices;
8 public static ManualResetEvent mre1 = new ManualResetEvent (false);
9 public static ManualResetEvent mre2 = new ManualResetEvent (false);
11 class StaticConstructor1
13 internal static bool gotToEnd, caughtException;
14 static StaticConstructor1 ()
17 Console.WriteLine ("StaticConstructor1.StaticConstructor1 (1)");
19 var sw = Stopwatch.StartNew ();
22 typeof (string).GetMethods ();
23 //XXX we assume that if we slept less than 900ms we got aborted
24 if (sw.ElapsedMilliseconds < 900)
25 throw new Exception ("Bad abort broke our sleep");
26 Console.WriteLine ("StaticConstructor1.StaticConstructor1 (2) waited {0}", sw.ElapsedMilliseconds);
28 } catch (Exception e) {
29 caughtException = true;
34 public static void Init ()
36 Console.WriteLine ("StaticConstructor1.Init");
40 [MethodImplAttribute (MethodImplOptions.NoInlining)]
41 static void IsStaticConstructor1Viable () {
42 new StaticConstructor1 ();
43 Console.WriteLine ("Did it get to the end? {0} Did it catch an exception {1}", StaticConstructor1.gotToEnd, StaticConstructor1.caughtException);
44 if (!StaticConstructor1.gotToEnd) /* the TAE must not land during a .cctor */
46 if (StaticConstructor1.caughtException)
53 Console.WriteLine ("Test 1:");
58 Thread thread = new Thread (() => {
60 StaticConstructor1.Init ();
61 } catch (Exception e) {
62 Console.WriteLine ("StaticConstructor1::init caught exception {0}", e);
64 if (!(e is ThreadAbortException))
71 Driver.mre1.WaitOne ();
73 // The ThreadAbortException should land while in
74 // the StaticConstructor1.cctor. The exception should
75 // be queued, and be rethrown when exiting the cctor.
80 //is StaticConstructor1 viable?
82 IsStaticConstructor1Viable ();
83 Console.WriteLine ("StaticConstructor1 is viable"); /* a TAE doesn't make a type unusable */
84 } catch (TypeInitializationException e) {
85 Console.WriteLine ("StaticConstructor1 not viable");
90 class StaticConstructor2Exception : Exception {}
92 class StaticConstructor2
94 static StaticConstructor2 ()
96 Console.WriteLine ("StaticConstructor2.StaticConstructor2 (1)");
98 throw new StaticConstructor2Exception ();
101 Console.WriteLine ("StaticConstructor2.StaticConstructor2 (2)");
104 public static void Init ()
106 Console.WriteLine ("StaticConstructor2.Init");
110 [MethodImplAttribute (MethodImplOptions.NoInlining)]
111 static void IsStaticConstructor2Viable () {
112 new StaticConstructor2 ();
118 Console.WriteLine ("Test 2:");
120 Driver.mre1.Reset ();
121 Driver.mre2.Reset ();
123 Thread thread = new Thread (() => {
125 StaticConstructor2.Init ();
126 } catch (TypeInitializationException e) {
127 Console.WriteLine (e);
129 if (!(e.InnerException is StaticConstructor2Exception))
136 Driver.mre1.WaitOne ();
138 // A InvalidOperationException should be thrown while in
139 // the StaticConstructor2.cctor. The exception should
140 // be wrapped in a TypeInitializationException.
142 if (Driver.mre2.WaitOne (500)) {
143 /* We shouldn't reach Driver.mre.Set () in StaticConstructor2.cctor */
144 Environment.Exit (4);
149 //is StaticConstructor2 viable?
151 IsStaticConstructor2Viable ();
152 Console.WriteLine ("StaticConstructor2 is viable");
153 /* A regular exception escaping the .cctor makes the type not usable */
154 Environment.Exit (5);
155 } catch (TypeInitializationException e) {
156 Console.WriteLine ("StaticConstructor2 not viable");
161 class StaticConstructor3
163 static StaticConstructor3 ()
165 Console.WriteLine ("StaticConstructor3.StaticConstructor3 (1)");
167 Thread.CurrentThread.Abort ();
170 Console.WriteLine ("StaticConstructor3.StaticConstructor3 (2)");
171 Environment.Exit (6);
174 public static void Init ()
176 Console.WriteLine ("StaticConstructor3.Init");
180 [MethodImplAttribute (MethodImplOptions.NoInlining)]
181 static void IsStaticConstructor3Viable () {
182 new StaticConstructor3 ();
187 Console.WriteLine ("Test 3:");
188 bool catched_abort = false;
190 Driver.mre1.Reset ();
191 Driver.mre2.Reset ();
193 Thread thread = new Thread (() => {
195 StaticConstructor3.Init ();
196 Console.WriteLine ("cctor3 didn't throw?!?!");
197 /* StaticConstructor3 self aborted */
198 Environment.Exit (7);
199 } catch (ThreadAbortException e) {
200 Console.WriteLine ("TEST 3: aborted {0}", e);
201 catched_abort = true;
207 Driver.mre1.WaitOne ();
209 // A InvalidOperationException should be thrown while in
210 // the StaticConstructor2.cctor. The exception should
211 // be wrapped in a TypeInitializationException.
215 // Did we catch the abort
217 Environment.Exit (8);
219 //is StaticConstructor2 viable?
221 IsStaticConstructor3Viable ();
222 Console.WriteLine ("StaticConstructor3 is viable");
223 /* A regular exception escaping the .cctor makes the type not usable */
224 Environment.Exit (9);
225 } catch (TypeInitializationException e) {
226 Console.WriteLine ("StaticConstructor3 not viable");
234 class StaticConstructor4
236 internal static bool gotToEnd, caughtException;
238 static StaticConstructor4 ()
241 Console.WriteLine ("StaticConstructor4.StaticConstructor4 (1)");
243 var sw = Stopwatch.StartNew ();
246 typeof (string).GetMethods ();
247 //XXX we assume that if we slept less than 900ms we got aborted
248 if (sw.ElapsedMilliseconds < 900)
249 throw new Exception ("Bad abort broke our sleep");
250 Console.WriteLine ("StaticConstructor4.StaticConstructor4 (2) waited {0}", sw.ElapsedMilliseconds);
252 } catch (Exception e) {
253 caughtException = true;
258 public static void Init ()
260 Console.WriteLine ("StaticConstructor4.Init");
264 static bool got_to_the_end_of_the_finally = false;
266 [MethodImplAttribute (MethodImplOptions.NoInlining)]
267 static void IsStaticConstructor4Viable () {
268 new StaticConstructor4 ();
269 Console.WriteLine ("IsStaticConstructor4Viable: Did it get to the end? {0} Did it catch an exception {1} and end of the finally block {2}", StaticConstructor4.gotToEnd, StaticConstructor4.caughtException, got_to_the_end_of_the_finally);
270 if (!StaticConstructor4.gotToEnd) /* the TAE must not land during a .cctor */
271 Environment.Exit (10);
272 if (StaticConstructor4.caughtException)
273 Environment.Exit (11);
278 Console.WriteLine ("Test 4:");
280 Driver.mre1.Reset ();
281 Driver.mre2.Reset ();
283 Thread thread = new Thread (() => {
288 StaticConstructor4.Init ();
289 Console.WriteLine ("Test 4: After the cctor");
290 got_to_the_end_of_the_finally = true;
292 } catch (Exception e) {
293 Console.WriteLine ("StaticConstructor4::init caught exception {0}", e);
294 if (!(e is ThreadAbortException))
296 if (!got_to_the_end_of_the_finally)
297 throw new Exception ("Test 4: did not get to the end of the cctor");
303 Driver.mre1.WaitOne ();
305 // The ThreadAbortException should land while in
306 // the StaticConstructor4.cctor. The exception should
307 // be queued, and be rethrown when exiting the cctor.
312 if (!got_to_the_end_of_the_finally) {
313 Console.WriteLine ("Did not get to the end of test 4 cctor");
314 Environment.Exit (12);
317 //is StaticConstructor4viable?
319 IsStaticConstructor4Viable ();
320 Console.WriteLine ("StaticConstructor4 is viable"); /* a TAE doesn't make a type unusable */
321 } catch (TypeInitializationException e) {
322 Console.WriteLine ("StaticConstructor4 not viable");
323 Environment.Exit (13);
328 class StaticConstructor5 {
329 public static bool catched_exception = false;
330 static StaticConstructor5 ()
333 Driver.mre2.WaitOne ();
335 throw new Exception ();
336 } catch (Exception) {
337 Console.WriteLine ("Catched exception in cctor");
338 catched_exception = true;
345 bool catched_abort = false;
346 Driver.mre1.Reset ();
347 Driver.mre2.Reset ();
348 Thread thread = new Thread (() => {
350 new StaticConstructor5 ();
351 } catch (ThreadAbortException) {
352 Console.WriteLine ("Catched thread abort");
353 catched_abort = true;
358 Driver.mre1.WaitOne ();
364 if (!StaticConstructor5.catched_exception)
365 Environment.Exit (14);
367 Environment.Exit (15);
370 public static int Main ()
377 Console.WriteLine ("done, all things good");