Switch to container.queue. Remove PendingQueue
This commit is contained in:
parent
1123d01e6c
commit
f7f92e7906
@ -10,6 +10,7 @@
|
||||
*
|
||||
* ---
|
||||
* import tanya.async;
|
||||
* import tanya.memory;
|
||||
* import tanya.network.socket;
|
||||
*
|
||||
* class EchoProtocol : TransmissionControlProtocol
|
||||
@ -33,44 +34,48 @@
|
||||
*
|
||||
* void main()
|
||||
* {
|
||||
* auto address = new InternetAddress("127.0.0.1", cast(ushort) 8192);
|
||||
* auto address = theAllocator.make!InternetAddress("127.0.0.1", cast(ushort) 8192);
|
||||
*
|
||||
* version (Windows)
|
||||
* {
|
||||
* auto sock = new OverlappedStreamSocket(AddressFamily.INET);
|
||||
* auto sock = theAllocator.make!OverlappedStreamSocket(AddressFamily.INET);
|
||||
* }
|
||||
* else
|
||||
* {
|
||||
* auto sock = new StreamSocket(AddressFamily.INET);
|
||||
* auto sock = theAllocator.make!StreamSocket(AddressFamily.INET);
|
||||
* sock.blocking = false;
|
||||
* }
|
||||
*
|
||||
* sock.bind(address);
|
||||
* sock.listen(5);
|
||||
*
|
||||
* auto io = new ConnectionWatcher(sock);
|
||||
* auto io = theAllocator.make!ConnectionWatcher(sock);
|
||||
* io.setProtocol!EchoProtocol;
|
||||
*
|
||||
* defaultLoop.start(io);
|
||||
* defaultLoop.run();
|
||||
*
|
||||
* sock.shutdown();
|
||||
* theAllocator.dispose(io);
|
||||
* theAllocator.dispose(sock);
|
||||
* theAllocator.dispose(address);
|
||||
* }
|
||||
* ---
|
||||
*/
|
||||
module tanya.async.loop;
|
||||
|
||||
import tanya.async.protocol;
|
||||
import tanya.async.transport;
|
||||
import tanya.async.watcher;
|
||||
import tanya.container.buffer;
|
||||
import tanya.memory;
|
||||
import tanya.memory.mmappool;
|
||||
import tanya.network.socket;
|
||||
import core.time;
|
||||
import std.algorithm.iteration;
|
||||
import std.algorithm.mutation;
|
||||
import std.typecons;
|
||||
import tanya.async.protocol;
|
||||
import tanya.async.transport;
|
||||
import tanya.async.watcher;
|
||||
import tanya.container.buffer;
|
||||
import tanya.container.queue;
|
||||
import tanya.memory;
|
||||
import tanya.memory.mmappool;
|
||||
import tanya.network.socket;
|
||||
|
||||
version (DisableBackends)
|
||||
{
|
||||
@ -126,9 +131,9 @@ alias EventMask = BitFlags!Event;
|
||||
abstract class Loop
|
||||
{
|
||||
/// Pending watchers.
|
||||
protected PendingQueue!Watcher pendings;
|
||||
protected Queue!Watcher pendings;
|
||||
|
||||
protected PendingQueue!Watcher swapPendings;
|
||||
protected Queue!Watcher swapPendings;
|
||||
|
||||
/**
|
||||
* Returns: Maximal event count can be got at a time
|
||||
@ -144,8 +149,8 @@ abstract class Loop
|
||||
*/
|
||||
this()
|
||||
{
|
||||
pendings = MmapPool.instance.make!(PendingQueue!Watcher);
|
||||
swapPendings = MmapPool.instance.make!(PendingQueue!Watcher);
|
||||
pendings = MmapPool.instance.make!(Queue!Watcher);
|
||||
swapPendings = MmapPool.instance.make!(Queue!Watcher);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -153,7 +158,16 @@ abstract class Loop
|
||||
*/
|
||||
~this()
|
||||
{
|
||||
foreach (w; pendings)
|
||||
{
|
||||
MmapPool.instance.dispose(w);
|
||||
}
|
||||
MmapPool.instance.dispose(pendings);
|
||||
|
||||
foreach (w; swapPendings)
|
||||
{
|
||||
MmapPool.instance.dispose(w);
|
||||
}
|
||||
MmapPool.instance.dispose(swapPendings);
|
||||
}
|
||||
|
||||
@ -287,7 +301,6 @@ abstract class Loop
|
||||
*/
|
||||
class BadLoopException : Exception
|
||||
{
|
||||
@nogc:
|
||||
/**
|
||||
* Params:
|
||||
* file = The file where the exception occurred.
|
||||
@ -295,7 +308,7 @@ class BadLoopException : Exception
|
||||
* next = The previous exception in the chain of exceptions, if any.
|
||||
*/
|
||||
this(string file = __FILE__, size_t line = __LINE__, Throwable next = null)
|
||||
pure @safe nothrow const
|
||||
pure nothrow const @safe @nogc
|
||||
{
|
||||
super("Event loop cannot be initialized.", file, line, next);
|
||||
}
|
||||
@ -352,132 +365,3 @@ body
|
||||
}
|
||||
|
||||
private Loop defaultLoop_;
|
||||
|
||||
/**
|
||||
* Queue.
|
||||
*
|
||||
* Params:
|
||||
* T = Content type.
|
||||
*/
|
||||
class PendingQueue(T)
|
||||
{
|
||||
/**
|
||||
* Creates a new $(D_PSYMBOL Queue).
|
||||
*/
|
||||
this()
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes all elements from the queue.
|
||||
*/
|
||||
~this()
|
||||
{
|
||||
foreach (e; this)
|
||||
{
|
||||
MmapPool.instance.dispose(e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns: First element.
|
||||
*/
|
||||
@property ref T front()
|
||||
in
|
||||
{
|
||||
assert(!empty);
|
||||
}
|
||||
body
|
||||
{
|
||||
return first.next.content;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts a new element.
|
||||
*
|
||||
* Params:
|
||||
* x = New element.
|
||||
*
|
||||
* Returns: $(D_KEYWORD this).
|
||||
*/
|
||||
typeof(this) insertBack(T x)
|
||||
{
|
||||
Entry* temp = MmapPool.instance.make!Entry;
|
||||
|
||||
temp.content = x;
|
||||
|
||||
if (empty)
|
||||
{
|
||||
first.next = rear = temp;
|
||||
}
|
||||
else
|
||||
{
|
||||
rear.next = temp;
|
||||
rear = rear.next;
|
||||
}
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
alias insert = insertBack;
|
||||
|
||||
/**
|
||||
* Inserts a new element.
|
||||
*
|
||||
* Params:
|
||||
* x = New element.
|
||||
*
|
||||
* Returns: $(D_KEYWORD this).
|
||||
*/
|
||||
typeof(this) opOpAssign(string Op)(ref T x)
|
||||
if (Op == "~")
|
||||
{
|
||||
return insertBack(x);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns: $(D_KEYWORD true) if the queue is empty.
|
||||
*/
|
||||
@property bool empty() const @safe pure nothrow
|
||||
{
|
||||
return first.next is null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Move position to the next element.
|
||||
*
|
||||
* Returns: $(D_KEYWORD this).
|
||||
*/
|
||||
typeof(this) popFront()
|
||||
in
|
||||
{
|
||||
assert(!empty);
|
||||
}
|
||||
body
|
||||
{
|
||||
auto n = first.next.next;
|
||||
|
||||
MmapPool.instance.dispose(first.next);
|
||||
first.next = n;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Queue entry.
|
||||
*/
|
||||
protected struct Entry
|
||||
{
|
||||
/// Queue item content.
|
||||
T content;
|
||||
|
||||
/// Next list item.
|
||||
Entry* next;
|
||||
}
|
||||
|
||||
/// The first element of the list.
|
||||
protected Entry first;
|
||||
|
||||
/// The last element of the list.
|
||||
protected Entry* rear;
|
||||
}
|
||||
|
@ -10,15 +10,16 @@
|
||||
*/
|
||||
module tanya.async.watcher;
|
||||
|
||||
import std.functional;
|
||||
import std.exception;
|
||||
import tanya.async.loop;
|
||||
import tanya.async.protocol;
|
||||
import tanya.async.transport;
|
||||
import tanya.container.buffer;
|
||||
import tanya.container.queue;
|
||||
import tanya.memory;
|
||||
import tanya.memory.mmappool;
|
||||
import tanya.network.socket;
|
||||
import std.functional;
|
||||
import std.exception;
|
||||
|
||||
version (Windows)
|
||||
{
|
||||
@ -52,7 +53,7 @@ class ConnectionWatcher : Watcher
|
||||
/// Protocol factory.
|
||||
protected Protocol delegate() protocolFactory;
|
||||
|
||||
package PendingQueue!IOWatcher incoming;
|
||||
package Queue!IOWatcher incoming;
|
||||
|
||||
/**
|
||||
* Params:
|
||||
@ -61,7 +62,7 @@ class ConnectionWatcher : Watcher
|
||||
this(Socket socket)
|
||||
{
|
||||
socket_ = socket;
|
||||
incoming = MmapPool.instance.make!(PendingQueue!IOWatcher);
|
||||
incoming = MmapPool.instance.make!(Queue!IOWatcher);
|
||||
}
|
||||
|
||||
/// Ditto.
|
||||
@ -71,6 +72,10 @@ class ConnectionWatcher : Watcher
|
||||
|
||||
~this()
|
||||
{
|
||||
foreach (w; incoming)
|
||||
{
|
||||
MmapPool.instance.dispose(w);
|
||||
}
|
||||
MmapPool.instance.dispose(incoming);
|
||||
}
|
||||
|
||||
|
@ -121,7 +121,7 @@ class Queue(T)
|
||||
/**
|
||||
* Returns: $(D_KEYWORD true) if the queue is empty.
|
||||
*/
|
||||
@property bool empty() inout const
|
||||
@property bool empty() inout const pure nothrow @safe @nogc
|
||||
{
|
||||
return first.next is null;
|
||||
}
|
||||
@ -170,7 +170,8 @@ class Queue(T)
|
||||
}
|
||||
|
||||
/**
|
||||
* $(D_KEYWORD foreach) iteration.
|
||||
* $(D_KEYWORD foreach) iteration. The elements will be automatically
|
||||
* dequeued.
|
||||
*
|
||||
* Params:
|
||||
* dg = $(D_KEYWORD foreach) body.
|
||||
|
Loading…
Reference in New Issue
Block a user