1 using System;
  2 using System.Threading.Fibers;
  3 
  4 public class Context
  5 {
  6     public nothrow Context() : mainFiber(null)otherFiber(null)runningFiber(null)otherFiberRunning(false)
  7     {
  8     }
  9     public nothrow void SetFibers(Fiber* mainFiber_Fiber* otherFiber_)
 10     {
 11         mainFiber = mainFiber_;
 12         otherFiber = otherFiber_;
 13         runningFiber = mainFiber;
 14     }
 15     public nothrow void SetOtherFiberRunning(bool running)
 16     {
 17         otherFiberRunning = running;
 18     }
 19     public nothrow bool IsOtherFiberRunning() const
 20     {
 21         return otherFiberRunning;
 22     }
 23     public nothrow void Switch()
 24     {
 25         if (runningFiber == mainFiber)
 26         {
 27             runningFiber = otherFiber;
 28             SwitchToFiber(*otherFiber);
 29         }
 30         else
 31         {
 32             runningFiber = mainFiber;
 33             SwitchToFiber(*mainFiber);
 34         }
 35     }
 36     private Fiber* mainFiber;
 37     private Fiber* otherFiber;
 38     private Fiber* runningFiber;
 39     private bool otherFiberRunning;
 40 }
 41 
 42 public void FiberHelper(Context* context)
 43 {
 44     Console.Out() << "in fiber helper" << endl();
 45     int count = 1;
 46     while (count <= 3)
 47     {
 48         Console.Out() << "switching context from fiber helper, count = " << count << endl();
 49         context->Switch();
 50         Console.Out() << "back in fiber helper, count = " << count << endl();
 51         ++count;
 52     }
 53     Console.Out() << "exiting fiber helper" << endl();
 54 }
 55 
 56 public void FiberFunc(void* data)
 57 {
 58     Console.Out() << "in fiber" << endl();
 59     Context* context = cast<Context*>(data);
 60     try
 61     {
 62         context->SetOtherFiberRunning(true);
 63         context->Switch();
 64         FiberHelper(context);
 65         context->SetOtherFiberRunning(false);
 66         Console.Out() << "fiber exiting" << endl();
 67     }
 68     catch (const Exception& ex)
 69     {
 70         Console.Error() << "fiber got exception: " << ex.Message() << endl();
 71         context->SetOtherFiberRunning(false);
 72     }
 73     context->Switch();
 74 }
 75 
 76 public int main()
 77 {
 78     try
 79     {
 80         Context context;
 81         Fiber mainFiber = Fiber.FromCurrentThread();
 82         FiberFunction fiberFunction = FiberFunc;
 83         Fiber otherFiber(fiberFunction&context);
 84         context.SetFibers(&mainFiber&otherFiber);
 85         context.Switch();
 86         Console.Out() << "back in main fiber" << endl();
 87         while (context.IsOtherFiberRunning())
 88         {
 89             Console.Out() << "switch context from main fiber" << endl();
 90             context.Switch();
 91             Console.Out() << "back in main fiber" << endl();
 92         }
 93         Console.Out() << "exiting main" << endl();
 94     }
 95     catch (const Exception& ex)
 96     {
 97         Console.Error() << "main got exception: " << ex.Message() << endl();
 98         return 1;
 99     }
100     return 0;
101 }