aboutsummaryrefslogtreecommitdiffstats
path: root/android/async-socket.c
diff options
context:
space:
mode:
Diffstat (limited to 'android/async-socket.c')
-rw-r--r--android/async-socket.c402
1 files changed, 261 insertions, 141 deletions
diff --git a/android/async-socket.c b/android/async-socket.c
index 13e15ca..4be69f6 100644
--- a/android/async-socket.c
+++ b/android/async-socket.c
@@ -37,9 +37,6 @@
* Asynchronous Socket internal API declarations
*******************************************************************************/
-/* Asynchronous socket I/O (reader, or writer) descriptor. */
-typedef struct AsyncSocketIO AsyncSocketIO;
-
/* Gets socket's address string. */
static const char* _async_socket_string(AsyncSocket* as);
@@ -48,10 +45,11 @@ static Looper* _async_socket_get_looper(AsyncSocket* as);
/* Handler for the I/O time out.
* Param:
- * as - Asynchronous socket for the reader.
+ * as - Asynchronous socket for the I/O.
* asio - Desciptor for the timed out I/O.
*/
-static void _async_socket_io_timed_out(AsyncSocket* as, AsyncSocketIO* asio);
+static AsyncIOAction _async_socket_io_timed_out(AsyncSocket* as,
+ AsyncSocketIO* asio);
/********************************************************************************
* Asynchronous Socket Reader / Writer
@@ -72,10 +70,12 @@ struct AsyncSocketIO {
uint32_t to_transfer;
/* Bytes thransferred through the socket in this I/O. */
uint32_t transferred;
- /* I/O callbacks for this I/O. */
- const ASIOCb* io_cb;
+ /* I/O callback for this I/O. */
+ on_as_io_cb on_io;
/* I/O type selector: 1 - read, 0 - write. */
int is_io_read;
+ /* State of the I/O. */
+ AsyncIOState state;
};
/*
@@ -105,7 +105,7 @@ static void _on_async_socket_io_timed_out(void* opaque);
* as - Asynchronous socket for the I/O.
* is_io_read - I/O type selector: 1 - read, 0 - write.
* buffer, len - Reader / writer buffer address.
- * io_cb - Callbacks for this reader / writer.
+ * io_cb - Callback for this reader / writer.
* io_opaque - An opaque pointer associated with the I/O.
* deadline - Deadline to complete the I/O.
* Return:
@@ -116,7 +116,7 @@ _async_socket_rw_new(AsyncSocket* as,
int is_io_read,
void* buffer,
uint32_t len,
- const ASIOCb* io_cb,
+ on_as_io_cb io_cb,
void* io_opaque,
Duration deadline)
{
@@ -137,8 +137,9 @@ _async_socket_rw_new(AsyncSocket* as,
asio->buffer = (uint8_t*)buffer;
asio->to_transfer = len;
asio->transferred = 0;
- asio->io_cb = io_cb;
+ asio->on_io = io_cb;
asio->io_opaque = io_opaque;
+ asio->state = ASIO_STATE_QUEUED;
loopTimer_init(asio->timer, _async_socket_get_looper(as),
_on_async_socket_io_timed_out, asio);
@@ -168,7 +169,7 @@ _async_socket_io_destroy(AsyncSocketIO* asio)
* Param:
* as - Asynchronous socket for the reader.
* buffer, len - Reader's buffer.
- * io_cb - Lists reader's callbacks.
+ * io_cb - Reader's callback.
* reader_opaque - An opaque pointer associated with the reader.
* deadline - Deadline to complete the operation.
* Return:
@@ -178,7 +179,7 @@ static AsyncSocketIO*
_async_socket_reader_new(AsyncSocket* as,
void* buffer,
uint32_t len,
- const ASIOCb* io_cb,
+ on_as_io_cb io_cb,
void* reader_opaque,
Duration deadline)
{
@@ -191,7 +192,7 @@ _async_socket_reader_new(AsyncSocket* as,
* Param:
* as - Asynchronous socket for the writer.
* buffer, len - Writer's buffer.
- * io_cb - Lists writer's callbacks.
+ * io_cb - Writer's callback.
* writer_opaque - An opaque pointer associated with the writer.
* deadline - Deadline to complete the operation.
* Return:
@@ -201,7 +202,7 @@ static AsyncSocketIO*
_async_socket_writer_new(AsyncSocket* as,
const void* buffer,
uint32_t len,
- const ASIOCb* io_cb,
+ on_as_io_cb io_cb,
void* writer_opaque,
Duration deadline)
{
@@ -216,8 +217,76 @@ static void
_on_async_socket_io_timed_out(void* opaque)
{
AsyncSocketIO* const asio = (AsyncSocketIO*)opaque;
- _async_socket_io_timed_out(asio->as, asio);
- _async_socket_io_destroy(asio);
+ const AsyncIOAction action = _async_socket_io_timed_out(asio->as, asio);
+ if (action != ASIO_ACTION_RETRY) {
+ _async_socket_io_destroy(asio);
+ }
+}
+
+/********************************************************************************
+ * Public Asynchronous Socket I/O API
+ *******************************************************************************/
+
+AsyncSocket*
+async_socket_io_get_socket(const AsyncSocketIO* asio)
+{
+ return asio->as;
+}
+
+void
+async_socket_io_cancel_time_out(AsyncSocketIO* asio)
+{
+ loopTimer_stop(asio->timer);
+}
+
+void*
+async_socket_io_get_io_opaque(const AsyncSocketIO* asio)
+{
+ return asio->io_opaque;
+}
+
+void*
+async_socket_io_get_client_opaque(const AsyncSocketIO* asio)
+{
+ return async_socket_get_client_opaque(asio->as);
+}
+
+void*
+async_socket_io_get_buffer_info(const AsyncSocketIO* asio,
+ uint32_t* transferred,
+ uint32_t* to_transfer)
+{
+ if (transferred != NULL) {
+ *transferred = asio->transferred;
+ }
+ if (to_transfer != NULL) {
+ *to_transfer = asio->to_transfer;
+ }
+ return asio->buffer;
+}
+
+void*
+async_socket_io_get_buffer(const AsyncSocketIO* asio)
+{
+ return asio->buffer;
+}
+
+uint32_t
+async_socket_io_get_transferred(const AsyncSocketIO* asio)
+{
+ return asio->transferred;
+}
+
+uint32_t
+async_socket_io_get_to_transfer(const AsyncSocketIO* asio)
+{
+ return asio->to_transfer;
+}
+
+int
+async_socket_io_is_read(const AsyncSocketIO* asio)
+{
+ return asio->is_io_read;
}
/********************************************************************************
@@ -227,8 +296,8 @@ _on_async_socket_io_timed_out(void* opaque)
struct AsyncSocket {
/* TCP address for the socket. */
SockAddress address;
- /* Client callbacks for this socket. */
- const ASClientCb* client_cb;
+ /* Connection callback for this socket. */
+ on_as_connection_cb on_connection;
/* An opaque pointer associated with this socket by the client. */
void* client_opaque;
/* I/O looper for asynchronous I/O on the socket. */
@@ -353,7 +422,7 @@ _async_socket_remove_io(AsyncSocket* as,
* as - Initialized AsyncSocket instance.
* list_head, list_tail - Pointers to the list head and tail.
* Return:
- * Next I/O at the head of the list, or NULL if I/O list become empty.
+ * Next I/O at the head of the list, or NULL if I/O list became empty.
*/
static AsyncSocketIO*
_async_socket_advance_io(AsyncSocket* as,
@@ -375,7 +444,7 @@ _async_socket_advance_io(AsyncSocket* as,
* Param:
* as - Initialized AsyncSocket instance.
* Return:
- * Next reader at the head of the list, or NULL if reader list become empty.
+ * Next reader at the head of the list, or NULL if reader list became empty.
*/
static AsyncSocketIO*
_async_socket_advance_reader(AsyncSocket* as)
@@ -387,7 +456,7 @@ _async_socket_advance_reader(AsyncSocket* as)
* Param:
* as - Initialized AsyncSocket instance.
* Return:
- * Next writer at the head of the list, or NULL if writer list become empty.
+ * Next writer at the head of the list, or NULL if writer list became empty.
*/
static AsyncSocketIO*
_async_socket_advance_writer(AsyncSocket* as)
@@ -399,75 +468,58 @@ _async_socket_advance_writer(AsyncSocket* as)
* Param:
* as - Initialized AsyncSocket instance.
* asio - I/O to complete.
+ * Return:
+ * One of AsyncIOAction values.
*/
-static void
+static AsyncIOAction
_async_socket_complete_io(AsyncSocket* as, AsyncSocketIO* asio)
{
/* Stop the timer. */
loopTimer_stop(asio->timer);
- /* Report I/O completion. First report via I/O callback, and only if it is
- * not set, report via client callback. */
- if (asio->io_cb && asio->io_cb->on_completed) {
- asio->io_cb->on_completed(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer, asio->transferred);
- } else if (as->client_cb->io_cb && as->client_cb->io_cb->on_completed) {
- as->client_cb->io_cb->on_completed(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred);
- }
+ return asio->on_io(asio->io_opaque, asio, ASIO_STATE_SUCCEEDED);
}
/* Timeouts an I/O.
* Param:
* as - Initialized AsyncSocket instance.
* asio - An I/O that has timed out.
+ * Return:
+ * One of AsyncIOAction values.
*/
-static void
+static AsyncIOAction
_async_socket_io_timed_out(AsyncSocket* as, AsyncSocketIO* asio)
{
- /* Remove the I/O from a list of active I/O. */
- if (asio->is_io_read) {
- _async_socket_remove_io(as, &as->readers_head, &as->readers_tail, asio);
- } else {
- _async_socket_remove_io(as, &as->writers_head, &as->writers_tail, asio);
+ /* Report to the client. */
+ const AsyncIOAction action = asio->on_io(asio->io_opaque, asio,
+ ASIO_STATE_TIMED_OUT);
+
+ /* Remove the I/O from a list of active I/O for actions other than retry. */
+ if (action != ASIO_ACTION_RETRY) {
+ if (asio->is_io_read) {
+ _async_socket_remove_io(as, &as->readers_head, &as->readers_tail, asio);
+ } else {
+ _async_socket_remove_io(as, &as->writers_head, &as->writers_tail, asio);
+ }
}
- /* Report I/O time out. First report it via I/O callbacks, and only if it is
- * not set, report it via client callbacks. */
- if (asio->io_cb && asio->io_cb->on_timed_out) {
- asio->io_cb->on_timed_out(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred, asio->to_transfer);
- } else if (as->client_cb->io_cb && as->client_cb->io_cb->on_timed_out) {
- as->client_cb->io_cb->on_timed_out(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred, asio->to_transfer);
- }
+ return action;
}
/* Cancels an I/O.
* Param:
* as - Initialized AsyncSocket instance.
* asio - An I/O to cancel.
+ * Return:
+ * One of AsyncIOAction values.
*/
-static void
+static AsyncIOAction
_async_socket_cancel_io(AsyncSocket* as, AsyncSocketIO* asio)
{
/* Stop the timer. */
loopTimer_stop(asio->timer);
- /* Report I/O cancellation. First report it via I/O callbacks, and only if it
- * is not set, report it via client callbacks. */
- if (asio->io_cb && asio->io_cb->on_cancelled) {
- asio->io_cb->on_cancelled(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred, asio->to_transfer);
- } else if (as->client_cb->io_cb && as->client_cb->io_cb->on_cancelled) {
- as->client_cb->io_cb->on_cancelled(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred, asio->to_transfer);
- }
+ return asio->on_io(asio->io_opaque, asio, ASIO_STATE_CANCELLED);
}
/* Reports an I/O failure.
@@ -475,25 +527,17 @@ _async_socket_cancel_io(AsyncSocket* as, AsyncSocketIO* asio)
* as - Initialized AsyncSocket instance.
* asio - An I/O that has failed. Can be NULL for general failures.
* failure - Failure (errno) that has occurred.
+ * Return:
+ * One of AsyncIOAction values.
*/
-static void
+static AsyncIOAction
_async_socket_io_failure(AsyncSocket* as, AsyncSocketIO* asio, int failure)
{
/* Stop the timer. */
loopTimer_stop(asio->timer);
- /* Report I/O failure. First report it via I/O callbacks, and only if it
- * is not set, report it via client callbacks. */
- if (asio && asio->io_cb && asio->io_cb->on_io_failure) {
- asio->io_cb->on_io_failure(as->client_opaque, as, asio->is_io_read,
- asio->io_opaque, asio->buffer,
- asio->transferred, asio->to_transfer, failure);
- } else if (as->client_cb->io_cb && as->client_cb->io_cb->on_io_failure) {
- as->client_cb->io_cb->on_io_failure(as->client_opaque, as,
- asio->is_io_read, asio->io_opaque,
- asio->buffer, asio->transferred,
- asio->to_transfer, failure);
- }
+ errno = failure;
+ return asio->on_io(asio->io_opaque, asio, ASIO_STATE_FAILED);
}
/* Cancels all the active socket readers.
@@ -505,6 +549,8 @@ _async_socket_cancel_readers(AsyncSocket* as)
{
while (as->readers_head != NULL) {
AsyncSocketIO* const to_cancel = _async_socket_pull_first_reader(as);
+ /* We ignore action returned from the cancellation callback, since we're
+ * in a disconnected state here. */
_async_socket_cancel_io(as, to_cancel);
_async_socket_io_destroy(to_cancel);
}
@@ -519,6 +565,8 @@ _async_socket_cancel_writers(AsyncSocket* as)
{
while (as->writers_head != NULL) {
AsyncSocketIO* const to_cancel = _async_socket_pull_first_writer(as);
+ /* We ignore action returned from the cancellation callback, since we're
+ * in a disconnected state here. */
_async_socket_cancel_io(as, to_cancel);
_async_socket_io_destroy(to_cancel);
}
@@ -607,7 +655,7 @@ _on_async_socket_disconnected(AsyncSocket* as)
{
/* Save error to restore it for the client's callback. */
const int save_errno = errno;
- ASConnectAction action = ASCA_ABORT;
+ AsyncIOAction action = ASIO_ACTION_ABORT;
D("Async socket '%s' is disconnected. Error %d -> %s",
_async_socket_string(as), errno, strerror(errno));
@@ -620,14 +668,11 @@ _on_async_socket_disconnected(AsyncSocket* as)
/* Restore errno, and invoke client's callback. */
errno = save_errno;
- action = as->client_cb->on_connection(as->client_opaque, as,
- ASCS_DISCONNECTED);
+ action = as->on_connection(as->client_opaque, as, ASIO_STATE_FAILED);
- if (action == ASCA_RETRY) {
+ if (action == ASIO_ACTION_RETRY) {
/* Client requested reconnection. */
- if (as->reconnect_to) {
- _async_socket_reconnect(as, as->reconnect_to);
- }
+ _async_socket_reconnect(as, as->reconnect_to);
}
}
@@ -636,14 +681,14 @@ _on_async_socket_disconnected(AsyncSocket* as)
* as - Initialized AsyncSocket instance.
* asio - Descriptor for the failed I/O. Can be NULL for general failures.
*/
-static void
+static AsyncIOAction
_on_async_socket_failure(AsyncSocket* as, AsyncSocketIO* asio)
{
- D("Async socket '%s' I/O failure %d: %s",
+ D("Async socket '%s' I/O failure: %d -> %s",
_async_socket_string(as), errno, strerror(errno));
/* Report the failure. */
- _async_socket_io_failure(as, asio, errno);
+ return _async_socket_io_failure(as, asio, errno);
}
/* A callback that is invoked when there is data available to read.
@@ -656,6 +701,8 @@ _on_async_socket_failure(AsyncSocket* as, AsyncSocketIO* asio)
static int
_on_async_socket_recv(AsyncSocket* as)
{
+ AsyncIOAction action;
+
/* Get current reader. */
AsyncSocketIO* const asr = as->readers_head;
if (asr == NULL) {
@@ -665,6 +712,29 @@ _on_async_socket_recv(AsyncSocket* as)
return 0;
}
+ /* Bump I/O state, and inform the client that I/O is in progress. */
+ if (asr->state == ASIO_STATE_QUEUED) {
+ asr->state = ASIO_STATE_STARTED;
+ } else {
+ asr->state = ASIO_STATE_CONTINUES;
+ }
+ action = asr->on_io(asr->io_opaque, asr, asr->state);
+ if (action == ASIO_ACTION_ABORT) {
+ D("Read is aborted by the client of async socket '%s'",
+ _async_socket_string(as));
+ /* Move on to the next reader. */
+ _async_socket_advance_reader(as);
+ _async_socket_io_destroy(asr);
+ /* Lets see if there are still active readers, and enable, or disable
+ * read I/O callback accordingly. */
+ if (as->readers_head != NULL) {
+ loopIo_wantRead(as->io);
+ } else {
+ loopIo_dontWantRead(as->io);
+ }
+ return 0;
+ }
+
/* Read next chunk of data. */
int res = socket_recv(as->fd, asr->buffer + asr->transferred,
asr->to_transfer - asr->transferred);
@@ -688,7 +758,21 @@ _on_async_socket_recv(AsyncSocket* as)
}
/* An I/O error. */
- _on_async_socket_failure(as, asr);
+ action = _on_async_socket_failure(as, asr);
+ if (action == ASIO_ACTION_ABORT) {
+ D("Read is aborted on failure by the client of async socket '%s'",
+ _async_socket_string(as));
+ /* Move on to the next reader. */
+ _async_socket_advance_reader(as);
+ _async_socket_io_destroy(asr);
+ /* Lets see if there are still active readers, and enable, or disable
+ * read I/O callback accordingly. */
+ if (as->readers_head != NULL) {
+ loopIo_wantRead(as->io);
+ } else {
+ loopIo_dontWantRead(as->io);
+ }
+ }
return -1;
}
@@ -724,6 +808,8 @@ _on_async_socket_recv(AsyncSocket* as)
static int
_on_async_socket_send(AsyncSocket* as)
{
+ AsyncIOAction action;
+
/* Get current writer. */
AsyncSocketIO* const asw = as->writers_head;
if (asw == NULL) {
@@ -733,6 +819,29 @@ _on_async_socket_send(AsyncSocket* as)
return 0;
}
+ /* Bump I/O state, and inform the client that I/O is in progress. */
+ if (asw->state == ASIO_STATE_QUEUED) {
+ asw->state = ASIO_STATE_STARTED;
+ } else {
+ asw->state = ASIO_STATE_CONTINUES;
+ }
+ action = asw->on_io(asw->io_opaque, asw, asw->state);
+ if (action == ASIO_ACTION_ABORT) {
+ D("Write is aborted by the client of async socket '%s'",
+ _async_socket_string(as));
+ /* Move on to the next reader. */
+ _async_socket_advance_reader(as);
+ _async_socket_io_destroy(asw);
+ /* Lets see if there are still active writers, and enable, or disable
+ * write I/O callback accordingly. */
+ if (as->writers_head != NULL) {
+ loopIo_wantWrite(as->io);
+ } else {
+ loopIo_dontWantWrite(as->io);
+ }
+ return 0;
+ }
+
/* Write next chunk of data. */
int res = socket_send(as->fd, asw->buffer + asw->transferred,
asw->to_transfer - asw->transferred);
@@ -756,7 +865,22 @@ _on_async_socket_send(AsyncSocket* as)
}
/* An I/O error. */
- _on_async_socket_failure(as, asw);
+ /* An I/O error. */
+ action = _on_async_socket_failure(as, asw);
+ if (action == ASIO_ACTION_ABORT) {
+ D("Write is aborted on failure by the client of async socket '%s'",
+ _async_socket_string(as));
+ /* Move on to the next reader. */
+ _async_socket_advance_reader(as);
+ _async_socket_io_destroy(asw);
+ /* Lets see if there are still active writers, and enable, or disable
+ * write I/O callback accordingly. */
+ if (as->writers_head != NULL) {
+ loopIo_wantWrite(as->io);
+ } else {
+ loopIo_dontWantWrite(as->io);
+ }
+ }
return -1;
}
@@ -813,51 +937,33 @@ _on_async_socket_io(void* opaque, int fd, unsigned events)
* connector - Connector that is used to connect this socket.
* event - Connection event.
* Return:
- * One of ASCCbRes values.
+ * One of AsyncIOAction values.
*/
-static ASCCbRes
+static AsyncIOAction
_on_connector_events(void* opaque,
AsyncSocketConnector* connector,
- ASCEvent event)
+ AsyncIOState event)
{
- ASConnectAction action;
- ASConnectStatus adsc_status;
+ AsyncIOAction action;
AsyncSocket* const as = (AsyncSocket*)opaque;
- /* Convert connector event into async socket connection event. */
- switch (event) {
- case ASC_CONNECTION_SUCCEEDED:
- /* Accept the connection. */
- adsc_status = ASCS_CONNECTED;
- as->fd = async_socket_connector_pull_fd(connector);
- loopIo_init(as->io, as->looper, as->fd, _on_async_socket_io, as);
- break;
-
- case ASC_CONNECTION_RETRY:
- adsc_status = ASCS_RETRY;
- break;
-
- case ASC_CONNECTION_FAILED:
- default:
- adsc_status = ASCS_FAILURE;
- break;
+ if (event == ASIO_STATE_SUCCEEDED) {
+ /* Accept the connection. */
+ as->fd = async_socket_connector_pull_fd(connector);
+ loopIo_init(as->io, as->looper, as->fd, _on_async_socket_io, as);
}
/* Invoke client's callback. */
- action = as->client_cb->on_connection(as->client_opaque, as, adsc_status);
- if (event == ASC_CONNECTION_SUCCEEDED && action != ASCA_KEEP) {
+ action = as->on_connection(as->client_opaque, as, event);
+ if (event == ASIO_STATE_SUCCEEDED && action != ASIO_ACTION_DONE) {
/* For whatever reason the client didn't want to keep this connection.
* Close it. */
+ D("Connection is discarded by a client of async socket '%s'",
+ _async_socket_string(as));
_async_socket_close_socket(as);
}
- if (action == ASCA_RETRY) {
- return ASC_CB_RETRY;
- } else if (action == ASCA_ABORT) {
- return ASC_CB_ABORT;
- } else {
- return ASC_CB_KEEP;
- }
+ return action;
}
/* Timer callback invoked to reconnect the lost connection.
@@ -879,12 +985,12 @@ _on_async_socket_reconnect(void* opaque)
AsyncSocket*
async_socket_new(int port,
int reconnect_to,
- const ASClientCb* client_cb,
+ on_as_connection_cb client_cb,
void* client_opaque)
{
AsyncSocket* as;
- if (client_cb == NULL || client_cb->on_connection == NULL) {
+ if (client_cb == NULL) {
E("Invalid client_cb parameter");
return NULL;
}
@@ -893,7 +999,7 @@ async_socket_new(int port,
as->fd = -1;
as->client_opaque = client_opaque;
- as->client_cb = client_cb;
+ as->on_connection = client_cb;
as->readers_head = as->readers_tail = NULL;
as->reconnect_to = reconnect_to;
sock_address_init_inet(&as->address, SOCK_ADDRESS_INET_LOOPBACK, port);
@@ -901,6 +1007,7 @@ async_socket_new(int port,
if (as->looper == NULL) {
E("Unable to create I/O looper for async socket '%s'",
_async_socket_string(as));
+ client_cb(client_opaque, as, ASIO_STATE_FAILED);
_async_socket_destroy(as);
return NULL;
}
@@ -909,15 +1016,16 @@ async_socket_new(int port,
return as;
}
-int
+void
async_socket_connect(AsyncSocket* as, int retry_to)
{
AsyncSocketConnector* const connector =
async_socket_connector_new(&as->address, retry_to, _on_connector_events, as);
- if (connector == NULL) {
- return -1;
+ if (connector != NULL) {
+ async_socket_connector_connect(connector);
+ } else {
+ as->on_connection(as->client_opaque, as, ASIO_STATE_FAILED);
}
- return (async_socket_connector_connect(connector) == ASC_CONNECT_FAILED) ? -1 : 0;
}
void
@@ -930,18 +1038,18 @@ async_socket_disconnect(AsyncSocket* as)
}
}
-int
+void
async_socket_reconnect(AsyncSocket* as, int retry_to)
{
_async_socket_cancel_all_io(as);
_async_socket_close_socket(as);
- return async_socket_connect(as, retry_to);
+ async_socket_connect(as, retry_to);
}
-int
+void
async_socket_read_abs(AsyncSocket* as,
void* buffer, uint32_t len,
- const ASIOCb* reader_cb,
+ on_as_io_cb reader_cb,
void* reader_opaque,
Duration deadline)
{
@@ -955,25 +1063,24 @@ async_socket_read_abs(AsyncSocket* as,
as->readers_tail = asr;
}
loopIo_wantRead(as->io);
- return 0;
}
-int
+void
async_socket_read_rel(AsyncSocket* as,
void* buffer, uint32_t len,
- const ASIOCb* reader_cb,
+ on_as_io_cb reader_cb,
void* reader_opaque,
int to)
{
const Duration dl = (to >= 0) ? looper_now(_async_socket_get_looper(as)) + to :
DURATION_INFINITE;
- return async_socket_read_abs(as, buffer, len, reader_cb, reader_opaque, dl);
+ async_socket_read_abs(as, buffer, len, reader_cb, reader_opaque, dl);
}
-int
+void
async_socket_write_abs(AsyncSocket* as,
const void* buffer, uint32_t len,
- const ASIOCb* writer_cb,
+ on_as_io_cb writer_cb,
void* writer_opaque,
Duration deadline)
{
@@ -987,16 +1094,29 @@ async_socket_write_abs(AsyncSocket* as,
as->writers_tail = asw;
}
loopIo_wantWrite(as->io);
- return 0;
}
-int async_socket_write_rel(AsyncSocket* as,
- const void* buffer, uint32_t len,
- const ASIOCb* writer_cb,
- void* writer_opaque,
- int to)
+void
+async_socket_write_rel(AsyncSocket* as,
+ const void* buffer, uint32_t len,
+ on_as_io_cb writer_cb,
+ void* writer_opaque,
+ int to)
{
const Duration dl = (to >= 0) ? looper_now(_async_socket_get_looper(as)) + to :
DURATION_INFINITE;
- return async_socket_write_abs(as, buffer, len, writer_cb, writer_opaque, dl);
+ async_socket_write_abs(as, buffer, len, writer_cb, writer_opaque, dl);
+}
+
+void*
+async_socket_get_client_opaque(const AsyncSocket* as)
+{
+ return as->client_opaque;
+}
+
+Duration
+async_socket_deadline(AsyncSocket* as, int rel)
+{
+ return (rel >= 0) ? looper_now(_async_socket_get_looper(as)) + rel :
+ DURATION_INFINITE;
}