How to switch context from fiber to original fiber?
Patrick Jeeves via Digitalmars-d
digitalmars-d at puremagic.com
Fri Nov 21 14:45:41 PST 2014
So I've been using an event range rather than an event loop or
event/listener system; because I realized I could process events
more effectively using a recursive descent parser on them. So I
made this class to strip the events into different ranges and
send them to different parsers:
auto demultiplex(alias attrFunc, string functional, Range)(Range
r)
{
alias attr = std.functional.unaryFun!(attrFunc);
alias T = ElementType!(Range);
struct SlaveRange {
private T** _front;
private Fiber _fiber;
this(T ** it) {
_front = it;
_fiber = Fiber.getThis();
}
@property bool empty() const { return *_front is null; }
@property T front() const { return *(*_front); }
void popFront() { _fiber.call(); }
}
struct MasterRange {
private SlaveRange _slave;
private Range _input;
private T _cur;
private T * _front;
private Fiber _fiber;
private void run() {
mixin("_slave." ~ functional ~ ";");
}
private void call() {
if(_fiber.state != Fiber.State.TERM)
_fiber.call();
}
this(Range ins) {
_input = ins;
_fiber = new Fiber(&run);
_slave = &_front;
popFront();
_front = &_cur;
}
@property T front() const { return *_front; }
@property bool empty() const { return _front is null; }
void popFront() {
while(!_input.empty) {
_cur = _input.front;
_input.popFront();
final switch(attr(_cur)) {
case -1: break;
case 0: return;
case 1: call(); break;
case 2: call(); return;
}
}
_front = null;
}
}
return MasterRange(r);
}
the problem is that when the SlaveRange is constructed it needs
to know the current fiber, but if it isn't called from a fiber
then it returns null and can't switch back. And I can't use
yeild because I don't want to return to the calling fiber, that
doesn't help me.
More information about the Digitalmars-d
mailing list