34 #include <arpa/inet.h> 39 static void trace_connect_input (
trace_type_t *,
unsigned,
char *);
41 static void trace_disconnect_input (
trace_type_t *,
unsigned,
char *);
47 static isc_result_t omapi_connection_connect_internal (
omapi_object_t *);
49 static isc_result_t ctring_from_attribute(
omapi_object_t *obj,
char *attr_name,
56 const char *server_name,
66 log_debug (
"omapi_connect(%s, port=%d)", server_name, port);
69 if (!inet_aton (server_name, &foo)) {
72 he = gethostbyname (server_name);
75 for (i = 0; he -> h_addr_list [i]; i++)
82 if (status != ISC_R_SUCCESS)
84 for (i = 0; i < hix; i++) {
85 addrs -> addresses [i].addrtype = he -> h_addrtype;
86 addrs -> addresses [i].addrlen = he -> h_length;
87 memcpy (addrs -> addresses [i].address,
88 he -> h_addr_list [i],
89 (
unsigned)he -> h_length);
90 addrs -> addresses [i].port = port;
94 if (status != ISC_R_SUCCESS)
96 addrs -> addresses [0].addrtype = AF_INET;
97 addrs -> addresses [0].addrlen =
sizeof foo;
98 memcpy (addrs -> addresses [0].address, &foo,
sizeof foo);
99 addrs -> addresses [0].port = port;
113 struct sockaddr_in local_sin;
116 status = omapi_connection_allocate (&obj,
MDL);
117 if (status != ISC_R_SUCCESS)
122 if (status != ISC_R_SUCCESS) {
123 omapi_connection_dereference (&obj,
MDL);
127 if (status != ISC_R_SUCCESS) {
128 omapi_connection_dereference (&obj,
MDL);
137 #if defined (TRACING) 144 socket (PF_INET, SOCK_STREAM, IPPROTO_TCP);
145 if (obj -> socket < 0) {
146 omapi_connection_dereference (&obj,
MDL);
147 if (errno == EMFILE || errno == ENFILE
149 return ISC_R_NORESOURCES;
150 return ISC_R_UNEXPECTED;
156 if (local_addr -> addrtype != AF_INET) {
158 omapi_connection_dereference (&obj,
MDL);
161 local_sin.sin_port = htons (local_addr -> port);
162 memcpy (&local_sin.sin_addr,
163 local_addr -> address,
164 local_addr -> addrlen);
165 #if defined (HAVE_SA_LEN) 166 local_sin.sin_len =
sizeof local_addr;
168 local_sin.sin_family = AF_INET;
169 memset (&local_sin.sin_zero, 0,
170 sizeof local_sin.sin_zero);
172 if (bind (obj -> socket, (
struct sockaddr *)&local_sin,
173 sizeof local_sin) < 0) {
178 if (errno == EADDRINUSE)
179 return ISC_R_ADDRINUSE;
180 if (errno == EADDRNOTAVAIL)
181 return ISC_R_ADDRNOTAVAIL;
184 return ISC_R_UNEXPECTED;
186 obj -> local_addr = local_sin;
190 if (fcntl (obj -> socket, F_SETFD, 1) < 0) {
191 close (obj -> socket);
192 omapi_connection_dereference (&obj,
MDL);
193 return ISC_R_UNEXPECTED;
199 if (setsockopt (obj -> socket, SOL_SOCKET, SO_REUSEADDR,
200 (
char *)&flag,
sizeof flag) < 0) {
201 omapi_connection_dereference (&obj,
MDL);
202 return ISC_R_UNEXPECTED;
206 if (fcntl (obj -> socket, F_SETFL, O_NONBLOCK) < 0) {
207 omapi_connection_dereference (&obj,
MDL);
208 return ISC_R_UNEXPECTED;
217 if (setsockopt(obj->socket, SOL_SOCKET, SO_NOSIGPIPE,
218 (
char *)&flag,
sizeof(flag)) < 0) {
219 omapi_connection_dereference (&obj,
MDL);
220 return ISC_R_UNEXPECTED;
229 if (status != ISC_R_SUCCESS)
240 if (status == ISC_R_INPROGRESS) {
241 status = ISC_R_SUCCESS;
243 #if defined (TRACING) 249 omapi_connection_dereference (&obj,
MDL);
253 #if defined (TRACING) 261 trace_connect_stop,
MDL);
263 trace_disconnect_input,
264 trace_disconnect_stop,
MDL);
273 int32_t connect_index, listener_index;
274 static int32_t index;
276 if (!omapi_connections) {
277 status = omapi_connection_array_allocate (&omapi_connections,
279 if (status != ISC_R_SUCCESS)
283 status = omapi_connection_array_extend (omapi_connections, obj,
285 if (status != ISC_R_SUCCESS) {
290 #if defined (TRACING) 301 connect_index = htonl (index);
304 listener_index = htonl (obj -> listener -> index);
306 listener_index = htonl (-1);
307 iov [iov_count].
buf = (
char *)&connect_index;
308 iov [iov_count++].
len =
sizeof connect_index;
309 iov [iov_count].
buf = (
char *)&listener_index;
310 iov [iov_count++].
len =
sizeof listener_index;
311 iov [iov_count].
buf = (
char *)&obj -> remote_addr.sin_port;
312 iov [iov_count++].len =
sizeof obj -> remote_addr.sin_port;
313 iov [iov_count].buf = (
char *)&obj -> local_addr.sin_port;
314 iov [iov_count++].
len =
sizeof obj -> local_addr.sin_port;
315 iov [iov_count].
buf = (
char *)&obj -> remote_addr.sin_addr;
316 iov [iov_count++].len =
sizeof obj -> remote_addr.sin_addr;
317 iov [iov_count].buf = (
char *)&obj -> local_addr.sin_addr;
318 iov [iov_count++].
len =
sizeof obj -> local_addr.sin_addr;
327 unsigned length,
char *buf)
329 struct sockaddr_in remote, local;
330 int32_t connect_index, listener_index;
336 if (length != ((
sizeof connect_index) +
337 (
sizeof remote.sin_port) +
338 (
sizeof remote.sin_addr)) * 2) {
339 log_error (
"Trace connect: invalid length %d", length);
343 memset (&remote, 0,
sizeof remote);
344 memset (&local, 0,
sizeof local);
345 memcpy (&connect_index, s,
sizeof connect_index);
346 s +=
sizeof connect_index;
347 memcpy (&listener_index, s,
sizeof listener_index);
348 s +=
sizeof listener_index;
349 memcpy (&remote.sin_port, s,
sizeof remote.sin_port);
350 s +=
sizeof remote.sin_port;
351 memcpy (&local.sin_port, s,
sizeof local.sin_port);
352 s +=
sizeof local.sin_port;
353 memcpy (&remote.sin_addr, s,
sizeof remote.sin_addr);
354 s +=
sizeof remote.sin_addr;
355 memcpy (&local.sin_addr, s,
sizeof local.sin_addr);
356 s +=
sizeof local.sin_addr;
359 connect_index = ntohl (connect_index);
360 listener_index = ntohl (listener_index);
364 if (listener_index != -1) {
369 if (lp -> address.sin_port == local.sin_port) {
370 omapi_listener_reference (&listener, lp,
MDL);
371 omapi_listener_dereference (&lp,
MDL);
378 "Spurious traced listener connect - index ",
379 (
long int)listener_index,
380 inet_ntoa (local.sin_addr),
381 ntohs (local.sin_port));
386 if (status != ISC_R_SUCCESS) {
387 log_error (
"traced listener connect: %s",
388 isc_result_totext (status));
391 omapi_connection_dereference (&obj,
MDL);
392 omapi_listener_dereference (&listener,
MDL);
399 for (i = 0; (lp->connect_list &&
400 i < lp->connect_list->count); i++) {
401 if (!memcmp (&remote.sin_addr,
402 &lp->connect_list->addresses[i].address,
403 sizeof remote.sin_addr) &&
404 (ntohs (remote.sin_port) ==
405 lp->connect_list->addresses[i].port)) {
407 lp->remote_addr = remote;
408 lp->remote_addr.sin_family = AF_INET;
410 lp->index = connect_index;
413 omapi_connection_dereference (&lp,
MDL);
420 log_error (
"Spurious traced connect - index %ld, addr %s, port %d",
421 (
long int)connect_index, inet_ntoa (remote.sin_addr),
422 ntohs (remote.sin_port));
426 static void trace_connect_stop (
trace_type_t *ttype) { }
428 static void trace_disconnect_input (
trace_type_t *ttype,
429 unsigned length,
char *buf)
432 if (length !=
sizeof *index) {
433 log_error (
"trace disconnect: wrong length %d", length);
437 index = (int32_t *)buf;
441 if (lp -> index == ntohl (*index)) {
443 omapi_connection_dereference (&lp,
MDL);
449 log_error (
"trace disconnect: no connection matching index %ld",
450 (
long int)ntohl (*index));
453 static void trace_disconnect_stop (
trace_type_t *ttype) { }
465 #ifdef DEBUG_PROTOCOL 466 log_debug (
"omapi_disconnect(%s)", force ?
"force" :
"");
473 #if defined (TRACING) 478 index = htonl (c -> index);
480 sizeof index, (
char *)&index,
482 if (status != ISC_R_SUCCESS) {
485 isc_result_totext (status));
494 return ISC_R_SUCCESS;
501 if (!shutdown (c -> socket,
SHUT_RD)) {
502 if (c -> out_bytes > 0) {
505 return ISC_R_SUCCESS;
510 #if defined (TRACING) 527 if (h -> outer -> inner)
542 if (h->inner != NULL) {
543 if (h->inner->outer != NULL) {
562 return ISC_R_SUCCESS;
573 c -> bytes_needed = bytes;
574 if (c -> bytes_needed <= c -> in_bytes) {
575 return ISC_R_SUCCESS;
620 status = omapi_connection_connect_internal (h);
621 if (status == ISC_R_INPROGRESS)
622 return ISC_R_INPROGRESS;
624 if (status != ISC_R_SUCCESS)
627 return ISC_R_SUCCESS;
630 static isc_result_t omapi_connection_connect_internal (
omapi_object_t *h)
643 if (getsockopt (c -> socket, SOL_SOCKET, SO_ERROR,
644 (
char *)&error, &sl) < 0) {
646 return ISC_R_SUCCESS;
653 if (c -> cptr >= c -> connect_list -> count) {
656 status = ISC_R_CONNREFUSED;
659 status = ISC_R_NETUNREACH;
669 if (c -> connect_list -> addresses [c -> cptr].addrtype !=
675 memcpy (&c -> remote_addr.sin_addr,
676 &c -> connect_list -> addresses [c -> cptr].address,
677 sizeof c -> remote_addr.sin_addr);
678 c -> remote_addr.sin_family = AF_INET;
679 c -> remote_addr.sin_port =
680 htons (c -> connect_list -> addresses [c -> cptr].port);
681 #if defined (HAVE_SA_LEN) 682 c -> remote_addr.sin_len =
sizeof c -> remote_addr;
684 memset (&c -> remote_addr.sin_zero, 0,
685 sizeof c -> remote_addr.sin_zero);
688 error = connect (c -> socket,
689 (
struct sockaddr *)&c -> remote_addr,
690 sizeof c -> remote_addr);
693 if (error != EINPROGRESS) {
697 status = ISC_R_CONNREFUSED;
700 status = ISC_R_NETUNREACH;
716 sl =
sizeof (c -> local_addr);
717 if (getsockname (c -> socket,
718 (
struct sockaddr *)&c -> local_addr, &sl) < 0) {
732 if (status != ISC_R_SUCCESS) {
739 return ISC_R_INPROGRESS;
755 c -> out_bytes == 0) {
756 #ifdef DEBUG_PROTOCOL 757 log_debug (
"omapi_connection_reaper(): disconnect");
762 #ifdef DEBUG_PROTOCOL 763 log_debug (
"omapi_connection_reaper(): closed");
765 return ISC_R_NOTCONNECTED;
767 return ISC_R_SUCCESS;
773 char *algorithm_str = 0;
774 isc_result_t status = ISC_R_SUCCESS;
777 status = ctring_from_attribute(a,
"name", &name_str);
778 if (status == ISC_R_SUCCESS) {
780 status = ctring_from_attribute(a,
"algorithm", &algorithm_str);
781 if (status == ISC_R_SUCCESS) {
784 if (status == ISC_R_SUCCESS) {
794 status = ISC_R_NOMEMORY;
813 const unsigned char *data,
819 dst_context_t **dctx = (dst_context_t **)context;
824 if (status != ISC_R_SUCCESS) {
832 region.base = (
unsigned char *)data;
834 dst_context_adddata(*dctx, ®ion);
839 unsigned int sigsize;
842 status = dst_key_sigsize(key, &sigsize);
843 if (status != ISC_R_SUCCESS) {
850 if (status != ISC_R_SUCCESS) {
855 status = dst_context_sign(*dctx, &sigbuf);
856 if (status != ISC_R_SUCCESS) {
871 dst_context_destroy(dctx);
875 return ISC_R_SUCCESS;
888 return ISC_R_NOTFOUND;
890 return(dst_key_sigsize(c->
out_key, l));
909 if (c -> in_context) {
922 status = make_dst_key (&c -> in_key,
924 if (status != ISC_R_SUCCESS)
928 return ISC_R_SUCCESS;
934 if (c -> out_context) {
947 status = make_dst_key (&c -> out_key,
949 if (status != ISC_R_SUCCESS)
953 return ISC_R_SUCCESS;
956 if (h -> inner && h -> inner -> type -> set_value)
957 return (*(h -> inner -> type -> set_value))
958 (h -> inner, id, name, value);
959 return ISC_R_NOTFOUND;
970 unsigned int sigsize;
977 if (!c -> in_key || !c -> in_context)
978 return ISC_R_NOTFOUND;
984 if (status != ISC_R_SUCCESS)
993 return ISC_R_NOTFOUND;
995 status = dst_key_sigsize(c->
in_key, &sigsize);
996 if (status != ISC_R_SUCCESS) {
1003 if (!c -> out_key || !c -> out_context)
1004 return ISC_R_NOTFOUND;
1010 if (status != ISC_R_SUCCESS)
1019 return ISC_R_NOTFOUND;
1022 status = dst_key_sigsize(c->
out_key, &sigsize);
1023 if (status != ISC_R_SUCCESS) {
1030 if (h -> inner && h -> inner -> type -> get_value)
1031 return (*(h -> inner -> type -> get_value))
1032 (h -> inner, id, name, value);
1033 return ISC_R_NOTFOUND;
1041 #ifdef DEBUG_PROTOCOL 1042 log_debug (
"omapi_connection_destroy()");
1046 return ISC_R_UNEXPECTED;
1051 omapi_listener_dereference (&c -> listener,
file,
line);
1052 if (c -> connect_list)
1054 return ISC_R_SUCCESS;
1058 const char *name, va_list ap)
1063 #ifdef DEBUG_PROTOCOL 1064 log_debug (
"omapi_connection_signal_handler(%s)", name);
1067 if (h -> inner && h -> inner -> type -> signal_handler)
1068 return (*(h -> inner -> type -> signal_handler)) (h -> inner,
1070 return ISC_R_NOTFOUND;
1083 if (m -> inner && m -> inner -> type -> stuff_values)
1084 return (*(m -> inner -> type -> stuff_values)) (c, id,
1086 return ISC_R_SUCCESS;
1100 static isc_result_t ctring_from_attribute(
omapi_object_t *obj,
char *attr_name,
1102 isc_result_t status = ISC_R_SUCCESS;
1108 if (status != ISC_R_SUCCESS) {
1121 status = ISC_R_NOMEMORY;
isc_result_t omapi_reregister_io_object(omapi_object_t *, int(*)(omapi_object_t *), int(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *))
isc_result_t omapi_disconnect(omapi_object_t *h, int force)
isc_result_t omapi_typed_data_new(const char *, int, omapi_typed_data_t **, omapi_datatype_t,...)
isc_result_t omapi_connection_reader(omapi_object_t *)
isc_result_t omapi_connection_sign_data(int mode, dst_key_t *key, void **context, const unsigned char *data, const unsigned len, omapi_typed_data_t **result)
omapi_object_type_t * omapi_type_connection
isc_result_t omapi_register_io_object(omapi_object_t *, int(*)(omapi_object_t *), int(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *), isc_result_t(*)(omapi_object_t *))
isc_result_t omapi_make_int_value(omapi_value_t **, omapi_data_string_t *, int, const char *, int)
isc_result_t omapi_buffer_dereference(omapi_buffer_t **, const char *, int)
isc_result_t omapi_object_reference(omapi_object_t **, omapi_object_t *, const char *, int)
dhcp_context_t dhcp_gbl_ctx
#define DHCP_R_INVALIDARG
omapi_typed_data_t * value
int int int log_debug(const char *,...) __attribute__((__format__(__printf__
isc_result_t omapi_signal_in(omapi_object_t *, const char *,...)
int log_error(const char *,...) __attribute__((__format__(__printf__
#define DHCP_R_HOSTUNKNOWN
void omapi_connection_trace_setup(void)
struct omapi_typed_data_t::@3::@4 buffer
isc_result_t omapi_connection_output_auth_length(omapi_object_t *h, unsigned *l)
isc_result_t omapi_get_value_str(omapi_object_t *, omapi_object_t *, const char *, omapi_value_t **)
isc_result_t omapi_connection_set_value(omapi_object_t *h, omapi_object_t *id, omapi_data_string_t *name, omapi_typed_data_t *value)
OMAPI_OBJECT_ALLOC(omapi_connection, omapi_connection_object_t, omapi_type_connection)
isc_result_t omapi_addr_list_reference(omapi_addr_list_t **, omapi_addr_list_t *, const char *, int)
trace_type_t * trace_type_register(const char *, void *, void(*)(trace_type_t *, unsigned, char *), void(*)(trace_type_t *), const char *, int)
isc_result_t omapi_connection_writer(omapi_object_t *)
isc_result_t omapi_connect_list(omapi_object_t *c, omapi_addr_list_t *remote_addrs, omapi_addr_t *local_addr)
isc_result_t omapi_object_dereference(omapi_object_t **, const char *, int)
isc_result_t omapi_signal(omapi_object_t *, const char *,...)
isc_result_t trace_write_packet_iov(trace_type_t *, int, trace_iov_t *, const char *, int)
isc_result_t omapi_connection_reaper(omapi_object_t *h)
isc_result_t omapi_connection_require(omapi_object_t *h, unsigned bytes)
void dfree(void *, const char *, int)
isc_result_t omapi_make_value(omapi_value_t **, omapi_data_string_t *, omapi_typed_data_t *, const char *, int)
union omapi_typed_data_t::@3 u
void omapi_connection_register(omapi_connection_object_t *, const char *, int)
isc_result_t omapi_addr_list_dereference(omapi_addr_list_t **, const char *, int)
isc_result_t uerr2isc(int)
void * dmalloc(size_t, const char *, int)
isc_result_t omapi_connect(omapi_object_t *, const char *, unsigned)
isc_result_t omapi_typed_data_reference(omapi_typed_data_t **, omapi_typed_data_t *, const char *, int)
isc_result_t omapi_value_dereference(omapi_value_t **, const char *, int)
isc_result_t omapi_connection_stuff_values(omapi_object_t *c, omapi_object_t *id, omapi_object_t *m)
isc_result_t isclib_make_dst_key(char *inname, char *algorithm, unsigned char *secret, int length, dst_key_t **dstkey)
isc_result_t omapi_connection_get_value(omapi_object_t *h, omapi_object_t *id, omapi_data_string_t *name, omapi_value_t **value)
int omapi_ds_strcmp(omapi_data_string_t *, const char *)
isc_result_t omapi_connection_connect(omapi_object_t *h)
isc_result_t omapi_unregister_io_object(omapi_object_t *)
#define omapi_array_foreach_end(array, stype, var)
isc_result_t omapi_connection_signal_handler(omapi_object_t *h, const char *name, va_list ap)
isc_result_t omapi_listener_connect(omapi_connection_object_t **obj, omapi_listener_object_t *listener, int socket, struct sockaddr_in *remote_addr)
#define OMAPI_ARRAY_TYPE(name, stype)
#define DHCP_R_INCOMPLETE
int omapi_connection_readfd(omapi_object_t *h)
isc_result_t trace_write_packet(trace_type_t *, unsigned, const char *, const char *, int)
int omapi_connection_writefd(omapi_object_t *h)
isc_result_t omapi_connection_destroy(omapi_object_t *h, const char *file, int line)
isc_result_t omapi_typed_data_dereference(omapi_typed_data_t **, const char *, int)
#define omapi_array_foreach_begin(array, stype, var)
isc_result_t omapi_addr_list_new(omapi_addr_list_t **, unsigned, const char *, int)