mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-08-31 22:45:39 +00:00
checkpoint
This commit is contained in:
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: connection.c,v 1.8 2000/01/14 23:10:01 tale Exp $ */
|
/* $Id: connection.c,v 1.9 2000/01/17 18:02:04 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -88,6 +88,12 @@ free_connection(omapi_connection_object_t *connection) {
|
|||||||
*/
|
*/
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This one is locked too, unlock it so it can be destroyed.
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->recv_lock) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
while ((buffer = ISC_LIST_HEAD(connection->input_buffers)) != NULL) {
|
while ((buffer = ISC_LIST_HEAD(connection->input_buffers)) != NULL) {
|
||||||
ISC_LIST_UNLINK(connection->input_buffers, buffer, link);
|
ISC_LIST_UNLINK(connection->input_buffers, buffer, link);
|
||||||
isc_buffer_free(&buffer);
|
isc_buffer_free(&buffer);
|
||||||
@@ -104,37 +110,11 @@ free_connection(omapi_connection_object_t *connection) {
|
|||||||
if (connection->socket != NULL)
|
if (connection->socket != NULL)
|
||||||
isc_socket_detach(&connection->socket);
|
isc_socket_detach(&connection->socket);
|
||||||
|
|
||||||
/*
|
|
||||||
* It is possible the connection was abandoned while a message
|
|
||||||
* was being assembled. That thread needs to be unblocked.
|
|
||||||
* Make sure that when it is awakened, it exits the loop by
|
|
||||||
* setting messages_expected to 0.
|
|
||||||
*/
|
|
||||||
if (connection->is_client) {
|
|
||||||
connection->messages_expected = 0;
|
|
||||||
|
|
||||||
REQUIRE(isc_condition_signal(&connection->waiter) ==
|
|
||||||
ISC_R_SUCCESS);
|
|
||||||
RUNTIME_CHECK(isc_condition_destroy(&connection->waiter) ==
|
|
||||||
ISC_R_SUCCESS);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* XXXDCL ok, but what happens when omapi_connection_wait
|
|
||||||
* awakens and then tries to unlock the mutex, which is possibly
|
|
||||||
* being destroyed right here. i don't think relocking is
|
|
||||||
* a guarantee that isc_condition_wait exited and the mutex was
|
|
||||||
* unlocked in omapi_connection_wait. still, it's worth a shot.
|
|
||||||
*/
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
|
||||||
RUNTIME_CHECK(isc_mutex_destroy(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_destroy(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
RUNTIME_CHECK(isc_mutex_destroy(&connection->recv_lock) ==
|
||||||
/*
|
ISC_R_SUCCESS);
|
||||||
* Disconnect from I/O object, if any.
|
RUNTIME_CHECK(isc_condition_destroy(&connection->waiter) ==
|
||||||
*/
|
ISC_R_SUCCESS);
|
||||||
if (connection->outer != NULL)
|
|
||||||
OBJECT_DEREF(&connection->outer,
|
|
||||||
"omapi_connection_disconnect");
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If whatever created us registered a signal handler, send it
|
* If whatever created us registered a signal handler, send it
|
||||||
@@ -142,10 +122,20 @@ free_connection(omapi_connection_object_t *connection) {
|
|||||||
*/
|
*/
|
||||||
omapi_signal((omapi_object_t *)connection, "disconnect", connection);
|
omapi_signal((omapi_object_t *)connection, "disconnect", connection);
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
/*
|
||||||
|
* Free the inner generic object via the protocol object.
|
||||||
|
* XXXDCL wildass stab in the dark
|
||||||
|
*/
|
||||||
|
OBJECT_DEREF(&connection->inner->inner);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Finally, free the object itself.
|
* Finally, free the object itself.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&connection, "free_connection");
|
OBJECT_DEREF(&connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -161,6 +151,12 @@ end_connection(omapi_connection_object_t *connection, isc_event_t *event,
|
|||||||
* think this can be done with the connection as the object.
|
* think this can be done with the connection as the object.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Don't proceed until recv_done() has finished whatever
|
||||||
|
* it was doing that decremented events_pending to 0.
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_lock(&connection->recv_lock) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Lock the connection's mutex to examine connection->events_pending.
|
* Lock the connection's mutex to examine connection->events_pending.
|
||||||
*/
|
*/
|
||||||
@@ -170,11 +166,37 @@ end_connection(omapi_connection_object_t *connection, isc_event_t *event,
|
|||||||
connection->events_pending);
|
connection->events_pending);
|
||||||
|
|
||||||
if (connection->events_pending == 0) {
|
if (connection->events_pending == 0) {
|
||||||
free_connection(connection);
|
if (connection->waiting) {
|
||||||
|
/*
|
||||||
|
* This must have been an error, since
|
||||||
|
* omapi_connection_wait can't be called after
|
||||||
|
* omapi_connection_disconnect is called for
|
||||||
|
* a normal close.
|
||||||
|
*
|
||||||
|
* Signal omapi_connection_wait and have it do the
|
||||||
|
* cleanup. free_connection can't be called
|
||||||
|
* directly here because it can't be sure
|
||||||
|
* that the mutex has been finished being touched
|
||||||
|
* by omapi_connection_wait even if it
|
||||||
|
* free_connection signals it. (Nasty little
|
||||||
|
* race condition with the lock.)
|
||||||
|
*
|
||||||
|
* Make sure that when it is awakened, it exits its
|
||||||
|
* wait loop by setting messages_expected to 0.
|
||||||
|
*/
|
||||||
|
connection->state = omapi_connection_closed;
|
||||||
|
connection->messages_expected = 0;
|
||||||
|
|
||||||
|
RUNTIME_CHECK(isc_condition_signal(&connection->waiter)
|
||||||
|
== ISC_R_SUCCESS);
|
||||||
|
} else
|
||||||
|
free_connection(connection);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->recv_lock) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -208,7 +230,7 @@ connect_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
|
|
||||||
fprintf(stderr, "CONNECT_DONE\n");
|
fprintf(stderr, "CONNECT_DONE\n");
|
||||||
|
|
||||||
ENSURE(socket == connection->socket && task == connection->task);
|
INSIST(socket == connection->socket && task == connection->task);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
/*
|
/*
|
||||||
@@ -217,7 +239,7 @@ connect_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
* only in recv_done. I'm concerned that there might be some
|
* only in recv_done. I'm concerned that there might be some
|
||||||
* sort of logic window, however small, where that isn't true.
|
* sort of logic window, however small, where that isn't true.
|
||||||
*/
|
*/
|
||||||
ENSURE(connection->events_pending > 0);
|
INSIST(connection->events_pending > 0);
|
||||||
if (--connection->events_pending == 0 && connection->is_client &&
|
if (--connection->events_pending == 0 && connection->is_client &&
|
||||||
connection->state == omapi_connection_disconnecting)
|
connection->state == omapi_connection_disconnecting)
|
||||||
FATAL_ERROR(__FILE__, __LINE__,
|
FATAL_ERROR(__FILE__, __LINE__,
|
||||||
@@ -273,10 +295,40 @@ recv_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
|
|
||||||
fprintf(stderr, "RECV_DONE, %d bytes\n", socketevent->n);
|
fprintf(stderr, "RECV_DONE, %d bytes\n", socketevent->n);
|
||||||
|
|
||||||
ENSURE(socket == connection->socket && task == connection->task);
|
INSIST(socket == connection->socket && task == connection->task);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* XXXDCL This recv_lock is a dirty, ugly, nasty hack and I
|
||||||
|
* am ashamed for it. I have struggled for days with how to
|
||||||
|
* prevent the driving progam's call of omapi_connection_disconnect
|
||||||
|
* from conflicting with the execution of the task thread
|
||||||
|
* (this one, where recv_done is being called).
|
||||||
|
*
|
||||||
|
* Basically, most of the real work happens in the task thread,
|
||||||
|
* all kicked off by signalling "ready" a few lines below. If
|
||||||
|
* this recv_done() is processing the last expected bytes of a message,
|
||||||
|
* then it will wake up the driving program, and the driving program
|
||||||
|
* can go ahead and issue a disconnect. Since there are neither
|
||||||
|
* events_pending nor messages_expected, end_connecton goes ahead
|
||||||
|
* and frees the connection. But that can happen before this
|
||||||
|
* very function can go finish up what it is doing with the
|
||||||
|
* connection structure, which is clearly a bad thing.
|
||||||
|
*
|
||||||
|
* The regular mutex in the connection (the one named "mutex") is
|
||||||
|
* being used throughout the code in a much more localized fashion,
|
||||||
|
* and while it might be possible to more broadly scope it so that
|
||||||
|
* it essentially does the job that recv_lock is doing, I honestly
|
||||||
|
* have not yet fully thought that out and I have already burned
|
||||||
|
* so much time trying other approaches before I struck on this
|
||||||
|
* recv_lock idea. My gut reaction is I don't like how long
|
||||||
|
* a lock on 'mutex' would be held, and I am not entirely sure
|
||||||
|
* that there aren't deadlock situations. I have to think about it
|
||||||
|
* ... LATER.
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_lock(&connection->recv_lock) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
ENSURE(connection->events_pending > 0);
|
INSIST(connection->events_pending > 0);
|
||||||
connection->events_pending--;
|
connection->events_pending--;
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
@@ -295,13 +347,25 @@ recv_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
|
|
||||||
original_bytes_needed = connection->bytes_needed;
|
original_bytes_needed = connection->bytes_needed;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Signal omapi_protocol_signal_handler that the bytes it requested
|
||||||
|
* are present.
|
||||||
|
*
|
||||||
|
* XXXDCL it will then isc_condition_signal the driving thread,
|
||||||
|
* which is free to go ahead and call omapi_connection_disconnect.
|
||||||
|
* since there are possibly no more events pending and no more messages
|
||||||
|
* expected at that point, the driving thread may end up freeing the
|
||||||
|
* connection before this routine is done manipulating it.
|
||||||
|
* what a big, ugly, pain in the rump.
|
||||||
|
*/
|
||||||
while (connection->bytes_needed <= connection->in_bytes &&
|
while (connection->bytes_needed <= connection->in_bytes &&
|
||||||
connection->bytes_needed > 0)
|
connection->bytes_needed > 0)
|
||||||
|
|
||||||
if (omapi_signal((omapi_object_t *)connection, "ready",
|
if (omapi_signal((omapi_object_t *)connection, "ready",
|
||||||
connection) !=
|
connection) != ISC_R_SUCCESS)
|
||||||
ISC_R_SUCCESS)
|
|
||||||
goto abandon;
|
goto abandon;
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Queue up another recv request. If the bufferlist is empty,
|
* Queue up another recv request. If the bufferlist is empty,
|
||||||
* then, something under omapi_signal already called
|
* then, something under omapi_signal already called
|
||||||
@@ -313,20 +377,37 @@ recv_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* See if that was the last event the client was expecting, so
|
* See if that was the last event the client was expecting, so
|
||||||
* that the connection can be freed.
|
* that the connection can be freed. This test needs to be
|
||||||
* XXXDCL I don't *think* this has to be done in the
|
* done, because it is possible omapi_connection_disconnect has
|
||||||
* send_done or connect_done handlers, because a normal
|
* already been called, before the signal handler managed to
|
||||||
* termination will only happen
|
* decrement messages_expected. That means that _disconnect
|
||||||
|
* set the state to disconnecting but didn't call the
|
||||||
|
* end_connection routine. If this was the last event,
|
||||||
|
* no more events are going to come in and call recv_done again,
|
||||||
|
* so this is the only time that it can be identified that
|
||||||
|
* the conditions for finally freeing the connection are all true.
|
||||||
|
*
|
||||||
|
* XXXDCL I don't *think* this has to be done in the send_done or
|
||||||
|
* connect_done handlers, because a normal termination (one defined as
|
||||||
|
* "omapi_connection_disconnect called by the client with 'force' as
|
||||||
|
* false") will only happen after the last of the expected data is
|
||||||
|
* received.
|
||||||
*/
|
*/
|
||||||
if (connection->is_client) {
|
if (connection->is_client) {
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
if (connection->events_pending == 0 &&
|
if (connection->events_pending == 0 &&
|
||||||
connection->state == omapi_connection_disconnecting) {
|
connection->state == omapi_connection_disconnecting) {
|
||||||
ENSURE(connection->messages_expected == 1);
|
INSIST(connection->messages_expected == 1);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
/*
|
||||||
ISC_R_SUCCESS);
|
* omapi_connection_disconnect was called, but
|
||||||
|
* end_connection has not been. Call it now.
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex)
|
||||||
|
== ISC_R_SUCCESS);
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->recv_lock)
|
||||||
|
== ISC_R_SUCCESS);
|
||||||
|
|
||||||
end_connection(connection, event, ISC_R_SUCCESS);
|
end_connection(connection, event, ISC_R_SUCCESS);
|
||||||
return;
|
return;
|
||||||
@@ -334,11 +415,15 @@ recv_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->recv_lock) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
isc_event_free(&event);
|
isc_event_free(&event);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
abandon:
|
abandon:
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->recv_lock) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
end_connection(connection, event, socketevent->result);
|
end_connection(connection, event, socketevent->result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -360,13 +445,13 @@ send_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
|
|
||||||
fprintf(stderr, "SEND_DONE, %d bytes\n", socketevent->n);
|
fprintf(stderr, "SEND_DONE, %d bytes\n", socketevent->n);
|
||||||
|
|
||||||
ENSURE(socket == connection->socket && task == connection->task);
|
INSIST(socket == connection->socket && task == connection->task);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* XXXDCL I am assuming that partial writes are not done. I hope this
|
* XXXDCL I am assuming that partial writes are not done. I hope this
|
||||||
* does not prove to be incorrect. But the assumption can be tested ...
|
* does not prove to be incorrect. But the assumption can be tested ...
|
||||||
*/
|
*/
|
||||||
ENSURE(socketevent->n == connection->out_bytes &&
|
INSIST(socketevent->n == connection->out_bytes &&
|
||||||
socketevent->n ==
|
socketevent->n ==
|
||||||
isc_bufferlist_usedcount(&socketevent->bufferlist));
|
isc_bufferlist_usedcount(&socketevent->bufferlist));
|
||||||
|
|
||||||
@@ -377,7 +462,7 @@ send_done(isc_task_t *task, isc_event_t *event) {
|
|||||||
* only in recv_done. I'm concerned that there might be some
|
* only in recv_done. I'm concerned that there might be some
|
||||||
* sort of logic window, however small, where that isn't true.
|
* sort of logic window, however small, where that isn't true.
|
||||||
*/
|
*/
|
||||||
ENSURE(connection->events_pending > 0);
|
INSIST(connection->events_pending > 0);
|
||||||
if (--connection->events_pending == 0 && connection->is_client &&
|
if (--connection->events_pending == 0 && connection->is_client &&
|
||||||
connection->state == omapi_connection_disconnecting)
|
connection->state == omapi_connection_disconnecting)
|
||||||
FATAL_ERROR(__FILE__, __LINE__,
|
FATAL_ERROR(__FILE__, __LINE__,
|
||||||
@@ -421,7 +506,7 @@ connection_send(omapi_connection_object_t *connection) {
|
|||||||
REQUIRE(connection->state == omapi_connection_connected);
|
REQUIRE(connection->state == omapi_connection_connected);
|
||||||
|
|
||||||
if (connection->out_bytes > 0) {
|
if (connection->out_bytes > 0) {
|
||||||
ENSURE(!ISC_LIST_EMPTY(connection->output_buffers));
|
INSIST(!ISC_LIST_EMPTY(connection->output_buffers));
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
@@ -473,12 +558,13 @@ omapi_connection_toserver(omapi_object_t *protocol, const char *server_name,
|
|||||||
/*
|
/*
|
||||||
* Create a new connection object.
|
* Create a new connection object.
|
||||||
*/
|
*/
|
||||||
result = omapi_object_new((omapi_object_t **)&connection,
|
result = omapi_object_create((omapi_object_t **)&connection,
|
||||||
omapi_type_connection, sizeof(*connection));
|
omapi_type_connection, sizeof(*connection));
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
goto free_obuffer;
|
goto free_obuffer;
|
||||||
|
|
||||||
connection->is_client = ISC_TRUE;
|
connection->is_client = ISC_TRUE;
|
||||||
|
connection->waiting = ISC_FALSE;
|
||||||
|
|
||||||
connection->task = task;
|
connection->task = task;
|
||||||
|
|
||||||
@@ -488,6 +574,7 @@ omapi_connection_toserver(omapi_object_t *protocol, const char *server_name,
|
|||||||
ISC_LIST_APPEND(connection->output_buffers, obuffer, link);
|
ISC_LIST_APPEND(connection->output_buffers, obuffer, link);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_init(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_init(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
RUNTIME_CHECK(isc_mutex_init(&connection->recv_lock) == ISC_R_SUCCESS);
|
||||||
RUNTIME_CHECK(isc_condition_init(&connection->waiter) ==
|
RUNTIME_CHECK(isc_condition_init(&connection->waiter) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
@@ -503,8 +590,8 @@ omapi_connection_toserver(omapi_object_t *protocol, const char *server_name,
|
|||||||
/*
|
/*
|
||||||
* Tie the new connection object to the protocol object.
|
* Tie the new connection object to the protocol object.
|
||||||
*/
|
*/
|
||||||
OBJECT_REF(&protocol->outer, connection, "omapi_connection_toserver");
|
OBJECT_REF(&protocol->outer, connection);
|
||||||
OBJECT_REF(&connection->inner, protocol, "omapi_connection_toserver");
|
OBJECT_REF(&connection->inner, protocol);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Create a socket on which to communicate.
|
* Create a socket on which to communicate.
|
||||||
@@ -522,7 +609,7 @@ omapi_connection_toserver(omapi_object_t *protocol, const char *server_name,
|
|||||||
flag = 1;
|
flag = 1;
|
||||||
if (setsockopt(connection->socket, SOL_SOCKET, SO_REUSEADDR,
|
if (setsockopt(connection->socket, SOL_SOCKET, SO_REUSEADDR,
|
||||||
(char *)&flag, sizeof(flag)) < 0) {
|
(char *)&flag, sizeof(flag)) < 0) {
|
||||||
OBJECT_DEREF(&connection, "omapi_connect");
|
OBJECT_DEREF(&connection);
|
||||||
return (ISC_R_UNEXPECTED);
|
return (ISC_R_UNEXPECTED);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@@ -541,8 +628,8 @@ omapi_connection_toserver(omapi_object_t *protocol, const char *server_name,
|
|||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
free_object:
|
free_object:
|
||||||
OBJECT_DEREF(&connection, "omapi_connection_toserver");
|
OBJECT_DEREF(&connection);
|
||||||
OBJECT_DEREF(&protocol->outer, "omapi_connection_toserver");
|
OBJECT_DEREF(&protocol->outer);
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
free_obuffer:
|
free_obuffer:
|
||||||
@@ -694,6 +781,12 @@ omapi_connection_copyout(unsigned char *dst, omapi_object_t *generic,
|
|||||||
* the protocol.)
|
* the protocol.)
|
||||||
*
|
*
|
||||||
* The client might or might not want to block on the disconnection.
|
* The client might or might not want to block on the disconnection.
|
||||||
|
* Currently the way to accomplish this is to call omapi_connection_wait
|
||||||
|
* before calling this function. A more complex method could be developed,
|
||||||
|
* but after spending (too much) time thinking about it, it hardly seems to
|
||||||
|
* be worth the effort when it is easy to just insist that the
|
||||||
|
* omapi_connection_wait be done.
|
||||||
|
*
|
||||||
* Also, if the error is being thrown from the library, the client
|
* Also, if the error is being thrown from the library, the client
|
||||||
* might *already* be waiting on (or intending to wait on) whatever messages
|
* might *already* be waiting on (or intending to wait on) whatever messages
|
||||||
* it has already sent, so it needs to be awakened. That will be handled
|
* it has already sent, so it needs to be awakened. That will be handled
|
||||||
@@ -733,24 +826,31 @@ omapi_connection_disconnect(omapi_object_t *generic, isc_boolean_t force) {
|
|||||||
*/
|
*/
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
INSIST(connection->state == omapi_connection_connected);
|
||||||
|
|
||||||
connection->state = omapi_connection_disconnecting;
|
|
||||||
connection->messages_expected++;
|
connection->messages_expected++;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If there are no other messages expected for the socket,
|
* If there are other messages expected for the socket,
|
||||||
* the end_connection can be done right now. Otherwise,
|
* then set the state to disconnecting. Based on that
|
||||||
* when recv_done gets the last output from the server,
|
* flag, when recv_done gets the last output from the server,
|
||||||
* then it will then end the connection.
|
* it will then end the connection. The reason the state
|
||||||
|
* is set to disconnecting only here and not while falling
|
||||||
|
* through to end_connection below is that it is the
|
||||||
|
* flag which says whether end_connection has been called or
|
||||||
|
* not.
|
||||||
*/
|
*/
|
||||||
if (connection->messages_expected > 1) {
|
if (connection->messages_expected > 1) {
|
||||||
|
connection->state = omapi_connection_disconnecting;
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* ... else fall through.
|
* ... else fall through.
|
||||||
*/
|
*/
|
||||||
|
INSIST(connection->events_pending == 0);
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
@@ -777,23 +877,7 @@ omapi_connection_require(omapi_object_t *generic, unsigned int bytes) {
|
|||||||
|
|
||||||
connection = (omapi_connection_object_t *)generic;
|
connection = (omapi_connection_object_t *)generic;
|
||||||
|
|
||||||
/*
|
INSIST(connection->state == omapi_connection_connected ||
|
||||||
* There is a race condition here that is really, REALLY
|
|
||||||
* irritating me. Here's the latest attempt at fixing the
|
|
||||||
* whole dang disconnect problem. It is doomed to fail ...
|
|
||||||
* but maybe it will do the job for now.
|
|
||||||
* XXXDCL
|
|
||||||
*/
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
|
||||||
if (connection->state == omapi_connection_disconnecting &&
|
|
||||||
connection->messages_expected == 1) {
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
|
||||||
ISC_R_SUCCESS);
|
|
||||||
return (OMAPI_R_NOTYET);
|
|
||||||
}
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
ENSURE(connection->state == omapi_connection_connected ||
|
|
||||||
connection->state == omapi_connection_disconnecting);
|
connection->state == omapi_connection_disconnecting);
|
||||||
|
|
||||||
connection->bytes_needed += bytes;
|
connection->bytes_needed += bytes;
|
||||||
@@ -857,38 +941,15 @@ omapi_connection_require(omapi_object_t *generic, unsigned int bytes) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Don't queue any more read requests if the connection is
|
* Queue the receive task.
|
||||||
* disconnecting and no more messages are expected. This situation
|
* XXXDCL The "minimum" arg has not been fully thought out.
|
||||||
* can happen when omapi_connection_disconnect is called before
|
|
||||||
* omapi_protocol_signal_handler has had a chance to go back to
|
|
||||||
* its omapi_protocol_header_wait condition where it calls
|
|
||||||
* omapi_connection_require. It is possible the isc_socket_cancel
|
|
||||||
* was already done.
|
|
||||||
*/
|
*/
|
||||||
if (connection->state == omapi_connection_disconnecting &&
|
connection->events_pending++;
|
||||||
connection->messages_expected == 0) {
|
isc_socket_recvv(connection->socket, &connection->input_buffers,
|
||||||
/*
|
connection->bytes_needed - connection->in_bytes,
|
||||||
* Test the above comment's claim that this only happens
|
connection->task, recv_done, connection);
|
||||||
* when requesting to wait for the header of the next message.
|
|
||||||
* XXXDCL
|
|
||||||
* (omapi_protocol_object_t *)p->inner->header_size should
|
|
||||||
* be what is checked against, but at the present time
|
|
||||||
* the protocol_object_t exists only in protocol.c
|
|
||||||
*/
|
|
||||||
ENSURE(bytes == 24);
|
|
||||||
} else {
|
|
||||||
/*
|
|
||||||
* Queue the receive task.
|
|
||||||
* XXXDCL The "minimum" arg has not been fully thought out.
|
|
||||||
*/
|
|
||||||
connection->events_pending++;
|
|
||||||
isc_socket_recvv(connection->socket,
|
|
||||||
&connection->input_buffers,
|
|
||||||
(connection->bytes_needed -
|
|
||||||
connection->in_bytes),
|
|
||||||
connection->task, recv_done, connection);
|
|
||||||
}
|
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
@@ -903,6 +964,14 @@ omapi_connection_require(omapi_object_t *generic, unsigned int bytes) {
|
|||||||
* those events can happen before omapi_connection_wait is ever called.
|
* those events can happen before omapi_connection_wait is ever called.
|
||||||
* So a counter needs to be set for every expected message, and this
|
* So a counter needs to be set for every expected message, and this
|
||||||
* function can only return when that counter is 0.
|
* function can only return when that counter is 0.
|
||||||
|
*
|
||||||
|
* XXXDCL ICK. There is a problem. What if an error that causes disconnection
|
||||||
|
* is happens before it is detected by the driving program, before this
|
||||||
|
* function has ever been called, but after all of the connection data
|
||||||
|
* has been freed.
|
||||||
|
*
|
||||||
|
* Actually, that seems to be a problem throughout this WHOLE LIBRARY. It
|
||||||
|
* really needs to be handled somehow.
|
||||||
*/
|
*/
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_connection_wait(omapi_object_t *object,
|
omapi_connection_wait(omapi_object_t *object,
|
||||||
@@ -913,7 +982,7 @@ omapi_connection_wait(omapi_object_t *object,
|
|||||||
* XXXDCL 'object' is not really used.
|
* XXXDCL 'object' is not really used.
|
||||||
*/
|
*/
|
||||||
omapi_connection_object_t *connection;
|
omapi_connection_object_t *connection;
|
||||||
isc_result_t result, wait_result;
|
isc_result_t result = ISC_R_SUCCESS;
|
||||||
|
|
||||||
REQUIRE(object != NULL && connection_handle != NULL);
|
REQUIRE(object != NULL && connection_handle != NULL);
|
||||||
REQUIRE(connection_handle->type == omapi_type_connection);
|
REQUIRE(connection_handle->type == omapi_type_connection);
|
||||||
@@ -922,90 +991,41 @@ omapi_connection_wait(omapi_object_t *object,
|
|||||||
/*
|
/*
|
||||||
* This routine is not valid for server connections.
|
* This routine is not valid for server connections.
|
||||||
*/
|
*/
|
||||||
REQUIRE(connection->is_client);
|
INSIST(connection->is_client);
|
||||||
|
|
||||||
result = isc_mutex_lock(&connection->mutex);
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
if (result != ISC_R_SUCCESS)
|
INSIST(connection->state == omapi_connection_connected);
|
||||||
return (result);
|
|
||||||
|
connection->waiting = ISC_TRUE;
|
||||||
|
|
||||||
wait_result = ISC_R_SUCCESS;
|
while (connection->messages_expected > 0 && result == ISC_R_SUCCESS)
|
||||||
|
|
||||||
while (connection->messages_expected > 0 &&
|
|
||||||
wait_result == ISC_R_SUCCESS)
|
|
||||||
|
|
||||||
if (timeout == NULL)
|
if (timeout == NULL)
|
||||||
wait_result = isc_condition_wait(&connection->waiter,
|
result = isc_condition_wait(&connection->waiter,
|
||||||
&connection->mutex);
|
&connection->mutex);
|
||||||
else
|
else
|
||||||
wait_result =
|
result = isc_condition_waituntil(&connection->waiter,
|
||||||
isc_condition_waituntil(&connection->waiter,
|
&connection->mutex,
|
||||||
&connection->mutex,
|
timeout);
|
||||||
timeout);
|
|
||||||
|
|
||||||
RUNTIME_CHECK(wait_result == ISC_R_SUCCESS ||
|
RUNTIME_CHECK(result == ISC_R_SUCCESS || result == ISC_R_TIMEDOUT);
|
||||||
wait_result == ISC_R_TIMEDOUT);
|
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) == ISC_R_SUCCESS);
|
connection->waiting = ISC_FALSE;
|
||||||
|
|
||||||
return (wait_result);
|
if (connection->state == omapi_connection_closed)
|
||||||
}
|
/*
|
||||||
|
* An error occurred and end_connection needs to have
|
||||||
|
* free_connection called now that we're done looking
|
||||||
|
* at connection->messages_expected.
|
||||||
|
*
|
||||||
|
* XXXDCL something better to do with the result value?
|
||||||
|
*/
|
||||||
|
free_connection(connection);
|
||||||
|
else
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
isc_result_t
|
return (result);
|
||||||
omapi_connection_setvalue(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value)
|
|
||||||
{
|
|
||||||
REQUIRE(connection != NULL &&
|
|
||||||
connection->type == omapi_type_connection);
|
|
||||||
|
|
||||||
PASS_SETVALUE(connection);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_getvalue(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value)
|
|
||||||
{
|
|
||||||
REQUIRE(connection != NULL &&
|
|
||||||
connection->type == omapi_type_connection);
|
|
||||||
|
|
||||||
PASS_GETVALUE(connection);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_connection_destroy(omapi_object_t *handle, const char *name) {
|
|
||||||
omapi_connection_object_t *connection;
|
|
||||||
|
|
||||||
REQUIRE(handle != NULL && handle->type == omapi_type_connection);
|
|
||||||
|
|
||||||
(void)name;
|
|
||||||
|
|
||||||
connection = (omapi_connection_object_t *)handle;
|
|
||||||
|
|
||||||
if (connection->state == omapi_connection_connected)
|
|
||||||
omapi_connection_disconnect(handle, OMAPI_FORCE_DISCONNECT);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_signalhandler(omapi_object_t *connection, const char *name,
|
|
||||||
va_list ap)
|
|
||||||
{
|
|
||||||
REQUIRE(connection != NULL &&
|
|
||||||
connection->type == omapi_type_connection);
|
|
||||||
|
|
||||||
PASS_SIGNAL(connection);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Write all the published values associated with the object through the
|
|
||||||
* specified connection.
|
|
||||||
*/
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_object_t *handle)
|
|
||||||
{
|
|
||||||
REQUIRE(connection != NULL &&
|
|
||||||
connection->type == omapi_type_connection);
|
|
||||||
|
|
||||||
PASS_STUFFVALUES(handle);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -1163,3 +1183,71 @@ omapi_connection_puthandle(omapi_object_t *c, omapi_object_t *h) {
|
|||||||
|
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
connection_setvalue(omapi_object_t *connection, omapi_object_t *id,
|
||||||
|
omapi_data_string_t *name, omapi_typed_data_t *value)
|
||||||
|
{
|
||||||
|
REQUIRE(connection != NULL &&
|
||||||
|
connection->type == omapi_type_connection);
|
||||||
|
|
||||||
|
PASS_SETVALUE(connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
connection_getvalue(omapi_object_t *connection, omapi_object_t *id,
|
||||||
|
omapi_data_string_t *name, omapi_value_t **value)
|
||||||
|
{
|
||||||
|
REQUIRE(connection != NULL &&
|
||||||
|
connection->type == omapi_type_connection);
|
||||||
|
|
||||||
|
PASS_GETVALUE(connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
connection_destroy(omapi_object_t *handle) {
|
||||||
|
omapi_connection_object_t *connection;
|
||||||
|
|
||||||
|
REQUIRE(handle != NULL && handle->type == omapi_type_connection);
|
||||||
|
|
||||||
|
connection = (omapi_connection_object_t *)handle;
|
||||||
|
|
||||||
|
if (connection->state == omapi_connection_connected)
|
||||||
|
omapi_connection_disconnect(handle, OMAPI_FORCE_DISCONNECT);
|
||||||
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
connection_signalhandler(omapi_object_t *connection, const char *name,
|
||||||
|
va_list ap)
|
||||||
|
{
|
||||||
|
REQUIRE(connection != NULL &&
|
||||||
|
connection->type == omapi_type_connection);
|
||||||
|
|
||||||
|
PASS_SIGNAL(connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Write all the published values associated with the object through the
|
||||||
|
* specified connection.
|
||||||
|
*/
|
||||||
|
static isc_result_t
|
||||||
|
connection_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
||||||
|
omapi_object_t *handle)
|
||||||
|
{
|
||||||
|
REQUIRE(connection != NULL &&
|
||||||
|
connection->type == omapi_type_connection);
|
||||||
|
|
||||||
|
PASS_STUFFVALUES(handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_connection_init(void) {
|
||||||
|
return (omapi_object_register(&omapi_type_connection,
|
||||||
|
"connection",
|
||||||
|
connection_setvalue,
|
||||||
|
connection_getvalue,
|
||||||
|
connection_destroy,
|
||||||
|
connection_signalhandler,
|
||||||
|
connection_stuffvalues,
|
||||||
|
NULL, NULL, NULL));
|
||||||
|
}
|
||||||
|
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: data.c,v 1.2 2000/01/13 06:13:21 tale Exp $ */
|
/* $Id: data.c,v 1.3 2000/01/17 18:02:05 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -93,8 +93,7 @@ omapi_data_new(omapi_typed_data_t **t, omapi_datatype_t type, ...) {
|
|||||||
new->u.buffer.len = val;
|
new->u.buffer.len = val;
|
||||||
break;
|
break;
|
||||||
case omapi_datatype_object:
|
case omapi_datatype_object:
|
||||||
OBJECT_REF(&new->u.object, va_arg(l, omapi_object_t *),
|
OBJECT_REF(&new->u.object, va_arg(l, omapi_object_t *));
|
||||||
"omapi_datatype_new");
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
new->type = type;
|
new->type = type;
|
||||||
@@ -117,7 +116,7 @@ omapi_data_reference(omapi_typed_data_t **r, omapi_typed_data_t *h,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_data_dereference(omapi_typed_data_t **h, const char *name) {
|
omapi_data_dereference(omapi_typed_data_t **h) {
|
||||||
int length = 0;
|
int length = 0;
|
||||||
|
|
||||||
|
|
||||||
@@ -138,7 +137,7 @@ omapi_data_dereference(omapi_typed_data_t **h, const char *name) {
|
|||||||
(*h)->u.buffer.len;
|
(*h)->u.buffer.len;
|
||||||
break;
|
break;
|
||||||
case omapi_datatype_object:
|
case omapi_datatype_object:
|
||||||
OBJECT_DEREF(&(*h)->u.object, name);
|
OBJECT_DEREF(&(*h)->u.object);
|
||||||
length = OMAPI_TYPED_DATA_OBJECT_LEN;
|
length = OMAPI_TYPED_DATA_OBJECT_LEN;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@@ -237,7 +236,7 @@ omapi_data_valuedereference(omapi_value_t **h, const char *name) {
|
|||||||
if ((*h)->name != NULL)
|
if ((*h)->name != NULL)
|
||||||
omapi_data_stringdereference(&(*h)->name, name);
|
omapi_data_stringdereference(&(*h)->name, name);
|
||||||
if ((*h)->value != NULL)
|
if ((*h)->value != NULL)
|
||||||
omapi_data_dereference(&(*h)->value, name);
|
omapi_data_dereference(&(*h)->value);
|
||||||
isc_mem_put(omapi_mctx, *h, sizeof(*h));
|
isc_mem_put(omapi_mctx, *h, sizeof(*h));
|
||||||
}
|
}
|
||||||
*h = NULL;
|
*h = NULL;
|
||||||
|
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: dispatch.c,v 1.7 2000/01/13 06:13:22 tale Exp $ */
|
/* $Id: dispatch.c,v 1.8 2000/01/17 18:02:05 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -39,64 +39,3 @@ omapi_dispatch(struct timeval *t) {
|
|||||||
select(0, NULL, NULL, NULL, t ? t : NULL);
|
select(0, NULL, NULL, NULL, t ? t : NULL);
|
||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_setvalue(omapi_object_t *io, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value)
|
|
||||||
{
|
|
||||||
REQUIRE(io != NULL && io->type == omapi_type_io_object);
|
|
||||||
|
|
||||||
PASS_SETVALUE(io);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_getvalue(omapi_object_t *io, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value)
|
|
||||||
{
|
|
||||||
REQUIRE(io != NULL && io->type == omapi_type_io_object);
|
|
||||||
|
|
||||||
PASS_GETVALUE(io);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_io_destroy(omapi_object_t *io, const char *name) {
|
|
||||||
REQUIRE(io != NULL && io->type == omapi_type_io_object);
|
|
||||||
|
|
||||||
(void)name; /* Unused. */
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_signalhandler(omapi_object_t *io, const char *name, va_list ap)
|
|
||||||
{
|
|
||||||
REQUIRE(io != NULL && io->type == omapi_type_io_object);
|
|
||||||
|
|
||||||
PASS_SIGNAL(io);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_object_t *io)
|
|
||||||
{
|
|
||||||
REQUIRE(io != NULL && io->type == omapi_type_io_object);
|
|
||||||
|
|
||||||
PASS_STUFFVALUES(io);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_waiter_signal_handler(omapi_object_t *h, const char *name, va_list ap) {
|
|
||||||
omapi_waiter_object_t *waiter;
|
|
||||||
|
|
||||||
fprintf(stderr, "omapi_waiter_signal_handler\n");
|
|
||||||
|
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_waiter);
|
|
||||||
|
|
||||||
if (strcmp(name, "ready") == 0) {
|
|
||||||
fprintf(stderr, "unblocking waiter\n");
|
|
||||||
waiter = (omapi_waiter_object_t *)h;
|
|
||||||
isc_condition_signal(&waiter->ready);
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
}
|
|
||||||
|
|
||||||
PASS_SIGNAL(h);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: generic.c,v 1.6 2000/01/13 06:13:22 tale Exp $ */
|
/* $Id: generic.c,v 1.7 2000/01/17 18:02:06 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -29,9 +29,10 @@
|
|||||||
|
|
||||||
#include <omapi/private.h>
|
#include <omapi/private.h>
|
||||||
|
|
||||||
|
#if 0
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_generic_new(omapi_object_t **gen, const char *name) {
|
omapi_generic_new(omapi_object_t **generic_handle, const char *name) {
|
||||||
omapi_generic_object_t *obj;
|
omapi_generic_object_t *generic;
|
||||||
|
|
||||||
obj = isc_mem_get(omapi_mctx, sizeof(*obj));
|
obj = isc_mem_get(omapi_mctx, sizeof(*obj));
|
||||||
if (obj == NULL)
|
if (obj == NULL)
|
||||||
@@ -40,14 +41,15 @@ omapi_generic_new(omapi_object_t **gen, const char *name) {
|
|||||||
obj->refcnt = 0;
|
obj->refcnt = 0;
|
||||||
obj->type = omapi_type_generic;
|
obj->type = omapi_type_generic;
|
||||||
|
|
||||||
OBJECT_REF(gen, obj, name);
|
OBJECT_REF(gen, obj);
|
||||||
|
|
||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_generic_set_value(omapi_object_t *h, omapi_object_t *id,
|
generic_setvalue(omapi_object_t *h, omapi_object_t *id,
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value)
|
omapi_data_string_t *name, omapi_typed_data_t *value)
|
||||||
{
|
{
|
||||||
omapi_generic_object_t *g;
|
omapi_generic_object_t *g;
|
||||||
omapi_value_t *new;
|
omapi_value_t *new;
|
||||||
@@ -161,9 +163,9 @@ omapi_generic_set_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_generic_get_value(omapi_object_t *h, omapi_object_t *id,
|
generic_getvalue(omapi_object_t *h, omapi_object_t *id,
|
||||||
omapi_data_string_t *name, omapi_value_t **value)
|
omapi_data_string_t *name, omapi_value_t **value)
|
||||||
{
|
{
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
omapi_generic_object_t *g;
|
omapi_generic_object_t *g;
|
||||||
@@ -196,8 +198,8 @@ omapi_generic_get_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
PASS_GETVALUE(h);
|
PASS_GETVALUE(h);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
static void
|
||||||
omapi_generic_destroy(omapi_object_t *h, const char *name) {
|
generic_destroy(omapi_object_t *h) {
|
||||||
omapi_generic_object_t *g;
|
omapi_generic_object_t *g;
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
|
|
||||||
@@ -209,7 +211,7 @@ omapi_generic_destroy(omapi_object_t *h, const char *name) {
|
|||||||
for (i = 0; i < g->nvalues; i++)
|
for (i = 0; i < g->nvalues; i++)
|
||||||
if (g->values[i] != NULL)
|
if (g->values[i] != NULL)
|
||||||
omapi_data_valuedereference(&g->values[i],
|
omapi_data_valuedereference(&g->values[i],
|
||||||
name);
|
NULL);
|
||||||
|
|
||||||
isc_mem_put(omapi_mctx, g->values,
|
isc_mem_put(omapi_mctx, g->values,
|
||||||
g->va_max * sizeof(*g->values));
|
g->va_max * sizeof(*g->values));
|
||||||
@@ -218,8 +220,8 @@ omapi_generic_destroy(omapi_object_t *h, const char *name) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_generic_signal_handler(omapi_object_t *h, const char *name, va_list ap) {
|
generic_signalhandler(omapi_object_t *h, const char *name, va_list ap) {
|
||||||
|
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_generic);
|
REQUIRE(h != NULL && h->type == omapi_type_generic);
|
||||||
|
|
||||||
@@ -230,10 +232,9 @@ omapi_generic_signal_handler(omapi_object_t *h, const char *name, va_list ap) {
|
|||||||
* Write all the published values associated with the object through the
|
* Write all the published values associated with the object through the
|
||||||
* specified connection.
|
* specified connection.
|
||||||
*/
|
*/
|
||||||
|
static isc_result_t
|
||||||
isc_result_t
|
generic_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
||||||
omapi_generic_stuff_values(omapi_object_t *connection, omapi_object_t *id,
|
omapi_object_t *h)
|
||||||
omapi_object_t *h)
|
|
||||||
{
|
{
|
||||||
omapi_generic_object_t *src;
|
omapi_generic_object_t *src;
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
@@ -265,3 +266,15 @@ omapi_generic_stuff_values(omapi_object_t *connection, omapi_object_t *id,
|
|||||||
|
|
||||||
PASS_STUFFVALUES(h);
|
PASS_STUFFVALUES(h);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_generic_init(void) {
|
||||||
|
return (omapi_object_register(&omapi_type_generic,
|
||||||
|
"generic",
|
||||||
|
generic_setvalue,
|
||||||
|
generic_getvalue,
|
||||||
|
generic_destroy,
|
||||||
|
generic_signalhandler,
|
||||||
|
generic_stuffvalues,
|
||||||
|
NULL, NULL, NULL));
|
||||||
|
}
|
||||||
|
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: handle.c,v 1.4 2000/01/13 06:13:23 tale Exp $ */
|
/* $Id: handle.c,v 1.5 2000/01/17 18:02:06 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -176,8 +176,7 @@ omapi_object_handle_in_table(omapi_handle_t h, omapi_handle_table_t *table,
|
|||||||
* appropriate place.
|
* appropriate place.
|
||||||
*/
|
*/
|
||||||
if (table->leaf) {
|
if (table->leaf) {
|
||||||
OBJECT_REF(&table->children[h - table->first].object, o,
|
OBJECT_REF(&table->children[h - table->first].object, o);
|
||||||
"omapi_object_handle_in_table");
|
|
||||||
o->handle = h;
|
o->handle = h;
|
||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
@@ -296,8 +295,7 @@ omapi_handle_lookup_in(omapi_object_t **o, omapi_handle_t h,
|
|||||||
if (table->children[h - table->first].object == NULL)
|
if (table->children[h - table->first].object == NULL)
|
||||||
return (ISC_R_NOTFOUND);
|
return (ISC_R_NOTFOUND);
|
||||||
|
|
||||||
OBJECT_REF(o, table->children[h - table->first].object,
|
OBJECT_REF(o, table->children[h - table->first].object);
|
||||||
"omapi_handle_lookup_in");
|
|
||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -52,6 +52,11 @@ typedef struct omapi_typed_data omapi_typed_data_t;
|
|||||||
typedef struct omapi_data_string omapi_data_string_t;
|
typedef struct omapi_data_string omapi_data_string_t;
|
||||||
typedef struct omapi_value omapi_value_t;
|
typedef struct omapi_value omapi_value_t;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This preamble is common to all objects manipulated by libomapi.a,
|
||||||
|
* including specials objects created by external users of the library.
|
||||||
|
* It needs to be at the start of every struct that gets used as an object.
|
||||||
|
*/
|
||||||
#define OMAPI_OBJECT_PREAMBLE \
|
#define OMAPI_OBJECT_PREAMBLE \
|
||||||
omapi_object_type_t * type; \
|
omapi_object_type_t * type; \
|
||||||
size_t object_size; \
|
size_t object_size; \
|
||||||
@@ -168,25 +173,11 @@ struct omapi_object_type {
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* For use with omapi_connection_disconnect().
|
* For use with omapi_connection_disconnect().
|
||||||
|
* XXXDCL rename
|
||||||
*/
|
*/
|
||||||
#define OMAPI_FORCE_DISCONNECT ISC_TRUE
|
#define OMAPI_FORCE_DISCONNECT ISC_TRUE
|
||||||
#define OMAPI_CLEAN_DISCONNECT ISC_FALSE
|
#define OMAPI_CLEAN_DISCONNECT ISC_FALSE
|
||||||
|
|
||||||
/*****
|
|
||||||
***** Global Variables.
|
|
||||||
*****/
|
|
||||||
extern omapi_object_type_t *omapi_type_connection;
|
|
||||||
extern omapi_object_type_t *omapi_type_listener;
|
|
||||||
extern omapi_object_type_t *omapi_type_io_object;
|
|
||||||
extern omapi_object_type_t *omapi_type_generic;
|
|
||||||
extern omapi_object_type_t *omapi_type_protocol;
|
|
||||||
extern omapi_object_type_t *omapi_type_protocol_listener;
|
|
||||||
extern omapi_object_type_t *omapi_type_waiter;
|
|
||||||
extern omapi_object_type_t *omapi_type_remote;
|
|
||||||
extern omapi_object_type_t *omapi_type_message;
|
|
||||||
|
|
||||||
extern omapi_object_type_t *omapi_object_types;
|
|
||||||
|
|
||||||
/*****
|
/*****
|
||||||
***** Function Prototypes.
|
***** Function Prototypes.
|
||||||
*****/
|
*****/
|
||||||
@@ -221,7 +212,7 @@ omapi_protocol_stuff_values(omapi_object_t *connection, omapi_object_t *id,
|
|||||||
omapi_object_t *object);
|
omapi_object_t *object);
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_protocol_destroy(omapi_object_t *object, const char *name);
|
omapi_protocol_destroy(omapi_object_t *object);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_protocol_send_message(omapi_object_t *protocol,
|
omapi_protocol_send_message(omapi_object_t *protocol,
|
||||||
@@ -243,7 +234,7 @@ omapi_protocol_listener_get_value(omapi_object_t *object, omapi_object_t *id,
|
|||||||
omapi_value_t **value);
|
omapi_value_t **value);
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_protocol_listener_destroy(omapi_object_t *object, const char *name);
|
omapi_protocol_listener_destroy(omapi_object_t *object);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_protocol_listener_signal(omapi_object_t *protocol_listener,
|
omapi_protocol_listener_signal(omapi_object_t *protocol_listener,
|
||||||
@@ -275,49 +266,12 @@ omapi_connection_toserver(omapi_object_t *connection, const char *server,
|
|||||||
void
|
void
|
||||||
omapi_connection_disconnect(omapi_object_t *connection, isc_boolean_t force);
|
omapi_connection_disconnect(omapi_object_t *connection, isc_boolean_t force);
|
||||||
|
|
||||||
int
|
|
||||||
omapi_connection_readfd(omapi_object_t *connection);
|
|
||||||
|
|
||||||
int
|
|
||||||
omapi_connection_writefd(omapi_object_t *connection);
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_connection_read(isc_task_t *task, isc_event_t *event);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_reader(omapi_object_t *connection);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_writer(omapi_object_t *connection);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_reaper(omapi_object_t *connection);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_setvalue(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name,
|
|
||||||
omapi_typed_data_t *value);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_getvalue(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value);
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_connection_destroy(omapi_object_t *connection, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_signalhandler(omapi_object_t *connection, const char *name,
|
|
||||||
va_list args);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_connection_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_object_t *object);
|
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_connection_require(omapi_object_t *connection, unsigned int bytes);
|
omapi_connection_require(omapi_object_t *connection, unsigned int bytes);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_connection_wait(omapi_object_t *object, omapi_object_t *connection_handle,
|
omapi_connection_wait(omapi_object_t *object,
|
||||||
|
omapi_object_t *connection_handle,
|
||||||
isc_time_t *timeout);
|
isc_time_t *timeout);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
@@ -360,119 +314,22 @@ omapi_connection_puthandle(omapi_object_t *connection,
|
|||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_listener_listen(omapi_object_t *listener, int port, int backlog);
|
omapi_listener_listen(omapi_object_t *listener, int port, int backlog);
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_listener_setvalue(omapi_object_t *listener, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_listener_getvalue(omapi_object_t *listener, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value);
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_listener_destroy(omapi_object_t *listener, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_listener_signalhandler(omapi_object_t *listener, const char *name,
|
|
||||||
va_list args);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_listener_stuffvalues(omapi_object_t *listener, omapi_object_t *id,
|
|
||||||
omapi_object_t *object);
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* dispatch.c
|
* dispatch.c
|
||||||
*/
|
*/
|
||||||
isc_result_t
|
|
||||||
omapi_register_io_object(omapi_object_t *object,
|
|
||||||
int (*readfd)(omapi_object_t *),
|
|
||||||
int (*writefd)(omapi_object_t *),
|
|
||||||
isc_result_t (*reader)(omapi_object_t *),
|
|
||||||
isc_result_t (*writer)(omapi_object_t *),
|
|
||||||
isc_result_t (*reaper)(omapi_object_t *));
|
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_dispatch(struct timeval *timeout);
|
omapi_dispatch(struct timeval *timeout);
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_wait_for_completion(omapi_object_t *io, struct timeval *timeout);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_one_dispatch(omapi_object_t *waiter, struct timeval *timeout);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_setvalue(omapi_object_t *io, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_getvalue(omapi_object_t *io, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value);
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_io_destroy(omapi_object_t *io, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_signalhandler(omapi_object_t *io, const char *name, va_list args);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_io_stuffvalues(omapi_object_t *io, omapi_object_t *id,
|
|
||||||
omapi_object_t *object);
|
|
||||||
isc_result_t
|
|
||||||
omapi_waiter_signal_handler(omapi_object_t *waiter, const char *name,
|
|
||||||
va_list args);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* generic.c
|
|
||||||
*/
|
|
||||||
isc_result_t
|
|
||||||
omapi_generic_new(omapi_object_t **generic, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_generic_set_value(omapi_object_t *generic, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_generic_get_value(omapi_object_t *generic, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value);
|
|
||||||
|
|
||||||
void
|
|
||||||
omapi_generic_destroy(omapi_object_t *generic, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_generic_signal_handler(omapi_object_t *generic, const char *name,
|
|
||||||
va_list args);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_generic_stuff_values(omapi_object_t *generic, omapi_object_t *id,
|
|
||||||
omapi_object_t *object);
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* message.c
|
* message.c
|
||||||
*/
|
*/
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_message_new(omapi_object_t **message, const char *name);
|
omapi_message_new(omapi_object_t **message);
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_setvalue(omapi_object_t *message, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value);
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_getvalue(omapi_object_t *message, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name, omapi_value_t **value);
|
|
||||||
void
|
void
|
||||||
omapi_message_destroy(omapi_object_t *message, const char *name);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_signalhandler(omapi_object_t *message, const char *name,
|
|
||||||
va_list args);
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_stuffvalues(omapi_object_t *message, omapi_object_t *id,
|
|
||||||
omapi_object_t *object);
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_register(omapi_object_t *message);
|
omapi_message_register(omapi_object_t *message);
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_unregister(omapi_object_t *message);
|
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_message_process(omapi_object_t *message, omapi_object_t *protocol);
|
omapi_message_process(omapi_object_t *message, omapi_object_t *protocol);
|
||||||
|
|
||||||
@@ -483,47 +340,45 @@ isc_result_t
|
|||||||
omapi_init(isc_mem_t *mctx);
|
omapi_init(isc_mem_t *mctx);
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_shutdown(void);
|
omapi_destroy(void);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_type_register(omapi_object_type_t **type,
|
omapi_object_register(omapi_object_type_t **type, const char *name,
|
||||||
const char *name,
|
isc_result_t ((*set_value)
|
||||||
isc_result_t ((*set_value)
|
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
omapi_object_t *,
|
omapi_object_t *,
|
||||||
omapi_data_string_t *,
|
omapi_data_string_t *,
|
||||||
omapi_typed_data_t *)),
|
omapi_typed_data_t *)),
|
||||||
|
|
||||||
isc_result_t ((*get_value)
|
isc_result_t ((*get_value)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
omapi_object_t *,
|
omapi_object_t *,
|
||||||
omapi_data_string_t *,
|
omapi_data_string_t *,
|
||||||
omapi_value_t **)),
|
omapi_value_t **)),
|
||||||
|
|
||||||
void ((*destroy)
|
void ((*destroy)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *)),
|
||||||
const char *)),
|
|
||||||
|
|
||||||
isc_result_t ((*signal_handler)
|
isc_result_t ((*signal_handler)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
const char *,
|
const char *,
|
||||||
va_list)),
|
va_list)),
|
||||||
|
|
||||||
isc_result_t ((*stuff_values)
|
isc_result_t ((*stuff_values)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
omapi_object_t *,
|
omapi_object_t *,
|
||||||
omapi_object_t *)),
|
omapi_object_t *)),
|
||||||
|
|
||||||
isc_result_t ((*lookup)
|
isc_result_t ((*lookup)
|
||||||
(omapi_object_t **,
|
(omapi_object_t **,
|
||||||
omapi_object_t *,
|
omapi_object_t *,
|
||||||
omapi_object_t *)),
|
omapi_object_t *)),
|
||||||
|
|
||||||
isc_result_t ((*create)
|
isc_result_t ((*create)
|
||||||
(omapi_object_t **,
|
(omapi_object_t **,
|
||||||
omapi_object_t *)),
|
omapi_object_t *)),
|
||||||
|
|
||||||
isc_result_t ((*remove)
|
isc_result_t ((*remove)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
omapi_object_t *)));
|
omapi_object_t *)));
|
||||||
|
|
||||||
@@ -569,10 +424,6 @@ isc_result_t
|
|||||||
omapi_stuff_values(omapi_object_t *handle, omapi_object_t *id,
|
omapi_stuff_values(omapi_object_t *handle, omapi_object_t *id,
|
||||||
omapi_object_t *object);
|
omapi_object_t *object);
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_object_create(omapi_object_t **object, omapi_object_t *id,
|
|
||||||
omapi_object_type_t *type);
|
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_update(omapi_object_t *object, omapi_object_t *id,
|
omapi_object_update(omapi_object_t *object, omapi_object_t *id,
|
||||||
omapi_object_t *source, omapi_handle_t handle);
|
omapi_object_t *source, omapi_handle_t handle);
|
||||||
@@ -627,15 +478,14 @@ omapi_handle_td_lookup(omapi_object_t **object, omapi_typed_data_t *data);
|
|||||||
* object.c
|
* object.c
|
||||||
*/
|
*/
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_new(omapi_object_t **object, omapi_object_type_t *type,
|
omapi_object_create(omapi_object_t **object, omapi_object_type_t *type,
|
||||||
size_t size);
|
size_t size);
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_object_reference(omapi_object_t **reference, omapi_object_t *object,
|
omapi_object_reference(omapi_object_t **reference, omapi_object_t *object);
|
||||||
const char *name);
|
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_object_dereference(omapi_object_t **reference, const char *name);
|
omapi_object_dereference(omapi_object_t **reference);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* data.c
|
* data.c
|
||||||
@@ -649,7 +499,7 @@ omapi_data_reference(omapi_typed_data_t **reference, omapi_typed_data_t *data,
|
|||||||
const char *name);
|
const char *name);
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_data_dereference(omapi_typed_data_t **reference, const char *name);
|
omapi_data_dereference(omapi_typed_data_t **reference);
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_data_newstring(omapi_data_string_t **string, unsigned int length,
|
omapi_data_newstring(omapi_data_string_t **string, unsigned int length,
|
||||||
|
@@ -70,10 +70,12 @@ typedef struct omapi_message_object {
|
|||||||
typedef struct omapi_connection_object {
|
typedef struct omapi_connection_object {
|
||||||
OMAPI_OBJECT_PREAMBLE;
|
OMAPI_OBJECT_PREAMBLE;
|
||||||
isc_mutex_t mutex;
|
isc_mutex_t mutex;
|
||||||
|
isc_mutex_t recv_lock;
|
||||||
isc_socket_t *socket; /* Connection socket. */
|
isc_socket_t *socket; /* Connection socket. */
|
||||||
isc_task_t *task;
|
isc_task_t *task;
|
||||||
unsigned int events_pending; /* socket events */
|
unsigned int events_pending; /* socket events */
|
||||||
unsigned int messages_expected;
|
unsigned int messages_expected;
|
||||||
|
isc_boolean_t waiting;
|
||||||
isc_condition_t waiter; /* omapi_connection_wait() */
|
isc_condition_t waiter; /* omapi_connection_wait() */
|
||||||
omapi_connection_state_t state;
|
omapi_connection_state_t state;
|
||||||
isc_sockaddr_t remote_addr;
|
isc_sockaddr_t remote_addr;
|
||||||
@@ -96,23 +98,14 @@ typedef struct omapi_connection_object {
|
|||||||
*/
|
*/
|
||||||
isc_uint32_t out_bytes;
|
isc_uint32_t out_bytes;
|
||||||
isc_bufferlist_t output_buffers;
|
isc_bufferlist_t output_buffers;
|
||||||
#if 0
|
|
||||||
/*
|
|
||||||
* Listener that accepted this connection.
|
|
||||||
* XXXDCL This appears to not be needed.
|
|
||||||
* ... well, now it is. but it could just be an isc_boolean_t
|
|
||||||
* that indicates whether this is a server side connection or client.
|
|
||||||
*/
|
|
||||||
omapi_object_t * listener;
|
|
||||||
#endif
|
|
||||||
isc_boolean_t is_client;
|
isc_boolean_t is_client;
|
||||||
} omapi_connection_object_t;
|
} omapi_connection_object_t;
|
||||||
|
|
||||||
typedef struct omapi_generic_object {
|
typedef struct omapi_generic_object {
|
||||||
OMAPI_OBJECT_PREAMBLE;
|
OMAPI_OBJECT_PREAMBLE;
|
||||||
omapi_value_t ** values;
|
omapi_value_t ** values;
|
||||||
unsigned int nvalues;
|
unsigned int nvalues;
|
||||||
unsigned int va_max;
|
unsigned int va_max;
|
||||||
} omapi_generic_object_t;
|
} omapi_generic_object_t;
|
||||||
|
|
||||||
typedef struct omapi_waiter_object {
|
typedef struct omapi_waiter_object {
|
||||||
@@ -121,6 +114,18 @@ typedef struct omapi_waiter_object {
|
|||||||
isc_condition_t ready;
|
isc_condition_t ready;
|
||||||
} omapi_waiter_object_t;
|
} omapi_waiter_object_t;
|
||||||
|
|
||||||
|
/*****
|
||||||
|
***** Global Variables.
|
||||||
|
*****/
|
||||||
|
extern omapi_object_type_t *omapi_type_connection;
|
||||||
|
extern omapi_object_type_t *omapi_type_listener;
|
||||||
|
extern omapi_object_type_t *omapi_type_generic;
|
||||||
|
extern omapi_object_type_t *omapi_type_protocol;
|
||||||
|
extern omapi_object_type_t *omapi_type_protocol_listener;
|
||||||
|
extern omapi_object_type_t *omapi_type_message;
|
||||||
|
|
||||||
|
extern omapi_object_type_t *omapi_object_types;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Everything needs a memory context. This will likely be made a parameter
|
* Everything needs a memory context. This will likely be made a parameter
|
||||||
* where needed rather than a single global context. XXXDCL
|
* where needed rather than a single global context. XXXDCL
|
||||||
@@ -132,11 +137,6 @@ extern isc_mem_t *omapi_mctx;
|
|||||||
*/
|
*/
|
||||||
extern isc_taskmgr_t *omapi_taskmgr;
|
extern isc_taskmgr_t *omapi_taskmgr;
|
||||||
|
|
||||||
/*
|
|
||||||
* XXXDCL comment, localize?
|
|
||||||
*/
|
|
||||||
extern isc_timermgr_t *omapi_timermgr;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* XXXDCL comment, localize?
|
* XXXDCL comment, localize?
|
||||||
*/
|
*/
|
||||||
@@ -147,12 +147,12 @@ extern isc_boolean_t omapi_ipv6;
|
|||||||
void
|
void
|
||||||
connection_send(omapi_connection_object_t *connection);
|
connection_send(omapi_connection_object_t *connection);
|
||||||
|
|
||||||
#define OBJECT_REF(objectp, object, where) \
|
#define OBJECT_REF(objectp, object) \
|
||||||
omapi_object_reference((omapi_object_t **)objectp, \
|
omapi_object_reference((omapi_object_t **)objectp, \
|
||||||
(omapi_object_t *)object, where)
|
(omapi_object_t *)object)
|
||||||
|
|
||||||
#define OBJECT_DEREF(objectp, where) \
|
#define OBJECT_DEREF(objectp) \
|
||||||
omapi_object_dereference((omapi_object_t **)objectp, where)
|
omapi_object_dereference((omapi_object_t **)objectp)
|
||||||
|
|
||||||
#define PASS_CHECK(object, function) \
|
#define PASS_CHECK(object, function) \
|
||||||
(object->inner != NULL && object->inner->type->function != NULL)
|
(object->inner != NULL && object->inner->type->function != NULL)
|
||||||
@@ -193,6 +193,18 @@ connection_send(omapi_connection_object_t *connection);
|
|||||||
return (ISC_R_SUCCESS); \
|
return (ISC_R_SUCCESS); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_connection_init(void);
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_listener_init(void);
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_generic_init(void);
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_message_init(void);
|
||||||
|
|
||||||
ISC_LANG_ENDDECLS
|
ISC_LANG_ENDDECLS
|
||||||
|
|
||||||
#endif /* OMAPIP_OMAPIP_P_H */
|
#endif /* OMAPIP_OMAPIP_P_H */
|
||||||
|
@@ -40,7 +40,7 @@ typedef struct omapi_listener_object {
|
|||||||
* Reader callback for a listener object. Accept an incoming connection.
|
* Reader callback for a listener object. Accept an incoming connection.
|
||||||
*/
|
*/
|
||||||
static void
|
static void
|
||||||
omapi_listener_accept(isc_task_t *task, isc_event_t *event) {
|
listener_accept(isc_task_t *task, isc_event_t *event) {
|
||||||
isc_result_t result;
|
isc_result_t result;
|
||||||
isc_buffer_t *ibuffer, *obuffer;
|
isc_buffer_t *ibuffer, *obuffer;
|
||||||
isc_task_t *connection_task = NULL;
|
isc_task_t *connection_task = NULL;
|
||||||
@@ -58,7 +58,7 @@ omapi_listener_accept(isc_task_t *task, isc_event_t *event) {
|
|||||||
/*
|
/*
|
||||||
* Set up another listen task for the socket.
|
* Set up another listen task for the socket.
|
||||||
*/
|
*/
|
||||||
isc_socket_accept(event->sender, task, omapi_listener_accept,
|
isc_socket_accept(event->sender, task, listener_accept,
|
||||||
event->arg);
|
event->arg);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -95,7 +95,7 @@ omapi_listener_accept(isc_task_t *task, isc_event_t *event) {
|
|||||||
/*
|
/*
|
||||||
* Create a new connection object.
|
* Create a new connection object.
|
||||||
*/
|
*/
|
||||||
result = omapi_object_new((omapi_object_t **)&connection,
|
result = omapi_object_create((omapi_object_t **)&connection,
|
||||||
omapi_type_connection, sizeof(*connection));
|
omapi_type_connection, sizeof(*connection));
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
goto free_obuffer;
|
goto free_obuffer;
|
||||||
@@ -118,6 +118,7 @@ omapi_listener_accept(isc_task_t *task, isc_event_t *event) {
|
|||||||
ISC_LIST_APPEND(connection->output_buffers, obuffer, link);
|
ISC_LIST_APPEND(connection->output_buffers, obuffer, link);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_init(&connection->mutex) == ISC_R_SUCCESS);
|
RUNTIME_CHECK(isc_mutex_init(&connection->mutex) == ISC_R_SUCCESS);
|
||||||
|
RUNTIME_CHECK(isc_mutex_init(&connection->recv_lock) == ISC_R_SUCCESS);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Notify the listener object that a connection was made.
|
* Notify the listener object that a connection was made.
|
||||||
@@ -131,7 +132,7 @@ omapi_listener_accept(isc_task_t *task, isc_event_t *event) {
|
|||||||
* reaped. The omapi_protocol_listener_signal function added a
|
* reaped. The omapi_protocol_listener_signal function added a
|
||||||
* reference when it created a protocol object as connection->inner.
|
* reference when it created a protocol object as connection->inner.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&connection, "omapi_listener_accept");
|
OBJECT_DEREF(&connection);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
free_object:
|
free_object:
|
||||||
@@ -139,7 +140,7 @@ free_object:
|
|||||||
* Destroy the connection. This will free everything created
|
* Destroy the connection. This will free everything created
|
||||||
* in this function but the event.
|
* in this function but the event.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&connection, "omapi_listener_accept");
|
OBJECT_DEREF(&connection);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -189,8 +190,8 @@ omapi_listener_listen(omapi_object_t *caller, int port, int max) {
|
|||||||
/*
|
/*
|
||||||
* Tie the listener object to the calling object.
|
* Tie the listener object to the calling object.
|
||||||
*/
|
*/
|
||||||
OBJECT_REF(&caller->outer, listener, "omapi_protocol_listen");
|
OBJECT_REF(&caller->outer, listener);
|
||||||
OBJECT_REF(&listener->inner, caller, "omapi_protocol_listen");
|
OBJECT_REF(&listener->inner, caller);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Create a socket on which to listen.
|
* Create a socket on which to listen.
|
||||||
@@ -203,7 +204,7 @@ omapi_listener_listen(omapi_object_t *caller, int port, int max) {
|
|||||||
* because it has two refcnts, one for existing plus one
|
* because it has two refcnts, one for existing plus one
|
||||||
* for the tie to h->outer. This does not seem right to me.
|
* for the tie to h->outer. This does not seem right to me.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&listener, "omapi_listen");
|
OBJECT_DEREF(&listener);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -219,7 +220,7 @@ omapi_listener_listen(omapi_object_t *caller, int port, int max) {
|
|||||||
*/
|
*/
|
||||||
result = isc_socket_bind(listener->socket, &listener->address);
|
result = isc_socket_bind(listener->socket, &listener->address);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&listener, "omapi_listen");
|
OBJECT_DEREF(&listener);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -228,24 +229,24 @@ omapi_listener_listen(omapi_object_t *caller, int port, int max) {
|
|||||||
*/
|
*/
|
||||||
result = isc_socket_listen(listener->socket, max);
|
result = isc_socket_listen(listener->socket, max);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&listener, "omapi_listen");
|
OBJECT_DEREF(&listener);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Queue up the first accept event. The listener object
|
* Queue up the first accept event. The listener object
|
||||||
* will be passed to omapi_listener_accept() when it is called.
|
* will be passed to listener_accept() when it is called.
|
||||||
*/
|
*/
|
||||||
result = isc_socket_accept(listener->socket, task,
|
result = isc_socket_accept(listener->socket, task,
|
||||||
omapi_listener_accept, listener);
|
listener_accept, listener);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
OBJECT_DEREF(&listener, "omapi_listen");
|
OBJECT_DEREF(&listener);
|
||||||
|
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_listener_setvalue(omapi_object_t *listener, omapi_object_t *id,
|
listener_setvalue(omapi_object_t *listener, omapi_object_t *id,
|
||||||
omapi_data_string_t *name, omapi_typed_data_t *value)
|
omapi_data_string_t *name, omapi_typed_data_t *value)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
@@ -257,8 +258,8 @@ omapi_listener_setvalue(omapi_object_t *listener, omapi_object_t *id,
|
|||||||
PASS_SETVALUE(listener);
|
PASS_SETVALUE(listener);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_listener_getvalue(omapi_object_t *listener, omapi_object_t *id,
|
listener_getvalue(omapi_object_t *listener, omapi_object_t *id,
|
||||||
omapi_data_string_t *name, omapi_value_t **value)
|
omapi_data_string_t *name, omapi_value_t **value)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
@@ -270,14 +271,12 @@ omapi_listener_getvalue(omapi_object_t *listener, omapi_object_t *id,
|
|||||||
PASS_GETVALUE(listener);
|
PASS_GETVALUE(listener);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
static void
|
||||||
omapi_listener_destroy(omapi_object_t *object, const char *name) {
|
listener_destroy(omapi_object_t *object) {
|
||||||
omapi_listener_object_t *listener;
|
omapi_listener_object_t *listener;
|
||||||
|
|
||||||
REQUIRE(object != NULL && object->type == omapi_type_listener);
|
REQUIRE(object != NULL && object->type == omapi_type_listener);
|
||||||
|
|
||||||
(void)name; /* Unused. */
|
|
||||||
|
|
||||||
listener = (omapi_listener_object_t *)object;
|
listener = (omapi_listener_object_t *)object;
|
||||||
|
|
||||||
if (listener->socket != NULL) {
|
if (listener->socket != NULL) {
|
||||||
@@ -291,14 +290,13 @@ omapi_listener_destroy(omapi_object_t *object, const char *name) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_listener_signalhandler(omapi_object_t *listener, const char *name,
|
listener_signalhandler(omapi_object_t *listener, const char *name, va_list ap)
|
||||||
va_list ap)
|
|
||||||
{
|
{
|
||||||
REQUIRE(listener != NULL && listener->type == omapi_type_listener);
|
REQUIRE(listener != NULL && listener->type == omapi_type_listener);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This function is reached when omapi_listener_accept does
|
* This function is reached when listener_accept does
|
||||||
* an omapi_signal of "connect" on the listener object. Nothing
|
* an omapi_signal of "connect" on the listener object. Nothing
|
||||||
* need be done here, but the object that originally requested
|
* need be done here, but the object that originally requested
|
||||||
* the listen needs to signalled that a connection was made.
|
* the listen needs to signalled that a connection was made.
|
||||||
@@ -314,12 +312,23 @@ omapi_listener_signalhandler(omapi_object_t *listener, const char *name,
|
|||||||
* Write all the published values associated with the object through the
|
* Write all the published values associated with the object through the
|
||||||
* specified connection.
|
* specified connection.
|
||||||
*/
|
*/
|
||||||
isc_result_t
|
static isc_result_t
|
||||||
omapi_listener_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
listener_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
||||||
omapi_object_t *listener)
|
omapi_object_t *listener)
|
||||||
{
|
{
|
||||||
REQUIRE(listener != NULL && listener->type == omapi_type_listener);
|
REQUIRE(listener != NULL && listener->type == omapi_type_listener);
|
||||||
|
|
||||||
PASS_STUFFVALUES(listener);
|
PASS_STUFFVALUES(listener);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_listener_init(void) {
|
||||||
|
return (omapi_object_register(&omapi_type_listener,
|
||||||
|
"listener",
|
||||||
|
listener_setvalue,
|
||||||
|
listener_getvalue,
|
||||||
|
listener_destroy,
|
||||||
|
listener_signalhandler,
|
||||||
|
listener_stuffvalues,
|
||||||
|
NULL, NULL, NULL));
|
||||||
|
}
|
||||||
|
@@ -28,236 +28,34 @@
|
|||||||
omapi_message_object_t *omapi_registered_messages;
|
omapi_message_object_t *omapi_registered_messages;
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_message_new(omapi_object_t **o, const char *name) {
|
omapi_message_new(omapi_object_t **o) {
|
||||||
omapi_message_object_t *message = NULL;
|
omapi_message_object_t *message = NULL;
|
||||||
omapi_object_t *g;
|
omapi_object_t *g;
|
||||||
isc_result_t result;
|
isc_result_t result;
|
||||||
|
|
||||||
result = omapi_object_new((omapi_object_t **)&message,
|
result = omapi_object_create((omapi_object_t **)&message,
|
||||||
omapi_type_message, sizeof(*message));
|
omapi_type_message, sizeof(*message));
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
g = NULL;
|
g = NULL;
|
||||||
result = omapi_generic_new(&g, name);
|
result = omapi_object_create(&g, NULL, 0);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&message, "omapi_message_new");
|
OBJECT_DEREF(&message);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
OBJECT_REF(&message->inner, g, name);
|
OBJECT_REF(&message->inner, g);
|
||||||
OBJECT_REF(&g->outer, message, name);
|
OBJECT_REF(&g->outer, message);
|
||||||
OBJECT_REF(o, message, name);
|
OBJECT_REF(o, message);
|
||||||
|
|
||||||
OBJECT_DEREF(&message, name);
|
OBJECT_DEREF(&message);
|
||||||
OBJECT_DEREF(&g, name);
|
OBJECT_DEREF(&g);
|
||||||
|
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_setvalue(omapi_object_t *h, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name,
|
|
||||||
omapi_typed_data_t *value)
|
|
||||||
{
|
|
||||||
omapi_message_object_t *m;
|
|
||||||
|
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_message);
|
|
||||||
|
|
||||||
m = (omapi_message_object_t *)h;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Can't set authlen.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Can set authenticator, but the value must be typed data.
|
|
||||||
*/
|
|
||||||
if (omapi_ds_strcmp(name, "authenticator") == 0) {
|
|
||||||
if (m->authenticator != NULL)
|
|
||||||
omapi_data_dereference(&m->authenticator,
|
|
||||||
"omapi_message_set_value");
|
|
||||||
omapi_data_reference(&m->authenticator, value,
|
|
||||||
"omapi_message_set_value");
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
} else if (omapi_ds_strcmp(name, "object") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_object);
|
|
||||||
|
|
||||||
if (m->object != NULL)
|
|
||||||
OBJECT_DEREF(&m->object, "omapi_message_set_value");
|
|
||||||
OBJECT_REF(&m->object, value->u.object,
|
|
||||||
"omapi_message_set_value");
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
} else if (omapi_ds_strcmp(name, "notify-object") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_object);
|
|
||||||
|
|
||||||
if (m->notify_object != NULL)
|
|
||||||
OBJECT_DEREF(&m->notify_object,
|
|
||||||
"omapi_message_set_value");
|
|
||||||
OBJECT_REF(&m->notify_object, value->u.object,
|
|
||||||
"omapi_message_set_value");
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Can set authid, but it has to be an integer.
|
|
||||||
*/
|
|
||||||
} else if (omapi_ds_strcmp(name, "authid") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_int);
|
|
||||||
|
|
||||||
m->authid = value->u.integer;
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Can set op, but it has to be an integer.
|
|
||||||
*/
|
|
||||||
} else if (omapi_ds_strcmp(name, "op") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_int);
|
|
||||||
|
|
||||||
m->op = value->u.integer;
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Handle also has to be an integer.
|
|
||||||
*/
|
|
||||||
} else if (omapi_ds_strcmp(name, "handle") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_int);
|
|
||||||
|
|
||||||
m->h = value->u.integer;
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Transaction ID has to be an integer.
|
|
||||||
*/
|
|
||||||
} else if (omapi_ds_strcmp(name, "id") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_int);
|
|
||||||
|
|
||||||
m->id = value->u.integer;
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Remote transaction ID has to be an integer.
|
|
||||||
*/
|
|
||||||
} else if (omapi_ds_strcmp(name, "rid") == 0) {
|
|
||||||
INSIST(value != NULL && value->type == omapi_datatype_int);
|
|
||||||
|
|
||||||
m->rid = value->u.integer;
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Try to find some inner object that can take the value.
|
|
||||||
*/
|
|
||||||
PASS_SETVALUE(h);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_getvalue(omapi_object_t *h, omapi_object_t *id,
|
|
||||||
omapi_data_string_t *name,
|
|
||||||
omapi_value_t **value)
|
|
||||||
{
|
|
||||||
omapi_message_object_t *m;
|
|
||||||
|
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_message);
|
|
||||||
|
|
||||||
m = (omapi_message_object_t *)h;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Look for values that are in the message data structure.
|
|
||||||
*/
|
|
||||||
if (omapi_ds_strcmp(name, "authlen") == 0)
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->authlen,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
else if (omapi_ds_strcmp(name, "authenticator") == 0) {
|
|
||||||
if (m->authenticator != NULL)
|
|
||||||
return (omapi_make_value(value, name, m->authenticator,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
else
|
|
||||||
return (ISC_R_NOTFOUND);
|
|
||||||
} else if (omapi_ds_strcmp(name, "authid") == 0) {
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->authid,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
} else if (omapi_ds_strcmp(name, "op") == 0) {
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->op,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
} else if (omapi_ds_strcmp(name, "handle") == 0) {
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->handle,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
} else if (omapi_ds_strcmp(name, "id") == 0) {
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->id,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
} else if (omapi_ds_strcmp(name, "rid") == 0) {
|
|
||||||
return (omapi_make_int_value(value, name, (int)m->rid,
|
|
||||||
"omapi_message_get_value"));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* See if there's an inner object that has the value.
|
|
||||||
*/
|
|
||||||
PASS_GETVALUE(h);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_message_destroy(omapi_object_t *handle, const char *name) {
|
|
||||||
omapi_message_object_t *message;
|
|
||||||
|
|
||||||
REQUIRE(handle != NULL && handle->type == omapi_type_message);
|
|
||||||
|
|
||||||
message = (omapi_message_object_t *)handle;
|
|
||||||
|
|
||||||
if (message->authenticator != NULL)
|
|
||||||
omapi_data_dereference(&message->authenticator, name);
|
|
||||||
|
|
||||||
if (message->prev == NULL && omapi_registered_messages != message)
|
|
||||||
omapi_message_unregister(handle);
|
|
||||||
if (message->prev != NULL)
|
|
||||||
OBJECT_DEREF(&message->prev, name);
|
|
||||||
if (message->next != NULL)
|
|
||||||
OBJECT_DEREF(&message->next, name);
|
|
||||||
if (message->id_object != NULL)
|
|
||||||
OBJECT_DEREF(&message->id_object, name);
|
|
||||||
if (message->object != NULL)
|
|
||||||
OBJECT_DEREF(&message->object, name);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_signalhandler(omapi_object_t *handle, const char *name,
|
|
||||||
va_list ap) {
|
|
||||||
omapi_message_object_t *message;
|
|
||||||
|
|
||||||
REQUIRE(handle != NULL && handle->type == omapi_type_message);
|
|
||||||
|
|
||||||
message = (omapi_message_object_t *)handle;
|
|
||||||
|
|
||||||
if (strcmp(name, "status") == 0 &&
|
|
||||||
(message->object != NULL || message->notify_object != NULL)) {
|
|
||||||
if (message->object != NULL)
|
|
||||||
return ((message->object->type->signal_handler))
|
|
||||||
(message->object, name, ap);
|
|
||||||
else
|
|
||||||
return ((message->notify_object->type->signal_handler))
|
|
||||||
(message->notify_object, name, ap);
|
|
||||||
}
|
|
||||||
|
|
||||||
PASS_SIGNAL(handle);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Write all the published values associated with the object through the
|
|
||||||
* specified connection.
|
|
||||||
*/
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
|
||||||
omapi_object_t *message)
|
|
||||||
{
|
|
||||||
REQUIRE(message != NULL && message->type == omapi_type_message);
|
|
||||||
|
|
||||||
PASS_STUFFVALUES(message);
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_message_register(omapi_object_t *h) {
|
omapi_message_register(omapi_object_t *h) {
|
||||||
omapi_message_object_t *m;
|
omapi_message_object_t *m;
|
||||||
|
|
||||||
@@ -272,20 +70,15 @@ omapi_message_register(omapi_object_t *h) {
|
|||||||
omapi_registered_messages != m);
|
omapi_registered_messages != m);
|
||||||
|
|
||||||
if (omapi_registered_messages != NULL) {
|
if (omapi_registered_messages != NULL) {
|
||||||
OBJECT_REF(&m->next, omapi_registered_messages,
|
OBJECT_REF(&m->next, omapi_registered_messages);
|
||||||
"omapi_message_register");
|
OBJECT_REF(&omapi_registered_messages->prev, m);
|
||||||
OBJECT_REF(&omapi_registered_messages->prev, m,
|
OBJECT_DEREF(&omapi_registered_messages);
|
||||||
"omapi_message_register");
|
|
||||||
OBJECT_DEREF(&omapi_registered_messages,
|
|
||||||
"omapi_message_register");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
OBJECT_REF(&omapi_registered_messages, m,
|
OBJECT_REF(&omapi_registered_messages, m);
|
||||||
"omapi_message_register");
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
static void
|
||||||
omapi_message_unregister(omapi_object_t *h) {
|
omapi_message_unregister(omapi_object_t *h) {
|
||||||
omapi_message_object_t *m;
|
omapi_message_object_t *m;
|
||||||
omapi_message_object_t *n;
|
omapi_message_object_t *n;
|
||||||
@@ -301,35 +94,31 @@ omapi_message_unregister(omapi_object_t *h) {
|
|||||||
|
|
||||||
n = NULL;
|
n = NULL;
|
||||||
if (m->next != NULL) {
|
if (m->next != NULL) {
|
||||||
OBJECT_REF(&n, m->next, "omapi_message_unregister");
|
OBJECT_REF(&n, m->next);
|
||||||
OBJECT_DEREF(&m->next, "omapi_message_unregister");
|
OBJECT_DEREF(&m->next);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m->prev != NULL) {
|
if (m->prev != NULL) {
|
||||||
omapi_message_object_t *tmp = NULL;
|
omapi_message_object_t *tmp = NULL;
|
||||||
OBJECT_REF(&tmp, m->prev, "omapi_message_register");
|
OBJECT_REF(&tmp, m->prev);
|
||||||
OBJECT_DEREF(&m->prev, "omapi_message_unregister");
|
OBJECT_DEREF(&m->prev);
|
||||||
|
|
||||||
if (tmp->next != NULL)
|
if (tmp->next != NULL)
|
||||||
OBJECT_DEREF(&tmp->next, "omapi_message_unregister");
|
OBJECT_DEREF(&tmp->next);
|
||||||
|
|
||||||
if (n != NULL)
|
if (n != NULL)
|
||||||
OBJECT_REF(&tmp->next, n, "omapi_message_unregister");
|
OBJECT_REF(&tmp->next, n);
|
||||||
|
|
||||||
OBJECT_DEREF(&tmp, "omapi_message_unregister");
|
OBJECT_DEREF(&tmp);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
OBJECT_DEREF(&omapi_registered_messages,
|
OBJECT_DEREF(&omapi_registered_messages);
|
||||||
"omapi_message_unregister");
|
|
||||||
if (n != NULL)
|
if (n != NULL)
|
||||||
OBJECT_REF(&omapi_registered_messages, n,
|
OBJECT_REF(&omapi_registered_messages, n);
|
||||||
"omapi_message_unregister");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (n != NULL)
|
if (n != NULL)
|
||||||
OBJECT_DEREF(&n, "omapi_message_unregister");
|
OBJECT_DEREF(&n);
|
||||||
|
|
||||||
return (ISC_R_SUCCESS);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
@@ -492,7 +281,7 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
* return an error.
|
* return an error.
|
||||||
*/
|
*/
|
||||||
if (result == ISC_R_SUCCESS && create != 0 && exclusive != 0) {
|
if (result == ISC_R_SUCCESS && create != 0 && exclusive != 0) {
|
||||||
OBJECT_DEREF(&object, "omapi_message_process");
|
OBJECT_DEREF(&object);
|
||||||
return (omapi_protocol_send_status(po, NULL,
|
return (omapi_protocol_send_status(po, NULL,
|
||||||
ISC_R_EXISTS, message->id,
|
ISC_R_EXISTS, message->id,
|
||||||
"specified object already exists"));
|
"specified object already exists"));
|
||||||
@@ -502,7 +291,9 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
* If we're creating the object, do it now.
|
* If we're creating the object, do it now.
|
||||||
*/
|
*/
|
||||||
if (object == NULL) {
|
if (object == NULL) {
|
||||||
result = omapi_object_create(&object, NULL, type);
|
if (type->create == NULL)
|
||||||
|
return (ISC_R_NOTIMPLEMENTED);
|
||||||
|
result = (*(type->create))(&object, NULL);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
return (omapi_protocol_send_status(po, NULL,
|
return (omapi_protocol_send_status(po, NULL,
|
||||||
result, message->id,
|
result, message->id,
|
||||||
@@ -518,7 +309,7 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
message->object,
|
message->object,
|
||||||
message->handle);
|
message->handle);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&object, "omapi_message_process");
|
OBJECT_DEREF(&object);
|
||||||
return (omapi_protocol_send_status(po, NULL,
|
return (omapi_protocol_send_status(po, NULL,
|
||||||
result, message->id,
|
result, message->id,
|
||||||
"can't update object"));
|
"can't update object"));
|
||||||
@@ -541,13 +332,12 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
send:
|
send:
|
||||||
result = omapi_protocol_send_update(po, NULL,
|
result = omapi_protocol_send_update(po, NULL,
|
||||||
message->id, object);
|
message->id, object);
|
||||||
OBJECT_DEREF(&object, "omapi_message_process");
|
OBJECT_DEREF(&object);
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
case OMAPI_OP_UPDATE:
|
case OMAPI_OP_UPDATE:
|
||||||
if (m->object != NULL) {
|
if (m->object != NULL) {
|
||||||
OBJECT_REF(&object, m->object,
|
OBJECT_REF(&object, m->object);
|
||||||
"omapi_message_process");
|
|
||||||
} else {
|
} else {
|
||||||
result = omapi_handle_lookup(&object, message->handle);
|
result = omapi_handle_lookup(&object, message->handle);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
@@ -560,7 +350,7 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
result = omapi_object_update(object, NULL, message->object,
|
result = omapi_object_update(object, NULL, message->object,
|
||||||
message->handle);
|
message->handle);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&object, "omapi_message_process");
|
OBJECT_DEREF(&object);
|
||||||
if (message->rid == 0)
|
if (message->rid == 0)
|
||||||
return (omapi_protocol_send_status(po, NULL,
|
return (omapi_protocol_send_status(po, NULL,
|
||||||
result, message->id,
|
result, message->id,
|
||||||
@@ -627,10 +417,217 @@ omapi_message_process(omapi_object_t *mo, omapi_object_t *po) {
|
|||||||
"no remove method for object"));
|
"no remove method for object"));
|
||||||
|
|
||||||
result = (*(object->type->remove))(object, NULL);
|
result = (*(object->type->remove))(object, NULL);
|
||||||
OBJECT_DEREF(&object, "omapi_message_process");
|
OBJECT_DEREF(&object);
|
||||||
|
|
||||||
return (omapi_protocol_send_status(po, NULL, result,
|
return (omapi_protocol_send_status(po, NULL, result,
|
||||||
message->id, NULL));
|
message->id, NULL));
|
||||||
}
|
}
|
||||||
return (ISC_R_NOTIMPLEMENTED);
|
return (ISC_R_NOTIMPLEMENTED);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
message_setvalue(omapi_object_t *h, omapi_object_t *id,
|
||||||
|
omapi_data_string_t *name, omapi_typed_data_t *value)
|
||||||
|
{
|
||||||
|
omapi_message_object_t *m;
|
||||||
|
|
||||||
|
REQUIRE(h != NULL && h->type == omapi_type_message);
|
||||||
|
|
||||||
|
m = (omapi_message_object_t *)h;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can't set authlen.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can set authenticator, but the value must be typed data.
|
||||||
|
*/
|
||||||
|
if (omapi_ds_strcmp(name, "authenticator") == 0) {
|
||||||
|
if (m->authenticator != NULL)
|
||||||
|
omapi_data_dereference(&m->authenticator);
|
||||||
|
omapi_data_reference(&m->authenticator, value,
|
||||||
|
"omapi_message_set_value");
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
} else if (omapi_ds_strcmp(name, "object") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_object);
|
||||||
|
|
||||||
|
if (m->object != NULL)
|
||||||
|
OBJECT_DEREF(&m->object);
|
||||||
|
OBJECT_REF(&m->object, value->u.object);
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
} else if (omapi_ds_strcmp(name, "notify-object") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_object);
|
||||||
|
|
||||||
|
if (m->notify_object != NULL)
|
||||||
|
OBJECT_DEREF(&m->notify_object);
|
||||||
|
OBJECT_REF(&m->notify_object, value->u.object);
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can set authid, but it has to be an integer.
|
||||||
|
*/
|
||||||
|
} else if (omapi_ds_strcmp(name, "authid") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_int);
|
||||||
|
|
||||||
|
m->authid = value->u.integer;
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can set op, but it has to be an integer.
|
||||||
|
*/
|
||||||
|
} else if (omapi_ds_strcmp(name, "op") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_int);
|
||||||
|
|
||||||
|
m->op = value->u.integer;
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Handle also has to be an integer.
|
||||||
|
*/
|
||||||
|
} else if (omapi_ds_strcmp(name, "handle") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_int);
|
||||||
|
|
||||||
|
m->h = value->u.integer;
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Transaction ID has to be an integer.
|
||||||
|
*/
|
||||||
|
} else if (omapi_ds_strcmp(name, "id") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_int);
|
||||||
|
|
||||||
|
m->id = value->u.integer;
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Remote transaction ID has to be an integer.
|
||||||
|
*/
|
||||||
|
} else if (omapi_ds_strcmp(name, "rid") == 0) {
|
||||||
|
INSIST(value != NULL && value->type == omapi_datatype_int);
|
||||||
|
|
||||||
|
m->rid = value->u.integer;
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Try to find some inner object that can take the value.
|
||||||
|
*/
|
||||||
|
PASS_SETVALUE(h);
|
||||||
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
message_getvalue(omapi_object_t *h, omapi_object_t *id,
|
||||||
|
omapi_data_string_t *name, omapi_value_t **value)
|
||||||
|
{
|
||||||
|
omapi_message_object_t *m;
|
||||||
|
|
||||||
|
REQUIRE(h != NULL && h->type == omapi_type_message);
|
||||||
|
|
||||||
|
m = (omapi_message_object_t *)h;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Look for values that are in the message data structure.
|
||||||
|
*/
|
||||||
|
if (omapi_ds_strcmp(name, "authlen") == 0)
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->authlen,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
else if (omapi_ds_strcmp(name, "authenticator") == 0) {
|
||||||
|
if (m->authenticator != NULL)
|
||||||
|
return (omapi_make_value(value, name, m->authenticator,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
else
|
||||||
|
return (ISC_R_NOTFOUND);
|
||||||
|
} else if (omapi_ds_strcmp(name, "authid") == 0) {
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->authid,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
} else if (omapi_ds_strcmp(name, "op") == 0) {
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->op,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
} else if (omapi_ds_strcmp(name, "handle") == 0) {
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->handle,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
} else if (omapi_ds_strcmp(name, "id") == 0) {
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->id,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
} else if (omapi_ds_strcmp(name, "rid") == 0) {
|
||||||
|
return (omapi_make_int_value(value, name, (int)m->rid,
|
||||||
|
"omapi_message_get_value"));
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* See if there's an inner object that has the value.
|
||||||
|
*/
|
||||||
|
PASS_GETVALUE(h);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
message_destroy(omapi_object_t *handle) {
|
||||||
|
omapi_message_object_t *message;
|
||||||
|
|
||||||
|
REQUIRE(handle != NULL && handle->type == omapi_type_message);
|
||||||
|
|
||||||
|
message = (omapi_message_object_t *)handle;
|
||||||
|
|
||||||
|
if (message->authenticator != NULL)
|
||||||
|
omapi_data_dereference(&message->authenticator);
|
||||||
|
|
||||||
|
if (message->prev == NULL && omapi_registered_messages != message)
|
||||||
|
omapi_message_unregister(handle);
|
||||||
|
if (message->prev != NULL)
|
||||||
|
OBJECT_DEREF(&message->prev);
|
||||||
|
if (message->next != NULL)
|
||||||
|
OBJECT_DEREF(&message->next);
|
||||||
|
if (message->id_object != NULL)
|
||||||
|
OBJECT_DEREF(&message->id_object);
|
||||||
|
if (message->object != NULL)
|
||||||
|
OBJECT_DEREF(&message->object);
|
||||||
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
message_signalhandler(omapi_object_t *handle, const char *name,
|
||||||
|
va_list ap) {
|
||||||
|
omapi_message_object_t *message;
|
||||||
|
|
||||||
|
REQUIRE(handle != NULL && handle->type == omapi_type_message);
|
||||||
|
|
||||||
|
message = (omapi_message_object_t *)handle;
|
||||||
|
|
||||||
|
if (strcmp(name, "status") == 0 &&
|
||||||
|
(message->object != NULL || message->notify_object != NULL)) {
|
||||||
|
if (message->object != NULL)
|
||||||
|
return ((message->object->type->signal_handler))
|
||||||
|
(message->object, name, ap);
|
||||||
|
else
|
||||||
|
return ((message->notify_object->type->signal_handler))
|
||||||
|
(message->notify_object, name, ap);
|
||||||
|
}
|
||||||
|
|
||||||
|
PASS_SIGNAL(handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Write all the published values associated with the object through the
|
||||||
|
* specified connection.
|
||||||
|
*/
|
||||||
|
static isc_result_t
|
||||||
|
message_stuffvalues(omapi_object_t *connection, omapi_object_t *id,
|
||||||
|
omapi_object_t *message)
|
||||||
|
{
|
||||||
|
REQUIRE(message != NULL && message->type == omapi_type_message);
|
||||||
|
|
||||||
|
PASS_STUFFVALUES(message);
|
||||||
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
omapi_message_init(void) {
|
||||||
|
return (omapi_object_register(&omapi_type_message,
|
||||||
|
"message",
|
||||||
|
message_setvalue,
|
||||||
|
message_getvalue,
|
||||||
|
message_destroy,
|
||||||
|
message_signalhandler,
|
||||||
|
message_stuffvalues,
|
||||||
|
NULL, NULL, NULL));
|
||||||
|
}
|
||||||
|
@@ -15,7 +15,7 @@
|
|||||||
* SOFTWARE.
|
* SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* $Id: object.c,v 1.4 2000/01/14 23:10:03 tale Exp $ */
|
/* $Id: object.c,v 1.5 2000/01/17 18:02:08 tale Exp $ */
|
||||||
|
|
||||||
/* Principal Author: Ted Lemon */
|
/* Principal Author: Ted Lemon */
|
||||||
|
|
||||||
@@ -30,12 +30,18 @@
|
|||||||
#include <omapi/private.h>
|
#include <omapi/private.h>
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_new(omapi_object_t **object, omapi_object_type_t *type,
|
omapi_object_create(omapi_object_t **object, omapi_object_type_t *type,
|
||||||
size_t size)
|
size_t size)
|
||||||
{
|
{
|
||||||
omapi_object_t *new;
|
omapi_object_t *new;
|
||||||
|
|
||||||
REQUIRE(object != NULL && *object == NULL);
|
REQUIRE(object != NULL && *object == NULL);
|
||||||
|
REQUIRE(size > 0 || type == NULL);
|
||||||
|
|
||||||
|
if (type == NULL) {
|
||||||
|
type = omapi_type_generic;
|
||||||
|
size = sizeof(omapi_generic_object_t);
|
||||||
|
}
|
||||||
|
|
||||||
new = isc_mem_get(omapi_mctx, size);
|
new = isc_mem_get(omapi_mctx, size);
|
||||||
if (new == NULL)
|
if (new == NULL)
|
||||||
@@ -53,20 +59,16 @@ omapi_object_new(omapi_object_t **object, omapi_object_type_t *type,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_object_reference(omapi_object_t **r, omapi_object_t *h,
|
omapi_object_reference(omapi_object_t **r, omapi_object_t *h) {
|
||||||
const char *name)
|
|
||||||
{
|
|
||||||
REQUIRE(r != NULL && *r == NULL);
|
REQUIRE(r != NULL && *r == NULL);
|
||||||
REQUIRE(h != NULL);
|
REQUIRE(h != NULL);
|
||||||
|
|
||||||
(void)name; /* Unused. */
|
|
||||||
|
|
||||||
*r = h;
|
*r = h;
|
||||||
h->refcnt++;
|
h->refcnt++;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_object_dereference(omapi_object_t **h, const char *name) {
|
omapi_object_dereference(omapi_object_t **h) {
|
||||||
int outer_reference = 0;
|
int outer_reference = 0;
|
||||||
int inner_reference = 0;
|
int inner_reference = 0;
|
||||||
int handle_reference = 0;
|
int handle_reference = 0;
|
||||||
@@ -83,7 +85,7 @@ omapi_object_dereference(omapi_object_t **h, const char *name) {
|
|||||||
*/
|
*/
|
||||||
/*
|
/*
|
||||||
* XXXDCL my wording
|
* XXXDCL my wording
|
||||||
* Note whether the object being dereference has an inner object, but
|
* Note whether the object being dereferenced has an inner object, but
|
||||||
* only if the inner object's own outer pointer is not what is
|
* only if the inner object's own outer pointer is not what is
|
||||||
* being dereferenced.
|
* being dereferenced.
|
||||||
* (XXXDCL when does it happen that way ?)
|
* (XXXDCL when does it happen that way ?)
|
||||||
@@ -153,13 +155,14 @@ omapi_object_dereference(omapi_object_t **h, const char *name) {
|
|||||||
|
|
||||||
if (extra_references == 0) {
|
if (extra_references == 0) {
|
||||||
if (inner_reference != 0)
|
if (inner_reference != 0)
|
||||||
OBJECT_DEREF(&(*h)->inner->outer, name);
|
OBJECT_DEREF(&(*h)->inner->outer);
|
||||||
if (outer_reference != 0)
|
if (outer_reference != 0)
|
||||||
OBJECT_DEREF(&(*h)->outer->inner, name);
|
OBJECT_DEREF(&(*h)->outer->inner);
|
||||||
if ((*h)->type->destroy != NULL)
|
if ((*h)->type->destroy != NULL)
|
||||||
(*((*h)->type->destroy))(*h, name);
|
(*((*h)->type->destroy))(*h, NULL);
|
||||||
isc_mem_put(omapi_mctx, *h, (*h)->object_size);
|
isc_mem_put(omapi_mctx, *h, (*h)->object_size);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
*h = NULL;
|
*h = NULL;
|
||||||
}
|
}
|
||||||
|
@@ -78,22 +78,20 @@ omapi_protocol_connect(omapi_object_t *h, const char *server_name,
|
|||||||
isc_result_t result;
|
isc_result_t result;
|
||||||
omapi_protocol_object_t *obj;
|
omapi_protocol_object_t *obj;
|
||||||
|
|
||||||
obj = isc_mem_get(omapi_mctx, sizeof(*obj));
|
obj = NULL;
|
||||||
if (obj == NULL)
|
result = omapi_object_create((omapi_object_t **)&obj,
|
||||||
return (ISC_R_NOMEMORY);
|
omapi_type_protocol, sizeof(*obj));
|
||||||
memset(obj, 0, sizeof(*obj));
|
if (result != ISC_R_SUCCESS)
|
||||||
obj->object_size = sizeof(*obj);
|
return (result);
|
||||||
obj->refcnt = 1;
|
|
||||||
obj->type = omapi_type_protocol;
|
|
||||||
|
|
||||||
result = omapi_connection_toserver((omapi_object_t *)obj,
|
result = omapi_connection_toserver((omapi_object_t *)obj,
|
||||||
server_name, port);
|
server_name, port);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&obj, "omapi_protocol_connect");
|
OBJECT_DEREF(&obj);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
OBJECT_REF(&h->outer, obj, "omapi_protocol_connect");
|
OBJECT_REF(&h->outer, obj);
|
||||||
OBJECT_REF(&obj->inner, h, "omapi_protocol_connect");
|
OBJECT_REF(&obj->inner, h);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Send the introductory message.
|
* Send the introductory message.
|
||||||
@@ -102,13 +100,13 @@ omapi_protocol_connect(omapi_object_t *h, const char *server_name,
|
|||||||
OMAPI_PROTOCOL_VERSION,
|
OMAPI_PROTOCOL_VERSION,
|
||||||
sizeof(omapi_protocol_header_t));
|
sizeof(omapi_protocol_header_t));
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&obj, "omapi_protocol_connect");
|
OBJECT_DEREF(&obj);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (authinfo)
|
if (authinfo)
|
||||||
OBJECT_REF(&obj->authinfo, authinfo, "omapi_protocol_connect");
|
OBJECT_REF(&obj->authinfo, authinfo);
|
||||||
OBJECT_DEREF(&obj, "omapi_protocol_accept");
|
OBJECT_DEREF(&obj);
|
||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -286,16 +284,56 @@ omapi_protocol_send_message(omapi_object_t *po, omapi_object_t *id,
|
|||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* When the client sends a message, it expects a reply.
|
* When the client sends a message, it expects a reply. Increment
|
||||||
|
* the count of messages_expected and make sure an isc_socket_recv
|
||||||
|
* gets queued.
|
||||||
|
*
|
||||||
|
* If the connection is in the disconnecting state, connection_send
|
||||||
|
* will note it, with an abort :-), in just a moment. In any event, it
|
||||||
|
* is decreed to be a fatal error for the client program to call this
|
||||||
|
* function after having asked to disconnect, so going ahead with the
|
||||||
|
* omapi_connection_require call here in the driving thread (rather
|
||||||
|
* than in the task thread, where omapi_protocol_signal_handler
|
||||||
|
* normally does things) is ok. It is also known that if this is the
|
||||||
|
* only message being sent right now, then there should be no other
|
||||||
|
* recv_done() results coming in until after the
|
||||||
|
* omapi_connection_require(), so some error is not going to be blowing
|
||||||
|
* away the connection.
|
||||||
*/
|
*/
|
||||||
if (connection->is_client) {
|
if (connection->is_client) {
|
||||||
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
RUNTIME_CHECK(isc_mutex_lock(&connection->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
connection->messages_expected++;
|
if (++connection->messages_expected == 1) {
|
||||||
|
/*
|
||||||
|
* omapi_connection_require() needs an unlocked mutex.
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
result = omapi_connection_require(c, p->header_size);
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
/*
|
||||||
ISC_R_SUCCESS);
|
* How could there possibly be that amount of bytes
|
||||||
|
* waiting if no other messages were outstanding?
|
||||||
|
* Answer: it shouldn't be possible. Make sure.
|
||||||
|
*/
|
||||||
|
ENSURE(result != ISC_R_SUCCESS);
|
||||||
|
if (result != OMAPI_R_NOTYET)
|
||||||
|
goto disconnect;
|
||||||
|
|
||||||
|
} else
|
||||||
|
/*
|
||||||
|
* If messages_expected > 1, then the code after the
|
||||||
|
* call to omapi_message_process() in the
|
||||||
|
* omapi_protocol_signal_handler function has not yet
|
||||||
|
* been done, so it will handle the call to
|
||||||
|
* omapi_connection_require while messages_expected
|
||||||
|
* remains non-zero. (This check also happens at
|
||||||
|
* the end of the block that processes the intro
|
||||||
|
* message.)
|
||||||
|
*/
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&connection->mutex) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
connection_send(connection);
|
connection_send(connection);
|
||||||
@@ -367,6 +405,12 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
goto disconnect;
|
goto disconnect;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The next thing that shows up on incoming connections
|
||||||
|
* should be a message header.
|
||||||
|
*/
|
||||||
|
p->state = omapi_protocol_header_wait;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Signal omapi_connection_wait() to wake up.
|
* Signal omapi_connection_wait() to wake up.
|
||||||
* Only do this for the client side.
|
* Only do this for the client side.
|
||||||
@@ -383,36 +427,53 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Release the lock. Contrary to what you might think
|
* If the driving program has already called
|
||||||
* from some documentation sources, it is necessary
|
* omapi_protocol_send_message and the lock
|
||||||
* to do this for the waiting thread to unblock.
|
* was acquired in that function, then since
|
||||||
|
* messages_expected would have been >= 2 at
|
||||||
|
* the critical test, the omapi_connection_require
|
||||||
|
* would not have been done yet, and will need
|
||||||
|
* to be. Since messages_expected was decremented,
|
||||||
|
* drop through to the connection_require only if
|
||||||
|
* messages_expected is >= 1
|
||||||
|
*/
|
||||||
|
if (c->messages_expected == 0) {
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Proceed to the omapi_connection_require
|
||||||
|
* for the first "real" message's header.
|
||||||
*/
|
*/
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
to_header_wait:
|
to_header_wait:
|
||||||
/*
|
|
||||||
* The next thing we're expecting is a message header.
|
|
||||||
*/
|
|
||||||
p->state = omapi_protocol_header_wait;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Register a need for the number of bytes in a
|
* Register a need for the number of bytes in a header, and if
|
||||||
* header, and if we already have that many, process
|
* that many are here already, process them immediately.
|
||||||
* them immediately.
|
*
|
||||||
|
* XXXDCL there is a miniscule but non-zero chance that
|
||||||
|
* omapi_connection_require will return ISC_R_NOMEMORY
|
||||||
|
* from omapi_connection_require. If that happens,
|
||||||
|
* as things are currently written the client will likely
|
||||||
|
* just hang. no recv was queued, so no recv_done will get
|
||||||
|
* called, so this signal handler never gets called again.
|
||||||
*/
|
*/
|
||||||
if ((omapi_connection_require(connection, p->header_size))
|
result = omapi_connection_require(connection, p->header_size);
|
||||||
!= ISC_R_SUCCESS)
|
if (result == OMAPI_R_NOTYET)
|
||||||
break;
|
break;
|
||||||
/*
|
else if (result != ISC_R_SUCCESS)
|
||||||
* If we already have the data, fall through.
|
goto disconnect;
|
||||||
*/
|
|
||||||
|
/* FALLTHROUGH */
|
||||||
|
|
||||||
case omapi_protocol_header_wait:
|
case omapi_protocol_header_wait:
|
||||||
result = omapi_message_new((omapi_object_t **)&p->message,
|
result = omapi_message_new((omapi_object_t **)&p->message);
|
||||||
"omapi_protocol_signal_handler");
|
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
goto disconnect;
|
goto disconnect;
|
||||||
|
|
||||||
@@ -464,11 +525,13 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
/*
|
/*
|
||||||
* Wait for a 16-bit length.
|
* Wait for a 16-bit length.
|
||||||
*/
|
*/
|
||||||
if (omapi_connection_require(connection, 2) != ISC_R_SUCCESS)
|
result = omapi_connection_require(connection, 2);
|
||||||
|
if (result == OMAPI_R_NOTYET)
|
||||||
break;
|
break;
|
||||||
/*
|
else if (result != ISC_R_SUCCESS)
|
||||||
* If it's already here, fall through.
|
goto disconnect;
|
||||||
*/
|
|
||||||
|
/* FALLTHROUGH */
|
||||||
|
|
||||||
case omapi_protocol_name_length_wait:
|
case omapi_protocol_name_length_wait:
|
||||||
result = omapi_connection_getuint16(connection, &nlen);
|
result = omapi_connection_getuint16(connection, &nlen);
|
||||||
@@ -511,11 +574,14 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* the authenticator. If we already have it,
|
* the authenticator. If we already have it,
|
||||||
* go read it in.
|
* go read it in.
|
||||||
*/
|
*/
|
||||||
if (omapi_connection_require(connection,
|
result = omapi_connection_require(connection,
|
||||||
p->message->authlen)
|
p->message->authlen);
|
||||||
== ISC_R_SUCCESS)
|
if (result == OMAPI_R_NOTYET)
|
||||||
|
break;
|
||||||
|
else if (result == ISC_R_SUCCESS)
|
||||||
goto signature_wait;
|
goto signature_wait;
|
||||||
break;
|
else
|
||||||
|
goto disconnect;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -527,14 +593,14 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
goto disconnect;
|
goto disconnect;
|
||||||
|
|
||||||
p->state = omapi_protocol_name_wait;
|
p->state = omapi_protocol_name_wait;
|
||||||
if (omapi_connection_require(connection, nlen) !=
|
result = omapi_connection_require(connection, nlen);
|
||||||
ISC_R_SUCCESS)
|
if (result == OMAPI_R_NOTYET)
|
||||||
break;
|
break;
|
||||||
|
else if (result != ISC_R_SUCCESS)
|
||||||
|
goto disconnect;
|
||||||
|
|
||||||
|
/* FALLTHROUGH */
|
||||||
|
|
||||||
/*
|
|
||||||
* If it's already here, fall through.
|
|
||||||
* */
|
|
||||||
|
|
||||||
case omapi_protocol_name_wait:
|
case omapi_protocol_name_wait:
|
||||||
result = omapi_connection_copyout(p->name->value, connection,
|
result = omapi_connection_copyout(p->name->value, connection,
|
||||||
p->name->len);
|
p->name->len);
|
||||||
@@ -546,12 +612,12 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
*/
|
*/
|
||||||
p->state = omapi_protocol_value_length_wait;
|
p->state = omapi_protocol_value_length_wait;
|
||||||
result = omapi_connection_require(connection, 4);
|
result = omapi_connection_require(connection, 4);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result == OMAPI_R_NOTYET)
|
||||||
break;
|
break;
|
||||||
|
else if (result != ISC_R_SUCCESS)
|
||||||
|
goto disconnect;
|
||||||
|
|
||||||
/*
|
/* FALLTHROUGH */
|
||||||
* If it's already here, fall through.
|
|
||||||
*/
|
|
||||||
|
|
||||||
case omapi_protocol_value_length_wait:
|
case omapi_protocol_value_length_wait:
|
||||||
omapi_connection_getuint32(connection, &vlen);
|
omapi_connection_getuint32(connection, &vlen);
|
||||||
@@ -571,8 +637,10 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
|
|
||||||
p->state = omapi_protocol_value_wait;
|
p->state = omapi_protocol_value_wait;
|
||||||
result = omapi_connection_require(connection, vlen);
|
result = omapi_connection_require(connection, vlen);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result == OMAPI_R_NOTYET)
|
||||||
break;
|
break;
|
||||||
|
else if (result != ISC_R_SUCCESS)
|
||||||
|
goto disconnect;
|
||||||
/*
|
/*
|
||||||
* If it's already here, fall through.
|
* If it's already here, fall through.
|
||||||
*/
|
*/
|
||||||
@@ -595,8 +663,9 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* We need a generic object to hang off of the
|
* We need a generic object to hang off of the
|
||||||
* incoming message.
|
* incoming message.
|
||||||
*/
|
*/
|
||||||
result = omapi_generic_new(&p->message->object,
|
result =
|
||||||
"omapi_protocol_signal_handler");
|
omapi_object_create(&p->message->object,
|
||||||
|
NULL, 0);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
goto disconnect;
|
goto disconnect;
|
||||||
}
|
}
|
||||||
@@ -611,8 +680,7 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
|
|
||||||
omapi_data_stringdereference(&p->name,
|
omapi_data_stringdereference(&p->name,
|
||||||
"omapi_protocol_signal_handler");
|
"omapi_protocol_signal_handler");
|
||||||
omapi_data_dereference(&p->value,
|
omapi_data_dereference(&p->value);
|
||||||
"omapi_protocol_signal_handler");
|
|
||||||
goto need_name_length;
|
goto need_name_length;
|
||||||
|
|
||||||
signature_wait:
|
signature_wait:
|
||||||
@@ -639,6 +707,18 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
result = omapi_message_process((omapi_object_t *)p->message,
|
result = omapi_message_process((omapi_object_t *)p->message,
|
||||||
h);
|
h);
|
||||||
|
|
||||||
|
/* XXXTL unbind the authenticator. */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Free the message object.
|
||||||
|
*/
|
||||||
|
OBJECT_DEREF(&p->message);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The next thing the protocol reads will be a new message.
|
||||||
|
*/
|
||||||
|
p->state = omapi_protocol_header_wait;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Signal omapi_connection_wait() to wake up.
|
* Signal omapi_connection_wait() to wake up.
|
||||||
* XXXDCL duplicated from above.
|
* XXXDCL duplicated from above.
|
||||||
@@ -653,23 +733,32 @@ omapi_protocol_signal_handler(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
RUNTIME_CHECK(isc_condition_signal(&c->waiter) ==
|
RUNTIME_CHECK(isc_condition_signal(&c->waiter) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If there are no more messages expected, exit
|
||||||
|
* the signal handler.
|
||||||
|
*/
|
||||||
|
if (c->messages_expected == 0) {
|
||||||
|
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
||||||
|
ISC_R_SUCCESS);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
RUNTIME_CHECK(isc_mutex_unlock(&c->mutex) ==
|
||||||
ISC_R_SUCCESS);
|
ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* XXXTL unbind the authenticator. */
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Free the message object.
|
* Proceed to the omapi_connection_require for the next
|
||||||
|
* message's header.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&p->message, "omapi_protocol_signal_handler");
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* XXXDCL these gotos could be cleared up with one
|
* XXXDCL these gotos could be cleared up with one
|
||||||
* more variable to control a loop around the switch.
|
* more variable to control a loop around the switch.
|
||||||
*/
|
*/
|
||||||
fprintf(stderr, "going to header_wait, events_pending = %d\n",
|
fprintf(stderr, "going to header_wait, events_pending = %d"
|
||||||
c->events_pending);
|
" messages_expected = %d\n", c->events_pending,
|
||||||
|
c->messages_expected);
|
||||||
goto to_header_wait;
|
goto to_header_wait;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@@ -712,7 +801,7 @@ omapi_protocol_get_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_protocol_destroy(omapi_object_t *h, const char *name) {
|
omapi_protocol_destroy(omapi_object_t *h) {
|
||||||
omapi_protocol_object_t *p;
|
omapi_protocol_object_t *p;
|
||||||
|
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_protocol);
|
REQUIRE(h != NULL && h->type == omapi_type_protocol);
|
||||||
@@ -720,10 +809,10 @@ omapi_protocol_destroy(omapi_object_t *h, const char *name) {
|
|||||||
p = (omapi_protocol_object_t *)h;
|
p = (omapi_protocol_object_t *)h;
|
||||||
|
|
||||||
if (p->message != NULL)
|
if (p->message != NULL)
|
||||||
OBJECT_DEREF(&p->message, name);
|
OBJECT_DEREF(&p->message);
|
||||||
|
|
||||||
if (p->authinfo != NULL)
|
if (p->authinfo != NULL)
|
||||||
OBJECT_DEREF(&p->authinfo, name);
|
OBJECT_DEREF(&p->authinfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -758,12 +847,12 @@ omapi_protocol_listen(omapi_object_t *h, int port, int max) {
|
|||||||
obj->refcnt = 1;
|
obj->refcnt = 1;
|
||||||
obj->type = omapi_type_protocol_listener;
|
obj->type = omapi_type_protocol_listener;
|
||||||
|
|
||||||
OBJECT_REF(&h->outer, obj, "omapi_protocol_listen");
|
OBJECT_REF(&h->outer, obj);
|
||||||
OBJECT_REF(&obj->inner, h, "omapi_protocol_listen");
|
OBJECT_REF(&obj->inner, h);
|
||||||
|
|
||||||
result = omapi_listener_listen((omapi_object_t *)obj, port, max);
|
result = omapi_listener_listen((omapi_object_t *)obj, port, max);
|
||||||
|
|
||||||
OBJECT_DEREF(&obj, "omapi_protocol_listen");
|
OBJECT_DEREF(&obj);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -800,8 +889,8 @@ omapi_protocol_listener_signal(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* connection.
|
* connection.
|
||||||
*/
|
*/
|
||||||
obj = NULL;
|
obj = NULL;
|
||||||
result = omapi_object_new((omapi_object_t **)&obj, omapi_type_protocol,
|
result = omapi_object_create((omapi_object_t **)&obj,
|
||||||
sizeof(*obj));
|
omapi_type_protocol, sizeof(*obj));
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
/*
|
/*
|
||||||
* When the unsuccessful return value is percolated back to
|
* When the unsuccessful return value is percolated back to
|
||||||
@@ -814,8 +903,8 @@ omapi_protocol_listener_signal(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* Tie the protocol object bidirectionally to the connection
|
* Tie the protocol object bidirectionally to the connection
|
||||||
* object, with the connection as the outer object.
|
* object, with the connection as the outer object.
|
||||||
*/
|
*/
|
||||||
OBJECT_REF(&obj->outer, c, "omapi_protocol_accept");
|
OBJECT_REF(&obj->outer, c);
|
||||||
OBJECT_REF(&c->inner, obj, "omapi_protocol_accept");
|
OBJECT_REF(&c->inner, obj);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Send the introductory message.
|
* Send the introductory message.
|
||||||
@@ -833,7 +922,7 @@ omapi_protocol_listener_signal(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* XXXDCL aigh, this is so confusing. I don't think the
|
* XXXDCL aigh, this is so confusing. I don't think the
|
||||||
* right thing is being done.
|
* right thing is being done.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&c->inner, "omapi_protocol_accept");
|
OBJECT_DEREF(&c->inner);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Remove one of the references to the object, so it will be
|
* Remove one of the references to the object, so it will be
|
||||||
@@ -841,7 +930,7 @@ omapi_protocol_listener_signal(omapi_object_t *h, const char *name, va_list ap)
|
|||||||
* XXXDCL this is what ted did, but i'm not sure my explanation
|
* XXXDCL this is what ted did, but i'm not sure my explanation
|
||||||
* is correct.
|
* is correct.
|
||||||
*/
|
*/
|
||||||
OBJECT_DEREF(&obj, "omapi_protocol_accept");
|
OBJECT_DEREF(&obj);
|
||||||
|
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
@@ -867,10 +956,10 @@ omapi_protocol_listener_get_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
omapi_protocol_listener_destroy(omapi_object_t *h, const char *name) {
|
omapi_protocol_listener_destroy(omapi_object_t *h) {
|
||||||
REQUIRE(h != NULL && h->type == omapi_type_protocol_listener);
|
REQUIRE(h != NULL && h->type == omapi_type_protocol_listener);
|
||||||
|
|
||||||
(void)name; /* Unused. */
|
/* XXXDCL currently NOTHING */
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -898,7 +987,7 @@ omapi_protocol_send_status(omapi_object_t *po, omapi_object_t *id,
|
|||||||
|
|
||||||
REQUIRE(po != NULL && po->type == omapi_type_protocol);
|
REQUIRE(po != NULL && po->type == omapi_type_protocol);
|
||||||
|
|
||||||
result = omapi_message_new(&message, "omapi_protocol_send_status");
|
result = omapi_message_new(&message);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
@@ -918,7 +1007,7 @@ omapi_protocol_send_status(omapi_object_t *po, omapi_object_t *id,
|
|||||||
result = omapi_set_string_value(message, NULL, "message", msg);
|
result = omapi_set_string_value(message, NULL, "message", msg);
|
||||||
|
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&message, "omapi_protocol_send_status");
|
OBJECT_DEREF(&message);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -934,7 +1023,7 @@ omapi_protocol_send_update(omapi_object_t *po, omapi_object_t *id,
|
|||||||
|
|
||||||
REQUIRE(po != NULL && po->type == omapi_type_protocol);
|
REQUIRE(po != NULL && po->type == omapi_type_protocol);
|
||||||
|
|
||||||
result = omapi_message_new(&message, "omapi_protocol_send_update");
|
result = omapi_message_new(&message);
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
@@ -958,7 +1047,7 @@ omapi_protocol_send_update(omapi_object_t *po, omapi_object_t *id,
|
|||||||
"object", object);
|
"object", object);
|
||||||
|
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
OBJECT_DEREF(&message, "dhcpctl_open_object");
|
OBJECT_DEREF(&message);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -27,13 +27,9 @@
|
|||||||
|
|
||||||
omapi_object_type_t *omapi_type_connection;
|
omapi_object_type_t *omapi_type_connection;
|
||||||
omapi_object_type_t *omapi_type_listener;
|
omapi_object_type_t *omapi_type_listener;
|
||||||
omapi_object_type_t *omapi_type_io_object;
|
|
||||||
omapi_object_type_t *omapi_type_datagram;
|
|
||||||
omapi_object_type_t *omapi_type_generic;
|
omapi_object_type_t *omapi_type_generic;
|
||||||
omapi_object_type_t *omapi_type_protocol;
|
omapi_object_type_t *omapi_type_protocol;
|
||||||
omapi_object_type_t *omapi_type_protocol_listener;
|
omapi_object_type_t *omapi_type_protocol_listener;
|
||||||
omapi_object_type_t *omapi_type_waiter;
|
|
||||||
omapi_object_type_t *omapi_type_remote;
|
|
||||||
omapi_object_type_t *omapi_type_message;
|
omapi_object_type_t *omapi_type_message;
|
||||||
|
|
||||||
omapi_object_type_t *omapi_object_types;
|
omapi_object_type_t *omapi_object_types;
|
||||||
@@ -41,7 +37,6 @@ int omapi_object_type_count;
|
|||||||
|
|
||||||
isc_mem_t *omapi_mctx;
|
isc_mem_t *omapi_mctx;
|
||||||
isc_taskmgr_t *omapi_taskmgr;
|
isc_taskmgr_t *omapi_taskmgr;
|
||||||
isc_timermgr_t *omapi_timermgr;
|
|
||||||
isc_socketmgr_t *omapi_socketmgr;
|
isc_socketmgr_t *omapi_socketmgr;
|
||||||
|
|
||||||
isc_boolean_t omapi_ipv6 = ISC_FALSE;
|
isc_boolean_t omapi_ipv6 = ISC_FALSE;
|
||||||
@@ -74,64 +69,27 @@ omapi_init(isc_mem_t *mctx) {
|
|||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
omapi_timermgr = NULL;
|
|
||||||
result = isc_timermgr_create(omapi_mctx, &omapi_timermgr);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
|
||||||
return (result);
|
|
||||||
|
|
||||||
if (isc_net_probeipv6() == ISC_R_SUCCESS)
|
if (isc_net_probeipv6() == ISC_R_SUCCESS)
|
||||||
omapi_ipv6 = ISC_TRUE;
|
omapi_ipv6 = ISC_TRUE;
|
||||||
else
|
else
|
||||||
omapi_ipv6 = ISC_FALSE;
|
omapi_ipv6 = ISC_FALSE;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Register all the standard object types.
|
* Initialize all the standard object types.
|
||||||
*/
|
*/
|
||||||
result = omapi_object_type_register(&omapi_type_connection,
|
result = omapi_generic_init();
|
||||||
"connection",
|
|
||||||
omapi_connection_setvalue,
|
|
||||||
omapi_connection_getvalue,
|
|
||||||
omapi_connection_destroy,
|
|
||||||
omapi_connection_signalhandler,
|
|
||||||
omapi_connection_stuffvalues,
|
|
||||||
0, 0, 0);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_listener,
|
result = omapi_listener_init();
|
||||||
"listener",
|
|
||||||
omapi_listener_setvalue,
|
|
||||||
omapi_listener_getvalue,
|
|
||||||
omapi_listener_destroy,
|
|
||||||
omapi_listener_signalhandler,
|
|
||||||
omapi_listener_stuffvalues,
|
|
||||||
0, 0, 0);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_io_object,
|
result = omapi_connection_init();
|
||||||
"io",
|
|
||||||
omapi_io_setvalue,
|
|
||||||
omapi_io_getvalue,
|
|
||||||
omapi_io_destroy,
|
|
||||||
omapi_io_signalhandler,
|
|
||||||
omapi_io_stuffvalues,
|
|
||||||
0, 0, 0);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_generic,
|
result = omapi_object_register(&omapi_type_protocol,
|
||||||
"generic",
|
|
||||||
omapi_generic_set_value,
|
|
||||||
omapi_generic_get_value,
|
|
||||||
omapi_generic_destroy,
|
|
||||||
omapi_generic_signal_handler,
|
|
||||||
omapi_generic_stuff_values,
|
|
||||||
0, 0, 0);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
|
||||||
return (result);
|
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_protocol,
|
|
||||||
"protocol",
|
"protocol",
|
||||||
omapi_protocol_set_value,
|
omapi_protocol_set_value,
|
||||||
omapi_protocol_get_value,
|
omapi_protocol_get_value,
|
||||||
@@ -142,7 +100,7 @@ omapi_init(isc_mem_t *mctx) {
|
|||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_protocol_listener,
|
result = omapi_object_register(&omapi_type_protocol_listener,
|
||||||
"protocol-listener",
|
"protocol-listener",
|
||||||
omapi_protocol_listener_set_value,
|
omapi_protocol_listener_set_value,
|
||||||
omapi_protocol_listener_get_value,
|
omapi_protocol_listener_get_value,
|
||||||
@@ -153,45 +111,32 @@ omapi_init(isc_mem_t *mctx) {
|
|||||||
if (result != ISC_R_SUCCESS)
|
if (result != ISC_R_SUCCESS)
|
||||||
return (result);
|
return (result);
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_message,
|
result = omapi_message_init();
|
||||||
"message",
|
|
||||||
omapi_message_setvalue,
|
|
||||||
omapi_message_getvalue,
|
|
||||||
omapi_message_destroy,
|
|
||||||
omapi_message_signalhandler,
|
|
||||||
omapi_message_stuffvalues,
|
|
||||||
0, 0, 0);
|
|
||||||
if (result != ISC_R_SUCCESS)
|
|
||||||
return (result);
|
|
||||||
|
|
||||||
result = omapi_object_type_register(&omapi_type_waiter,
|
|
||||||
"waiter",
|
|
||||||
0,
|
|
||||||
0,
|
|
||||||
0,
|
|
||||||
omapi_waiter_signal_handler, 0,
|
|
||||||
0, 0, 0);
|
|
||||||
|
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This does not free connections and other in-use objects, only the
|
||||||
|
* things created by omapi_init(). It is the callers responsibility to
|
||||||
|
* free the other things (as via omapi_connection_disconnect or
|
||||||
|
* omapi_object_dereference).
|
||||||
|
*/
|
||||||
void
|
void
|
||||||
omapi_shutdown() {
|
omapi_destroy() {
|
||||||
omapi_object_type_t *type, *next_type;
|
omapi_object_type_t *type, *next_type;
|
||||||
|
|
||||||
isc_socketmgr_destroy(&omapi_socketmgr);
|
isc_socketmgr_destroy(&omapi_socketmgr);
|
||||||
isc_taskmgr_destroy(&omapi_taskmgr);
|
isc_taskmgr_destroy(&omapi_taskmgr);
|
||||||
isc_timermgr_destroy(&omapi_timermgr);
|
|
||||||
|
|
||||||
for (type = omapi_object_types; type != NULL; type = next_type) {
|
for (type = omapi_object_types; type != NULL; type = next_type) {
|
||||||
next_type = type->next;
|
next_type = type->next;
|
||||||
isc_mem_put(omapi_mctx, type, sizeof(*type));
|
isc_mem_put(omapi_mctx, type, sizeof(*type));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_type_register(omapi_object_type_t **type, const char *name,
|
omapi_object_register(omapi_object_type_t **type, const char *name,
|
||||||
isc_result_t (*set_value)
|
isc_result_t (*set_value)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
omapi_object_t *,
|
omapi_object_t *,
|
||||||
@@ -205,8 +150,7 @@ omapi_object_type_register(omapi_object_type_t **type, const char *name,
|
|||||||
omapi_value_t **),
|
omapi_value_t **),
|
||||||
|
|
||||||
void (*destroy)
|
void (*destroy)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *),
|
||||||
const char *),
|
|
||||||
|
|
||||||
isc_result_t (*signal_handler)
|
isc_result_t (*signal_handler)
|
||||||
(omapi_object_t *,
|
(omapi_object_t *,
|
||||||
@@ -341,7 +285,7 @@ omapi_set_boolean_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
|
|
||||||
result = omapi_set_value(h, id, n, tv);
|
result = omapi_set_value(h, id, n, tv);
|
||||||
omapi_data_stringdereference(&n, "omapi_set_boolean_value");
|
omapi_data_stringdereference(&n, "omapi_set_boolean_value");
|
||||||
omapi_data_dereference(&tv, "omapi_set_boolean_value");
|
omapi_data_dereference(&tv);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -367,7 +311,7 @@ omapi_set_int_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
|
|
||||||
result = omapi_set_value(h, id, n, tv);
|
result = omapi_set_value(h, id, n, tv);
|
||||||
omapi_data_stringdereference(&n, "omapi_set_int_value");
|
omapi_data_stringdereference(&n, "omapi_set_int_value");
|
||||||
omapi_data_dereference(&tv, "omapi_set_int_value");
|
omapi_data_dereference(&tv);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -393,7 +337,7 @@ omapi_set_object_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
|
|
||||||
result = omapi_set_value(h, id, n, tv);
|
result = omapi_set_value(h, id, n, tv);
|
||||||
omapi_data_stringdereference(&n, "omapi_set_object_value");
|
omapi_data_stringdereference(&n, "omapi_set_object_value");
|
||||||
omapi_data_dereference(&tv, "omapi_set_object_value");
|
omapi_data_dereference(&tv);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -419,7 +363,7 @@ omapi_set_string_value(omapi_object_t *h, omapi_object_t *id,
|
|||||||
|
|
||||||
result = omapi_set_value(h, id, n, tv);
|
result = omapi_set_value(h, id, n, tv);
|
||||||
omapi_data_stringdereference(&n, "omapi_set_string_value");
|
omapi_data_stringdereference(&n, "omapi_set_string_value");
|
||||||
omapi_data_dereference(&tv, "omapi_set_string_value");
|
omapi_data_dereference(&tv);
|
||||||
return (result);
|
return (result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -469,18 +413,6 @@ omapi_stuff_values(omapi_object_t *c, omapi_object_t *id, omapi_object_t *o) {
|
|||||||
return (ISC_R_NOTFOUND);
|
return (ISC_R_NOTFOUND);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_result_t
|
|
||||||
omapi_object_create(omapi_object_t **obj, omapi_object_t *id,
|
|
||||||
omapi_object_type_t *type)
|
|
||||||
{
|
|
||||||
REQUIRE(type != NULL);
|
|
||||||
|
|
||||||
if (type->create == NULL)
|
|
||||||
return (ISC_R_NOTIMPLEMENTED);
|
|
||||||
|
|
||||||
return ((*(type->create))(obj, id));
|
|
||||||
}
|
|
||||||
|
|
||||||
isc_result_t
|
isc_result_t
|
||||||
omapi_object_update(omapi_object_t *obj, omapi_object_t *id,
|
omapi_object_update(omapi_object_t *obj, omapi_object_t *id,
|
||||||
omapi_object_t *src, omapi_handle_t handle)
|
omapi_object_t *src, omapi_handle_t handle)
|
||||||
|
Reference in New Issue
Block a user