5.1 KiB
Chronos - The Efficient Asynchronous library
Core differences between the standard library asyncdispatch and Chronos
-
Unified callback type
CallbackFunc
:Current version of asyncdispatch uses many types of callbacks:
proc ()
is used in callSoon() callbacks and Future[T] completion callbacks.proc (fut: Future[T])
is used in Future[T] completion callbacks.proc (fd: AsyncFD, bytesTransferred: Dword, errcode: OSErrorCode)
is used in Windows IO completion callbacks.proc (fd: AsyncFD): bool
is used in Unix IO event callbacks.
Such a large number of different types creates big problems in the storage and processing of callbacks and in interaction between callbacks. Lack of ability to pass custom user data to a callback also creates difficulties and inefficiency with passing custom, user-defined data needed for using closures (one more allocation).
To resolve this issue, we have introduced a unified callback type,
CallbackFunc
:type CallbackFunc* = proc (arg: pointer = nil) {.gcsafe.}
Also, one more type was introduced for the callback storage,
AsyncCallback
:type AsyncCallback* = object function*: CallbackFunc udata*: pointer
-
The order of Future[T] completion callbacks:
Current version of asyncdispatch processes Future[T] completion callbacks in reverse order, but asyncdispatch2 schedules callbacks in forward order: https://github.com/nim-lang/Nim/issues/7197
-
Changed the behavior of OS descriptor event callbacks:
For some unknown reason, the current version of asyncdispatch uses seq[T] to hold a list of descriptor event listeners. However, in the asynchronous environment, there is no need for a list of event listeners. In Chronos, there is only one place for one READ listener and one place for one WRITE listener.
-
Removed the default timeout value for the poll() procedure, which allows incorrect usage of asyncdispatch and produces 500-ms timeouts in correct usage.
-
Changed the behavior of the scheduler in the poll() procedure, and fixed the following issues:
-
Chronos no longer uses
epochTime()
; instead, it uses the fastest time primitives for a specific OS,fastEpochTime()
. Also, because MacOS supports only a millisecond resolution inkqueue
, sub-millisecond resolution is not needed. For details, see https://github.com/nim-lang/Nim/issues/3909. -
Removed all IO primitives (
recv()
,recvFrom()
,connect()
,accept()
,send()
, andsendTo()
) from the public API, and moved all their functionality into Transports. -
Introduced an
addTimer()
/removeTimer()
callback interface. -
Introduced
removeReader()
foraddReader()
andremoveWriter()
foraddWriter()
. -
Changed the behavior of the
addReader()
,addWriter()
, andaddTimer()
callbacks. Now, only the explicit removal of the callbacks must be supplied viaremoveReader()
,removeWriter()
, andremoveTimer()
. -
Added the support for the cross-platform
sendfile()
operation. -
Removed the expensive
AsyncEvent
and the support for hardware timers andaddProcess
.addProcess
will be implemented as SubprocessTransport, while hardware-basedAsyncEvent
will be renamed toThreadAsyncEvent
. -
Added cheap synchronization primitives:
AsyncLock
,AsyncEvent
, andAsyncQueue[T]
.
Documentation
You can find more documentation, notes and examples in Wiki.
Installation
You can use Nim official package manager nimble
to install chronos
. The most recent version of the library can be installed via:
$ nimble install https://github.com/status-im/nim-chronos.git
TODO
- Pipe/Subprocess Transports.
- Multithreading Stream/Datagram servers
- Future[T] cancelation
License
Licensed and distributed under either of
- MIT license: LICENSE-MIT or http://opensource.org/licenses/MIT
or
- Apache License, Version 2.0, (LICENSE-APACHEv2 or http://www.apache.org/licenses/LICENSE-2.0)
at your option. This file may not be copied, modified, or distributed except according to those terms.