Code for the Iterator Example (p45-50
book)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using Microsoft.Ccr.Core;
using Microsoft.Dss.Core.Attributes;
using Microsoft.Dss.ServiceModel.Dssp;
using Microsoft.Dss.ServiceModel.DsspServiceBase;
using W3C.Soap;
using submgr = Microsoft.Dss.Services.SubscriptionManager;
using System.Threading;
namespace SpawnTest // Do not forget to change that namespace accordingly
{
[Contract(Contract.Identifier)]
[DisplayName("SpawnTest")]
[Description("SpawnTest service (no description provided)")]
[ActivationSettings(ShareDispatcher=false, ExecutionUnitsPerDispatcher=6)]
class SpawnTestService : DsspServiceBase
{
/// <summary>
/// Service state
/// </summary>
[ServiceState]
SpawnTestState _state = new SpawnTestState();
/// <summary>
/// Main service port
/// </summary>
[ServicePort("/SpawnTest", AllowMultipleInstances = true)]
SpawnTestOperations _mainPort = new SpawnTestOperations();
[SubscriptionManagerPartner]
submgr.SubscriptionManagerPort _submgrPort = new submgr.SubscriptionManagerPort();
/// <summary>
/// Service constructor
/// </summary>
public SpawnTestService(DsspServiceCreationPort creationPort)
: base(creationPort)
{
}
/// <summary>
/// Service start
/// </summary>
protected override void Start()
{
base.Start();
//Compare the results form the following code
//1.
//Spawn(RunFromIterator); // or simply RunFromIterator();
////2.
//SpawnIterator(IteratorExample);
//SpawnIterator(IteratorExample);
////3.
SpawnIterator<int>(5, SpawnIteratorExample);
Console.WriteLine("Spawn Iterator executed...");
}
void RunFromIterator()
{
Dispatcher d = new Dispatcher(4, "test Pool");
DispatcherQueue taskQ = new DispatcherQueue("Test Queue", d);
Console.WriteLine("Before Iterator submitted - thread {0}", Thread.CurrentThread.ManagedThreadId);
Arbiter.Activate(taskQ,
Arbiter.FromIteratorHandler(IteratorExample),
Arbiter.FromIteratorHandler(IteratorExample));
Console.WriteLine("After Iterator submitted - thread {0}",
Thread.CurrentThread.ManagedThreadId);
}
private static IEnumerator<ITask> IteratorExample()
{
Port<int> p1 = new Port<int>();
Port<int> p2 = new Port<int>();
p1.Post(0);
bool done = false;
while (!done)
{
yield return Arbiter.Receive(false, p1, delegate(int i)
{
Console.WriteLine("P1 Thread {0}: {1}", Thread.CurrentThread.ManagedThreadId, i);
p2.Post(i + 1);
}
);
yield return Arbiter.Receive(false, p2, delegate(int i)
{
Console.WriteLine("P2 Thread {0}: {1}", Thread.CurrentThread.ManagedThreadId, i);
if (i >= 10)
done = true;
else
p1.Post(i + 1);
}
);
}
yield break;
}
private static IEnumerator<ITask> SpawnIteratorExample(int n)
{
Port<int> p1 = new Port<int>();
Port<int> p2 = new Port<int>();
p1.Post(n);
bool done = false;
while (!done)
{
yield return Arbiter.Receive(false, p1, delegate(int i)
{
Console.WriteLine("P1 Thread {0}: {1}", Thread.CurrentThread.ManagedThreadId, i);
p2.Post(i + 1);
}
);
yield return Arbiter.Receive(false, p2, delegate(int i)
{
Console.WriteLine("P2 Thread {0}: {1}", Thread.CurrentThread.ManagedThreadId, i);
if (i >= n+10)
done = true;
else
p1.Post(i + 1);
}
);
}
yield break;
}
/// <summary>
/// Handles Subscribe messages
/// </summary>
/// <param name="subscribe">the subscribe request</param>
[ServiceHandler]
public void SubscribeHandler(Subscribe subscribe)
{
SubscribeHelper(_submgrPort, subscribe.Body, subscribe.ResponsePort);
}
}
}