From 6591a226144d371a6b68fc5e7201a90a77dc9153 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 17 Oct 2004 10:04:49 +0000 Subject: r3016: - converted the events code to talloc - added the new messaging system, based on unix domain sockets. It gets over 10k messages/second on my laptop without any socket cacheing, which is better than I expected. - added a LOCAL-MESSAGING torture test (This used to be commit 3af06478da7ab34a272226d8d9ac87e0a4940cfb) --- source4/lib/messaging/messaging.c | 445 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 445 insertions(+) create mode 100644 source4/lib/messaging/messaging.c (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c new file mode 100644 index 0000000000..f9caf5071c --- /dev/null +++ b/source4/lib/messaging/messaging.c @@ -0,0 +1,445 @@ +/* + Unix SMB/CIFS implementation. + + Samba internal messaging functions + + Copyright (C) Andrew Tridgell 2004 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include "includes.h" + +/* change the message version with any incompatible changes in the protocol */ +#define MESSAGING_VERSION 1 + +struct messaging_state { + servid_t server_id; + struct socket_context *sock; + char *path; + struct dispatch_fn *dispatch; + + struct { + struct event_context *ev; + struct fd_event *fde; + } event; +}; + +/* we have a linked list of dispatch handlers that this messaging + server can deal with */ +struct dispatch_fn { + struct dispatch_fn *next, *prev; + uint32_t msg_type; + void *private; + void (*fn)(void *msg_ctx, void *private, + uint32_t msg_type, servid_t server_id, DATA_BLOB *data); +}; + +/* an individual message */ +struct messaging_rec { + struct messaging_rec *next, *prev; + + struct messaging_state *msg; + struct socket_context *sock; + struct fd_event *fde; + const char *path; + + struct { + uint32_t version; + uint32_t msg_type; + servid_t from; + servid_t to; + uint32_t length; + } header; + + DATA_BLOB data; + + uint32_t ndone; +}; + +/* + A useful function for testing the message system. +*/ +static void ping_message(void *msg_ctx, void *private, + uint32_t msg_type, servid_t src, DATA_BLOB *data) +{ + DEBUG(1,("INFO: Received PING message from server %u [%.*s]\n", + (uint_t)src, data->length, data->data?(const char *)data->data:"")); + messaging_send(msg_ctx, src, MSG_PONG, data); +} + +/* + return the path to a messaging socket +*/ +static char *messaging_path(TALLOC_CTX *mem_ctx, servid_t server_id) +{ + char *name = talloc_asprintf(mem_ctx, "messaging/msg.%u", (unsigned)server_id); + char *ret; + ret = lock_path(mem_ctx, name); + talloc_free(name); + return ret; +} + +/* + dispatch a fully received message +*/ +static void messaging_dispatch(struct messaging_state *msg, struct messaging_rec *rec) +{ + struct dispatch_fn *d; + for (d=msg->dispatch;d;d=d->next) { + if (d->msg_type == rec->header.msg_type) { + d->fn(msg, d->private, d->msg_type, rec->header.from, &rec->data); + } + } + + /* we don't free the record itself here as there may + be more messages from this client */ + data_blob_free(&rec->data); + rec->header.length = 0; + rec->ndone = 0; +} + + +/* + handle IO for a single message +*/ +static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, + time_t t, uint16_t flags) +{ + struct messaging_rec *rec = fde->private; + struct messaging_state *msg = rec->msg; + NTSTATUS status; + + if (rec->ndone < sizeof(rec->header)) { + /* receive the header */ + DATA_BLOB blob; + status = socket_recv(rec->sock, rec, + &blob, sizeof(rec->header) - rec->ndone, 0); + if (NT_STATUS_IS_ERR(status)) { + talloc_free(rec); + return; + } + + if (blob.length == 0) { + return; + } + + memcpy(rec->ndone + (char *)&rec->header, blob.data, blob.length); + rec->ndone += blob.length; + data_blob_free(&blob); + + if (rec->ndone == sizeof(rec->header)) { + if (rec->header.version != MESSAGING_VERSION) { + DEBUG(0,("meessage with wrong version %u\n", + rec->header.version)); + talloc_free(rec); + } + rec->data = data_blob_talloc(rec, NULL, rec->header.length); + if (rec->data.length != rec->header.length) { + DEBUG(0,("Unable to allocate message of size %u\n", + rec->header.length)); + talloc_free(rec); + } + } + } + + if (rec->ndone >= sizeof(rec->header) && + rec->ndone < sizeof(rec->header) + rec->header.length) { + /* receive the body, if any */ + DATA_BLOB blob; + status = socket_recv(rec->sock, rec, + &blob, sizeof(rec->header) + rec->header.length - rec->ndone, 0); + if (NT_STATUS_IS_ERR(status)) { + talloc_free(rec); + return; + } + + if (blob.length == 0) { + return; + } + + memcpy(rec->data.data + (rec->ndone - sizeof(rec->header)), + blob.data, blob.length); + + rec->ndone += blob.length; + } + + if (rec->ndone == sizeof(rec->header) + rec->header.length) { + /* we've got the whole message */ + messaging_dispatch(msg, rec); + } +} + +/* + destroy a messaging record +*/ +static int rec_destructor(void *ptr) +{ + struct messaging_rec *rec = ptr; + struct messaging_state *msg = rec->msg; + event_remove_fd(msg->event.ev, rec->fde); + return 0; +} + +/* + handle a new incoming connection +*/ +static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, + time_t t, uint16_t flags) +{ + struct messaging_state *msg = fde->private; + struct messaging_rec *rec; + NTSTATUS status; + struct fd_event fde2; + + rec = talloc_p(msg, struct messaging_rec); + if (rec == NULL) { + smb_panic("Unable to allocate messaging_rec"); + } + + status = socket_accept(msg->sock, &rec->sock, 0); + if (!NT_STATUS_IS_OK(status)) { + smb_panic("Unable to accept messaging_rec"); + } + talloc_steal(rec, rec->sock); + + rec->msg = msg; + rec->ndone = 0; + rec->header.length = 0; + rec->path = msg->path; + + fde2.private = rec; + fde2.fd = socket_get_fd(rec->sock); + fde2.flags = EVENT_FD_READ; + fde2.handler = messaging_recv_handler; + + rec->fde = event_add_fd(msg->event.ev, &fde2); + + talloc_set_destructor(rec, rec_destructor); +} + +/* + Register a dispatch function for a particular message type. +*/ +void messaging_register(void *ctx, void *private, + uint32_t msg_type, + void (*fn)(void *, void *, uint32_t, servid_t, DATA_BLOB *)) +{ + struct messaging_state *msg = ctx; + struct dispatch_fn *d; + + d = talloc_p(msg, struct dispatch_fn); + d->msg_type = msg_type; + d->private = private; + d->fn = fn; + DLIST_ADD(msg->dispatch, d); +} + +/* + De-register the function for a particular message type. +*/ +void messaging_deregister(void *ctx, uint32_t msg_type) +{ + struct messaging_state *msg = ctx; + struct dispatch_fn *d, *next; + + for (d = msg->dispatch; d; d = next) { + next = d->next; + if (d->msg_type == msg_type) { + DLIST_REMOVE(msg->dispatch, d); + talloc_free(d); + } + } +} + + + +/* + handle IO for sending a message +*/ +static void messaging_send_handler(struct event_context *ev, struct fd_event *fde, + time_t t, uint16_t flags) +{ + struct messaging_rec *rec = fde->private; + NTSTATUS status; + + if (rec->ndone < sizeof(rec->header)) { + /* send the header */ + size_t nsent; + DATA_BLOB blob; + + blob.data = rec->ndone + (char *)&rec->header; + blob.length = sizeof(rec->header) - rec->ndone; + + status = socket_send(rec->sock, rec, &blob, &nsent, 0); + if (NT_STATUS_IS_ERR(status)) { + talloc_free(rec); + return; + } + + if (nsent == 0) { + return; + } + + rec->ndone += nsent; + } + + if (rec->ndone >= sizeof(rec->header) && + rec->ndone < sizeof(rec->header) + rec->header.length) { + /* send the body, if any */ + DATA_BLOB blob; + size_t nsent; + + blob.data = rec->data.data + (rec->ndone - sizeof(rec->header)); + blob.length = rec->header.length - (rec->ndone - sizeof(rec->header)); + + status = socket_send(rec->sock, rec, &blob, &nsent, 0); + if (NT_STATUS_IS_ERR(status)) { + talloc_free(rec); + return; + } + + rec->ndone += nsent; + } + + if (rec->ndone == sizeof(rec->header) + rec->header.length) { + /* we've done the whole message */ + talloc_free(rec); + } +} + + +/* + Send a message to a particular server +*/ +NTSTATUS messaging_send(void *msg_ctx, servid_t server, uint32_t msg_type, DATA_BLOB *data) +{ + struct messaging_state *msg = msg_ctx; + struct messaging_rec *rec; + NTSTATUS status; + struct fd_event fde; + + rec = talloc_p(msg, struct messaging_rec); + if (rec == NULL) { + return NT_STATUS_NO_MEMORY; + } + + rec->msg = msg; + rec->header.version = MESSAGING_VERSION; + rec->header.msg_type = msg_type; + rec->header.from = msg->server_id; + rec->header.to = server; + rec->header.length = data?data->length:0; + if (rec->header.length != 0) { + rec->data = data_blob_talloc(rec, data->data, data->length); + } else { + rec->data = data_blob(NULL, 0); + } + rec->ndone = 0; + + status = socket_create("unix", SOCKET_TYPE_STREAM, &rec->sock, 0); + if (!NT_STATUS_IS_OK(status)) { + talloc_free(rec); + return status; + } + talloc_steal(rec, rec->sock); + + rec->path = messaging_path(rec, server); + + status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + if (!NT_STATUS_IS_OK(status)) { + talloc_free(rec); + return status; + } + + fde.private = rec; + fde.fd = socket_get_fd(rec->sock); + fde.flags = EVENT_FD_WRITE; + fde.handler = messaging_send_handler; + + rec->fde = event_add_fd(msg->event.ev, &fde); + + talloc_set_destructor(rec, rec_destructor); + + return NT_STATUS_OK; +} + + +/* + destroy the messaging context +*/ +static int messaging_destructor(void *msg_ctx) +{ + struct messaging_state *msg = msg_ctx; + event_remove_fd(msg->event.ev, msg->event.fde); + return 0; +} + +/* + create the listening socket and setup the dispatcher +*/ +void *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id, struct event_context *ev) +{ + struct messaging_state *msg; + NTSTATUS status; + struct fd_event fde; + + msg = talloc_p(mem_ctx, struct messaging_state); + if (msg == NULL) { + return NULL; + } + + /* create the messaging directory if needed */ + msg->path = lock_path(msg, "messaging"); + mkdir(msg->path, 0700); + talloc_free(msg->path); + + msg->server_id = server_id; + msg->dispatch = NULL; + msg->path = messaging_path(msg, server_id); + + status = socket_create("unix", SOCKET_TYPE_STREAM, &msg->sock, 0); + if (!NT_STATUS_IS_OK(status)) { + talloc_free(msg); + return NULL; + } + + /* by stealing here we ensure that the socket is cleaned up (and even + deleted) on exit */ + talloc_steal(msg, msg->sock); + + status = socket_listen(msg->sock, msg->path, 0, 50, 0); + if (!NT_STATUS_IS_OK(status)) { + DEBUG(0,("Unable to setup messaging listener for '%s'\n", msg->path)); + talloc_free(msg); + return NULL; + } + + fde.private = msg; + fde.fd = socket_get_fd(msg->sock); + fde.flags = EVENT_FD_READ; + fde.handler = messaging_listen_handler; + + msg->event.ev = ev; + msg->event.fde = event_add_fd(ev, &fde); + + talloc_set_destructor(msg, messaging_destructor); + + messaging_register(msg, NULL, MSG_PING, ping_message); + + return msg; +} + + -- cgit From 5882311fc46132e0f939d3297fd98787ebac41f7 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 17 Oct 2004 12:41:04 +0000 Subject: r3018: handle STATUS_MORE_ENTRIES from socket_recv() in the messaging code (This used to be commit 13739b68d8357d5d330f12b851d0311feb81e545) --- source4/lib/messaging/messaging.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index f9caf5071c..7e87ea45df 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -125,6 +125,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd if (rec->ndone < sizeof(rec->header)) { /* receive the header */ DATA_BLOB blob; + blob.length = 0; status = socket_recv(rec->sock, rec, &blob, sizeof(rec->header) - rec->ndone, 0); if (NT_STATUS_IS_ERR(status)) { @@ -159,6 +160,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd rec->ndone < sizeof(rec->header) + rec->header.length) { /* receive the body, if any */ DATA_BLOB blob; + blob.length = 0; status = socket_recv(rec->sock, rec, &blob, sizeof(rec->header) + rec->header.length - rec->ndone, 0); if (NT_STATUS_IS_ERR(status)) { -- cgit From 6cc8941f05d5c41e04d83382a7e282fcc191ccd1 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 17 Oct 2004 13:33:03 +0000 Subject: r3023: added immediate send of messages when they are first queued. This makes things a bit more efficient (This used to be commit 8380225d326e4bfb3f15fddc72c097870713132a) --- source4/lib/messaging/messaging.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 7e87ea45df..2f9a43c847 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -375,6 +375,8 @@ NTSTATUS messaging_send(void *msg_ctx, servid_t server, uint32_t msg_type, DATA_ talloc_set_destructor(rec, rec_destructor); + messaging_send_handler(msg->event.ev, rec->fde, 0, EVENT_FD_WRITE); + return NT_STATUS_OK; } -- cgit From ca7e02fd3708a048cd691e6c2fc0357ffcc3b694 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 17 Oct 2004 22:28:26 +0000 Subject: r3026: - added automatic retry to messages when the servers listen queue is full. This means callers can just "send and forget" rather than having to check for a temporary failure. The mechanism takes nice advantage of the timed events handling is our events code. A message will only fail now if we completely run out of some resource (such as memory). - changed the test code not to do retries itself, but only to warn on real failures (This used to be commit 8cddc610a25e64c1ad39dd6a2fc2e7f467e04fc9) --- source4/lib/messaging/messaging.c | 49 +++++++++++++++++++++++++++++++++++++-- 1 file changed, 47 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 2f9a43c847..a0aabbbc21 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -49,8 +49,6 @@ struct dispatch_fn { /* an individual message */ struct messaging_rec { - struct messaging_rec *next, *prev; - struct messaging_state *msg; struct socket_context *sock; struct fd_event *fde; @@ -323,6 +321,43 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd } +/* + when the servers listen queue is full we use this to backoff the message +*/ +static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, time_t t) +{ + struct messaging_rec *rec = te->private; + struct messaging_state *msg = rec->msg; + NTSTATUS status; + struct fd_event fde; + + status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { + /* backoff again */ + te->next_event = t+1; + return; + } + + if (!NT_STATUS_IS_OK(status)) { + DEBUG(1,("messaging: Lost message from %u to %u of type %u after backoff - %s\n", + rec->header.from, rec->header.to, rec->header.msg_type, nt_errstr(status))); + talloc_free(rec); + return; + } + + fde.private = rec; + fde.fd = socket_get_fd(rec->sock); + fde.flags = EVENT_FD_WRITE; + fde.handler = messaging_send_handler; + + rec->fde = event_add_fd(msg->event.ev, &fde); + + talloc_set_destructor(rec, rec_destructor); + + messaging_send_handler(msg->event.ev, rec->fde, 0, EVENT_FD_WRITE); +} + + /* Send a message to a particular server */ @@ -361,6 +396,16 @@ NTSTATUS messaging_send(void *msg_ctx, servid_t server, uint32_t msg_type, DATA_ rec->path = messaging_path(rec, server); status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { + /* backoff on this message - the servers listen queue is full */ + struct timed_event te; + te.next_event = time(NULL)+1; + te.handler = messaging_backoff_handler; + te.private = rec; + event_add_timed(msg->event.ev, &te); + return NT_STATUS_OK; + } + if (!NT_STATUS_IS_OK(status)) { talloc_free(rec); return status; -- cgit From d0cc571e30bf49443ac7d1b1a0b896ee72d7d9a6 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 18 Oct 2004 07:40:17 +0000 Subject: r3029: implemented byte range lock timeouts. This adds a pvfs_wait_message() routine which uses the new messaging system, event timers and talloc destructors to give a nice generic async event handling system with a easy to use interface. The extensions to pvfs_lock.c are based on calls to pvfs_wait_message() routines. We now pass all of our smbtorture locking tests, although while writing this code I have thought of some additonal tests that should be added, particularly for lock cancel operations. I'll work on that soon. This commit also extends the smbtorture lock tests to test the rather weird 0xEEFFFFFF locking semantics that I have discovered in win2003. Win2003 treats the 0xEEFFFFFF boundary as special, and will give different error codes on either side of it. Locks on both sides are allowed, the only difference is which error code is given when a lock is denied. Anyone like to hazard a guess as to why? It has me stumped. (This used to be commit 4395c0557ab175d6a8dd99df03c266325949ffa5) --- source4/lib/messaging/messaging.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index a0aabbbc21..e78ec83b4b 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -250,14 +250,15 @@ void messaging_register(void *ctx, void *private, /* De-register the function for a particular message type. */ -void messaging_deregister(void *ctx, uint32_t msg_type) +void messaging_deregister(void *ctx, uint32_t msg_type, void *private) { struct messaging_state *msg = ctx; struct dispatch_fn *d, *next; for (d = msg->dispatch; d; d = next) { next = d->next; - if (d->msg_type == msg_type) { + if (d->msg_type == msg_type && + d->private == private) { DLIST_REMOVE(msg->dispatch, d); talloc_free(d); } -- cgit From 384f87bd38c1133c90e2a57775f139532574e3cc Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 18 Oct 2004 11:47:13 +0000 Subject: r3034: - fixed a bug in message dispatch, when the dispatch function called messaging_deregister() - added a pvfs_lock_close_pending() hook to remove pending locks on file close - fixed the private ptr argument to messaging_deregister() in pvfs_wait - fixed a bug in continuing lock requests after a lock that is blocking a pending lock is removed - removed bogus brl_unlock() call in lock continue - corrected error code for LOCKING_ANDX_CHANGE_LOCKTYPE - expanded the lock cancel test suite to test lock cancel by unlock and by close - added a testsuite for LOCKING_ANDX_CHANGE_LOCKTYPE (This used to be commit 5ef80f034d4aa4dd6810532c63ad041bfc019cb8) --- source4/lib/messaging/messaging.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index e78ec83b4b..b0ca9cc41e 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -95,8 +95,9 @@ static char *messaging_path(TALLOC_CTX *mem_ctx, servid_t server_id) */ static void messaging_dispatch(struct messaging_state *msg, struct messaging_rec *rec) { - struct dispatch_fn *d; - for (d=msg->dispatch;d;d=d->next) { + struct dispatch_fn *d, *next; + for (d=msg->dispatch;d;d=next) { + next = d->next; if (d->msg_type == rec->header.msg_type) { d->fn(msg, d->private, d->msg_type, rec->header.from, &rec->data); } -- cgit From 75ed4f7cc4d39b85cf6dba040cbf188fac3ed464 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 25 Oct 2004 03:30:39 +0000 Subject: r3183: moved the unlink of the messaging unixdom socket to the messaging destructor (This used to be commit ab222b236a091d31b1f5f2cba150a11585ab5836) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index b0ca9cc41e..13c1a049f8 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -435,6 +435,7 @@ static int messaging_destructor(void *msg_ctx) { struct messaging_state *msg = msg_ctx; event_remove_fd(msg->event.ev, msg->event.fde); + unlink(msg->path); return 0; } -- cgit From 05ad898f68a2df1b102af95fdba0704479bde073 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 26 Oct 2004 22:45:33 +0000 Subject: r3271: use "struct messaging_context *" instead of "void *" in messaging API (This used to be commit cc93813e4a09c538ad485dc2b3cb4c9be34f3d18) --- source4/lib/messaging/messaging.c | 41 ++++++++++++++++++--------------------- 1 file changed, 19 insertions(+), 22 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 13c1a049f8..afd18b4f2f 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -25,7 +25,7 @@ /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -struct messaging_state { +struct messaging_context { servid_t server_id; struct socket_context *sock; char *path; @@ -43,13 +43,13 @@ struct dispatch_fn { struct dispatch_fn *next, *prev; uint32_t msg_type; void *private; - void (*fn)(void *msg_ctx, void *private, + void (*fn)(struct messaging_context *msg, void *private, uint32_t msg_type, servid_t server_id, DATA_BLOB *data); }; /* an individual message */ struct messaging_rec { - struct messaging_state *msg; + struct messaging_context *msg; struct socket_context *sock; struct fd_event *fde; const char *path; @@ -70,12 +70,12 @@ struct messaging_rec { /* A useful function for testing the message system. */ -static void ping_message(void *msg_ctx, void *private, +static void ping_message(struct messaging_context *msg, void *private, uint32_t msg_type, servid_t src, DATA_BLOB *data) { DEBUG(1,("INFO: Received PING message from server %u [%.*s]\n", (uint_t)src, data->length, data->data?(const char *)data->data:"")); - messaging_send(msg_ctx, src, MSG_PONG, data); + messaging_send(msg, src, MSG_PONG, data); } /* @@ -93,7 +93,7 @@ static char *messaging_path(TALLOC_CTX *mem_ctx, servid_t server_id) /* dispatch a fully received message */ -static void messaging_dispatch(struct messaging_state *msg, struct messaging_rec *rec) +static void messaging_dispatch(struct messaging_context *msg, struct messaging_rec *rec) { struct dispatch_fn *d, *next; for (d=msg->dispatch;d;d=next) { @@ -118,7 +118,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd time_t t, uint16_t flags) { struct messaging_rec *rec = fde->private; - struct messaging_state *msg = rec->msg; + struct messaging_context *msg = rec->msg; NTSTATUS status; if (rec->ndone < sizeof(rec->header)) { @@ -189,7 +189,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd static int rec_destructor(void *ptr) { struct messaging_rec *rec = ptr; - struct messaging_state *msg = rec->msg; + struct messaging_context *msg = rec->msg; event_remove_fd(msg->event.ev, rec->fde); return 0; } @@ -200,7 +200,7 @@ static int rec_destructor(void *ptr) static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, time_t t, uint16_t flags) { - struct messaging_state *msg = fde->private; + struct messaging_context *msg = fde->private; struct messaging_rec *rec; NTSTATUS status; struct fd_event fde2; @@ -234,11 +234,10 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * /* Register a dispatch function for a particular message type. */ -void messaging_register(void *ctx, void *private, +void messaging_register(struct messaging_context *msg, void *private, uint32_t msg_type, - void (*fn)(void *, void *, uint32_t, servid_t, DATA_BLOB *)) + void (*fn)(struct messaging_context *, void *, uint32_t, servid_t, DATA_BLOB *)) { - struct messaging_state *msg = ctx; struct dispatch_fn *d; d = talloc_p(msg, struct dispatch_fn); @@ -251,9 +250,8 @@ void messaging_register(void *ctx, void *private, /* De-register the function for a particular message type. */ -void messaging_deregister(void *ctx, uint32_t msg_type, void *private) +void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void *private) { - struct messaging_state *msg = ctx; struct dispatch_fn *d, *next; for (d = msg->dispatch; d; d = next) { @@ -329,7 +327,7 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, time_t t) { struct messaging_rec *rec = te->private; - struct messaging_state *msg = rec->msg; + struct messaging_context *msg = rec->msg; NTSTATUS status; struct fd_event fde; @@ -363,9 +361,8 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve /* Send a message to a particular server */ -NTSTATUS messaging_send(void *msg_ctx, servid_t server, uint32_t msg_type, DATA_BLOB *data) +NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t msg_type, DATA_BLOB *data) { - struct messaging_state *msg = msg_ctx; struct messaging_rec *rec; NTSTATUS status; struct fd_event fde; @@ -431,9 +428,9 @@ NTSTATUS messaging_send(void *msg_ctx, servid_t server, uint32_t msg_type, DATA_ /* destroy the messaging context */ -static int messaging_destructor(void *msg_ctx) +static int messaging_destructor(void *ptr) { - struct messaging_state *msg = msg_ctx; + struct messaging_context *msg = ptr; event_remove_fd(msg->event.ev, msg->event.fde); unlink(msg->path); return 0; @@ -442,13 +439,13 @@ static int messaging_destructor(void *msg_ctx) /* create the listening socket and setup the dispatcher */ -void *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id, struct event_context *ev) +struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id, struct event_context *ev) { - struct messaging_state *msg; + struct messaging_context *msg; NTSTATUS status; struct fd_event fde; - msg = talloc_p(mem_ctx, struct messaging_state); + msg = talloc_p(mem_ctx, struct messaging_context); if (msg == NULL) { return NULL; } -- cgit From c6888da1487ab301292c3d4d05d0464833f3ce57 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 28 Oct 2004 04:00:43 +0000 Subject: r3304: changed the API to lib/socket/ a little. The main change is to make socket_recv() take a pre-allocated buffer, rather than allocating one itself. This allows non-blocking users of this API to avoid a memcpy(). As a result our messaging code is now about 10% faster, and the ncacn_ip_tcp and ncalrpc code is also faster. The second change was to remove the unused mem_ctx argument from socket_send(). Having it there implied that memory could be allocated, which meant the caller had to worry about freeing that memory (if for example it is sending in a tight loop using the same memory context). Removing that unused argument keeps life simpler for users. (This used to be commit a16e4756cd68ca8aab4ffc59d4d9db0b6e44dbd1) --- source4/lib/messaging/messaging.c | 36 +++++++++++++++++------------------- 1 file changed, 17 insertions(+), 19 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index afd18b4f2f..09d0c43934 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -123,22 +123,21 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd if (rec->ndone < sizeof(rec->header)) { /* receive the header */ - DATA_BLOB blob; - blob.length = 0; - status = socket_recv(rec->sock, rec, - &blob, sizeof(rec->header) - rec->ndone, 0); + size_t nread; + + status = socket_recv(rec->sock, + rec->ndone + (char *)&rec->header, + sizeof(rec->header) - rec->ndone, &nread, 0); if (NT_STATUS_IS_ERR(status)) { talloc_free(rec); return; } - if (blob.length == 0) { + if (nread == 0) { return; } - memcpy(rec->ndone + (char *)&rec->header, blob.data, blob.length); - rec->ndone += blob.length; - data_blob_free(&blob); + rec->ndone += nread; if (rec->ndone == sizeof(rec->header)) { if (rec->header.version != MESSAGING_VERSION) { @@ -158,23 +157,22 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd if (rec->ndone >= sizeof(rec->header) && rec->ndone < sizeof(rec->header) + rec->header.length) { /* receive the body, if any */ - DATA_BLOB blob; - blob.length = 0; - status = socket_recv(rec->sock, rec, - &blob, sizeof(rec->header) + rec->header.length - rec->ndone, 0); + size_t nread; + + status = socket_recv(rec->sock, + rec->data.data + (rec->ndone - sizeof(rec->header)), + sizeof(rec->header) + rec->header.length - rec->ndone, + &nread, 0); if (NT_STATUS_IS_ERR(status)) { talloc_free(rec); return; } - if (blob.length == 0) { + if (nread == 0) { return; } - memcpy(rec->data.data + (rec->ndone - sizeof(rec->header)), - blob.data, blob.length); - - rec->ndone += blob.length; + rec->ndone += nread; } if (rec->ndone == sizeof(rec->header) + rec->header.length) { @@ -283,7 +281,7 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd blob.data = rec->ndone + (char *)&rec->header; blob.length = sizeof(rec->header) - rec->ndone; - status = socket_send(rec->sock, rec, &blob, &nsent, 0); + status = socket_send(rec->sock, &blob, &nsent, 0); if (NT_STATUS_IS_ERR(status)) { talloc_free(rec); return; @@ -305,7 +303,7 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd blob.data = rec->data.data + (rec->ndone - sizeof(rec->header)); blob.length = rec->header.length - (rec->ndone - sizeof(rec->header)); - status = socket_send(rec->sock, rec, &blob, &nsent, 0); + status = socket_send(rec->sock, &blob, &nsent, 0); if (NT_STATUS_IS_ERR(status)) { talloc_free(rec); return; -- cgit From 990d76f7cbd4339c30f650781c40463234fc47e1 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 28 Oct 2004 07:55:33 +0000 Subject: r3314: added a option "socket:testnonblock" to the generic socket code. If you set this option (either on the command line using --option or in smb.conf) then every socket recv or send will return short by random amounts. This allows you to test that the non-blocking socket logic in your code works correctly. I also removed the flags argument to socket_accept(), and instead made the new socket inherit the flags of the old socket, which makes more sense to me. (This used to be commit 406d356e698da01c84e8aa5b7894752b4403f63c) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 09d0c43934..7f90bd4e40 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -208,7 +208,7 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * smb_panic("Unable to allocate messaging_rec"); } - status = socket_accept(msg->sock, &rec->sock, 0); + status = socket_accept(msg->sock, &rec->sock); if (!NT_STATUS_IS_OK(status)) { smb_panic("Unable to accept messaging_rec"); } -- cgit From 09d0b152b7bd85aa01898af81bd166a7673ab886 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 29 Oct 2004 08:38:59 +0000 Subject: r3360: improved the deletion of tmp files. smbd now puts all tmp files in var/locks/smbd.tmp/ and deletes that dir on startup. (This used to be commit 7e942e7f1bd2c293a0e6648df43a96f8b8a2a295) --- source4/lib/messaging/messaging.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 7f90bd4e40..125089ac62 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -85,7 +85,7 @@ static char *messaging_path(TALLOC_CTX *mem_ctx, servid_t server_id) { char *name = talloc_asprintf(mem_ctx, "messaging/msg.%u", (unsigned)server_id); char *ret; - ret = lock_path(mem_ctx, name); + ret = smbd_tmp_path(mem_ctx, name); talloc_free(name); return ret; } @@ -449,7 +449,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id } /* create the messaging directory if needed */ - msg->path = lock_path(msg, "messaging"); + msg->path = smbd_tmp_path(msg, "messaging"); mkdir(msg->path, 0700); talloc_free(msg->path); -- cgit From ead3508ac81ff3ed2a48753f3b5e23537ba6ec73 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 2 Nov 2004 00:24:21 +0000 Subject: r3447: more include/system/XXX.h include files (This used to be commit 264ce9181089922547e8f6f67116f2d7277a5105) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 125089ac62..a2316919cb 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -21,6 +21,7 @@ */ #include "includes.h" +#include "system/time.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From 3643fb11092e28a9538ef32cedce8ff21ad86a28 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 2 Nov 2004 06:42:15 +0000 Subject: r3463: separated out some more headers (asn_1.h, messages.h, dlinklist.h and ioctl.h) (This used to be commit b97e395c814762024336c1cf4d7c25be8da5813a) --- source4/lib/messaging/messaging.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index a2316919cb..48d608ee94 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -22,6 +22,8 @@ #include "includes.h" #include "system/time.h" +#include "messages.h" +#include "dlinklist.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From a99b6219a810a1cd10bd62a6716780602808f0cd Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 2 Nov 2004 12:15:17 +0000 Subject: r3481: split out client.h and events.h (This used to be commit c6f486574470a311e0d336c026103f131451e21e) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 48d608ee94..f862b2d505 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -21,6 +21,7 @@ */ #include "includes.h" +#include "events.h" #include "system/time.h" #include "messages.h" #include "dlinklist.h" -- cgit From dde07058075d357cfdc63624c8dcaa67ebd40add Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Wed, 3 Nov 2004 10:09:48 +0000 Subject: r3507: - added deferred replies on sharing violation in pvfs open. The deferred reply is short-circuited immediately when the file is closed by another user, allowing it to be opened by the waiting user. - added a sane set of timeval manipulation routines - converted all the events code and code that uses it to use struct timeval instead of time_t, which allows for microsecond resolution instead of 1 second resolution. This was needed for doing the pvfs deferred open code, and is why the patch is so big. (This used to be commit 0d51511d408d91eb5f68a35e980e0875299b1831) --- source4/lib/messaging/messaging.c | 51 +++++++++++++++++++++++++++++++-------- 1 file changed, 41 insertions(+), 10 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index f862b2d505..041554a7c0 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -29,6 +29,9 @@ /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 +/* the number of microseconds to backoff in retrying to send a message */ +#define MESSAGING_BACKOFF 250000 + struct messaging_context { servid_t server_id; struct socket_context *sock; @@ -119,7 +122,7 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r handle IO for a single message */ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, - time_t t, uint16_t flags) + struct timeval t, uint16_t flags) { struct messaging_rec *rec = fde->private; struct messaging_context *msg = rec->msg; @@ -200,7 +203,7 @@ static int rec_destructor(void *ptr) handle a new incoming connection */ static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, - time_t t, uint16_t flags) + struct timeval t, uint16_t flags) { struct messaging_context *msg = fde->private; struct messaging_rec *rec; @@ -272,7 +275,7 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void handle IO for sending a message */ static void messaging_send_handler(struct event_context *ev, struct fd_event *fde, - time_t t, uint16_t flags) + struct timeval t, uint16_t flags) { struct messaging_rec *rec = fde->private; NTSTATUS status; @@ -323,20 +326,34 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd } +/* + wrapper around socket_connect with raised privileges +*/ +static NTSTATUS try_connect(struct messaging_rec *rec) +{ + NTSTATUS status; + void *priv = root_privileges(); + status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + talloc_free(priv); + return status; +} + + /* when the servers listen queue is full we use this to backoff the message */ -static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, time_t t) +static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, + struct timeval t) { struct messaging_rec *rec = te->private; struct messaging_context *msg = rec->msg; NTSTATUS status; struct fd_event fde; - status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + status = try_connect(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { /* backoff again */ - te->next_event = t+1; + te->next_event = timeval_add(&t, 0, MESSAGING_BACKOFF); return; } @@ -356,7 +373,7 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve talloc_set_destructor(rec, rec_destructor); - messaging_send_handler(msg->event.ev, rec->fde, 0, EVENT_FD_WRITE); + messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); } @@ -396,11 +413,11 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t rec->path = messaging_path(rec, server); - status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); + status = try_connect(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { /* backoff on this message - the servers listen queue is full */ struct timed_event te; - te.next_event = time(NULL)+1; + te.next_event = timeval_current_ofs(0, MESSAGING_BACKOFF); te.handler = messaging_backoff_handler; te.private = rec; event_add_timed(msg->event.ev, &te); @@ -421,11 +438,25 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t talloc_set_destructor(rec, rec_destructor); - messaging_send_handler(msg->event.ev, rec->fde, 0, EVENT_FD_WRITE); + messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); return NT_STATUS_OK; } +/* + Send a message to a particular server, with the message containing a single pointer +*/ +NTSTATUS messaging_send_ptr(struct messaging_context *msg, servid_t server, + uint32_t msg_type, void *ptr) +{ + DATA_BLOB blob; + + blob.data = (void *)&ptr; + blob.length = sizeof(void *); + + return messaging_send(msg, server, msg_type, &blob); +} + /* destroy the messaging context -- cgit From 9112a632f6791ffc3c3c1aadd214cbaba8fe816e Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Sat, 4 Dec 2004 13:56:25 +0000 Subject: r4063: - change char * -> uint8_t in struct request_buffer - change smbcli_read/write to take void * for the buffers to match read(2)/write(2) all this fixes a lot of gcc-4 warnings metze (This used to be commit b94f92bc6637f748d6f7049f4f9a30b0b8d18a7a) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 041554a7c0..6975f45c8e 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -285,7 +285,7 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd size_t nsent; DATA_BLOB blob; - blob.data = rec->ndone + (char *)&rec->header; + blob.data = rec->ndone + (uint8_t *)&rec->header; blob.length = sizeof(rec->header) - rec->ndone; status = socket_send(rec->sock, &blob, &nsent, 0); -- cgit From cfc10f2a83b7c6190742498f1027256215cd0b31 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Fri, 14 Jan 2005 01:21:56 +0000 Subject: r4727: add a reference to the event context to that the destructor don't double free the registered events when the event context is first in the talloc_free() hierarchie fixes a bug with process_model_thread and the talloc_steal(conn, ev) metze (This used to be commit 05c3d1c4a6a6350cc8b5fb2ee8201ae6feed3d3d) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6975f45c8e..84c9adc874 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -514,7 +514,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id fde.flags = EVENT_FD_READ; fde.handler = messaging_listen_handler; - msg->event.ev = ev; + msg->event.ev = talloc_reference(msg,ev); msg->event.fde = event_add_fd(ev, &fde); talloc_set_destructor(msg, messaging_destructor); -- cgit From fd62df64188c0f992876c72fdda8a6da5dba3090 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 23 Jan 2005 11:49:15 +0000 Subject: r4943: Smplified the events handling code a lot. The first source of complexity was that events didn't automatically cleanup themselves. This was because the events code was written before we had talloc destructors, so you needed to call event_remove_XX() to clean the event out of the event lists from every piece of code that used events. I have now added automatic event destructors, which in turn allowed me to simplify a lot of the calling code. The 2nd source of complexity was caused by the ref_count, which was needed to cope with event handlers destroying events while handling them, which meant the linked lists became invalid, so the ref_count ws used to mark events for later destruction. The new system is much simpler. I now have a ev->destruction_count, which is incremented in all event destructors. The event dispatch code checks for changes to this and handles it. (This used to be commit a3c7417cfeab429ffb22d5546b205818f531a7b4) --- source4/lib/messaging/messaging.c | 21 ++++----------------- 1 file changed, 4 insertions(+), 17 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 84c9adc874..beceb342c9 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -188,17 +188,6 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd } } -/* - destroy a messaging record -*/ -static int rec_destructor(void *ptr) -{ - struct messaging_rec *rec = ptr; - struct messaging_context *msg = rec->msg; - event_remove_fd(msg->event.ev, rec->fde); - return 0; -} - /* handle a new incoming connection */ @@ -233,7 +222,7 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * rec->fde = event_add_fd(msg->event.ev, &fde2); - talloc_set_destructor(rec, rec_destructor); + talloc_steal(rec, rec->fde); } /* @@ -370,8 +359,7 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve fde.handler = messaging_send_handler; rec->fde = event_add_fd(msg->event.ev, &fde); - - talloc_set_destructor(rec, rec_destructor); + talloc_steal(rec, rec->fde); messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); } @@ -435,8 +423,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t fde.handler = messaging_send_handler; rec->fde = event_add_fd(msg->event.ev, &fde); - - talloc_set_destructor(rec, rec_destructor); + talloc_steal(rec, rec->fde); messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); @@ -464,7 +451,6 @@ NTSTATUS messaging_send_ptr(struct messaging_context *msg, servid_t server, static int messaging_destructor(void *ptr) { struct messaging_context *msg = ptr; - event_remove_fd(msg->event.ev, msg->event.fde); unlink(msg->path); return 0; } @@ -516,6 +502,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id msg->event.ev = talloc_reference(msg,ev); msg->event.fde = event_add_fd(ev, &fde); + talloc_steal(msg, msg->event.fde); talloc_set_destructor(msg, messaging_destructor); -- cgit From 6c14b0133dede38294a812be7f5f5bd5ec3d498b Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 23 Jan 2005 12:17:45 +0000 Subject: r4944: every event_add_*() caller was having to call talloc_steal() to take control of the event, so instead build that into the function. If you pass NULL as mem_ctx then it leaves it as a child of the events structure. (This used to be commit 7f981b9ed96f39027cbfd500f41e0c2be64cbb50) --- source4/lib/messaging/messaging.c | 15 +++++---------- 1 file changed, 5 insertions(+), 10 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index beceb342c9..ca7682f5d2 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -220,9 +220,7 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * fde2.flags = EVENT_FD_READ; fde2.handler = messaging_recv_handler; - rec->fde = event_add_fd(msg->event.ev, &fde2); - - talloc_steal(rec, rec->fde); + rec->fde = event_add_fd(msg->event.ev, &fde2, rec); } /* @@ -358,8 +356,7 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve fde.flags = EVENT_FD_WRITE; fde.handler = messaging_send_handler; - rec->fde = event_add_fd(msg->event.ev, &fde); - talloc_steal(rec, rec->fde); + rec->fde = event_add_fd(msg->event.ev, &fde, rec); messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); } @@ -408,7 +405,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t te.next_event = timeval_current_ofs(0, MESSAGING_BACKOFF); te.handler = messaging_backoff_handler; te.private = rec; - event_add_timed(msg->event.ev, &te); + event_add_timed(msg->event.ev, &te, rec); return NT_STATUS_OK; } @@ -422,8 +419,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t fde.flags = EVENT_FD_WRITE; fde.handler = messaging_send_handler; - rec->fde = event_add_fd(msg->event.ev, &fde); - talloc_steal(rec, rec->fde); + rec->fde = event_add_fd(msg->event.ev, &fde, rec); messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); @@ -501,8 +497,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id fde.handler = messaging_listen_handler; msg->event.ev = talloc_reference(msg,ev); - msg->event.fde = event_add_fd(ev, &fde); - talloc_steal(msg, msg->event.fde); + msg->event.fde = event_add_fd(ev, &fde, msg); talloc_set_destructor(msg, messaging_destructor); -- cgit From 759da3b915e2006d4c87b5ace47f399accd9ce91 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 27 Jan 2005 07:08:20 +0000 Subject: r5037: got rid of all of the TALLOC_DEPRECATED stuff. My apologies for the large commit. I thought this was worthwhile to get done for consistency. (This used to be commit ec32b22ed5ec224f6324f5e069d15e92e38e15c0) --- source4/lib/messaging/messaging.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index ca7682f5d2..e2e8161111 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -199,7 +199,7 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * NTSTATUS status; struct fd_event fde2; - rec = talloc_p(msg, struct messaging_rec); + rec = talloc(msg, struct messaging_rec); if (rec == NULL) { smb_panic("Unable to allocate messaging_rec"); } @@ -232,7 +232,7 @@ void messaging_register(struct messaging_context *msg, void *private, { struct dispatch_fn *d; - d = talloc_p(msg, struct dispatch_fn); + d = talloc(msg, struct dispatch_fn); d->msg_type = msg_type; d->private = private; d->fn = fn; @@ -371,7 +371,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t NTSTATUS status; struct fd_event fde; - rec = talloc_p(msg, struct messaging_rec); + rec = talloc(msg, struct messaging_rec); if (rec == NULL) { return NT_STATUS_NO_MEMORY; } @@ -460,7 +460,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id NTSTATUS status; struct fd_event fde; - msg = talloc_p(mem_ctx, struct messaging_context); + msg = talloc(mem_ctx, struct messaging_context); if (msg == NULL) { return NULL; } -- cgit From 55d4d36993293fee914a009f1d8f05810e347f2b Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 30 Jan 2005 00:54:57 +0000 Subject: r5102: This is a major simplification of the logic for controlling top level servers in smbd. The old code still contained a fairly bit of legacy from the time when smbd was only handling SMB connection. The new code gets rid of all of the smb_server specific code in smbd/, and creates a much simpler infrastructures for new server code. Major changes include: - simplified the process model code a lot. - got rid of the top level server and service structures completely. The top level context is now the event_context. This got rid of service.h and server.h completely (they were the most confusing parts of the old code) - added service_stream.[ch] for the helper functions that are specific to stream type services (services that handle streams, and use a logically separate process per connection) - got rid of the builtin idle_handler code in the service logic, as none of the servers were using it, and it can easily be handled by a server in future by adding its own timed_event to the event context. - fixed some major memory leaks in the rpc server code. - added registration of servers, rather than hard coding our list of possible servers. This allows for servers as modules in the future. - temporarily disabled the winbind code until I add the helper functions for that type of server - added error checking on service startup. If a configured server fails to startup then smbd doesn't startup. - cleaned up the command line handling in smbd, removing unused options (This used to be commit cf6a46c3cbde7b1eb1b86bd3882b953a2de3a42e) --- source4/lib/messaging/messaging.c | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index e2e8161111..09d30027b0 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -33,7 +33,7 @@ #define MESSAGING_BACKOFF 250000 struct messaging_context { - servid_t server_id; + uint32_t server_id; struct socket_context *sock; char *path; struct dispatch_fn *dispatch; @@ -51,7 +51,7 @@ struct dispatch_fn { uint32_t msg_type; void *private; void (*fn)(struct messaging_context *msg, void *private, - uint32_t msg_type, servid_t server_id, DATA_BLOB *data); + uint32_t msg_type, uint32_t server_id, DATA_BLOB *data); }; /* an individual message */ @@ -64,8 +64,8 @@ struct messaging_rec { struct { uint32_t version; uint32_t msg_type; - servid_t from; - servid_t to; + uint32_t from; + uint32_t to; uint32_t length; } header; @@ -78,7 +78,7 @@ struct messaging_rec { A useful function for testing the message system. */ static void ping_message(struct messaging_context *msg, void *private, - uint32_t msg_type, servid_t src, DATA_BLOB *data) + uint32_t msg_type, uint32_t src, DATA_BLOB *data) { DEBUG(1,("INFO: Received PING message from server %u [%.*s]\n", (uint_t)src, data->length, data->data?(const char *)data->data:"")); @@ -88,7 +88,7 @@ static void ping_message(struct messaging_context *msg, void *private, /* return the path to a messaging socket */ -static char *messaging_path(TALLOC_CTX *mem_ctx, servid_t server_id) +static char *messaging_path(TALLOC_CTX *mem_ctx, uint32_t server_id) { char *name = talloc_asprintf(mem_ctx, "messaging/msg.%u", (unsigned)server_id); char *ret; @@ -228,7 +228,7 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * */ void messaging_register(struct messaging_context *msg, void *private, uint32_t msg_type, - void (*fn)(struct messaging_context *, void *, uint32_t, servid_t, DATA_BLOB *)) + void (*fn)(struct messaging_context *, void *, uint32_t, uint32_t, DATA_BLOB *)) { struct dispatch_fn *d; @@ -365,7 +365,7 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve /* Send a message to a particular server */ -NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t msg_type, DATA_BLOB *data) +NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t msg_type, DATA_BLOB *data) { struct messaging_rec *rec; NTSTATUS status; @@ -429,7 +429,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, servid_t server, uint32_t /* Send a message to a particular server, with the message containing a single pointer */ -NTSTATUS messaging_send_ptr(struct messaging_context *msg, servid_t server, +NTSTATUS messaging_send_ptr(struct messaging_context *msg, uint32_t server, uint32_t msg_type, void *ptr) { DATA_BLOB blob; @@ -454,7 +454,7 @@ static int messaging_destructor(void *ptr) /* create the listening socket and setup the dispatcher */ -struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id, struct event_context *ev) +struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id, struct event_context *ev) { struct messaging_context *msg; NTSTATUS status; @@ -496,7 +496,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, servid_t server_id fde.flags = EVENT_FD_READ; fde.handler = messaging_listen_handler; - msg->event.ev = talloc_reference(msg,ev); + msg->event.ev = talloc_reference(msg, ev); msg->event.fde = event_add_fd(ev, &fde, msg); talloc_set_destructor(msg, messaging_destructor); -- cgit From 66170ef8b36b499aa5b44ef10c1bd362a50f2636 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 3 Feb 2005 02:35:52 +0000 Subject: r5185: make all the events data structures private to events.c. This will make it possible to add optimisations to the events code such as keeping the next timed event in a sorted list, and using epoll for file descriptor events. I also removed the loop events code, as it wasn't being used anywhere, and changed timed events to always be one-shot (as adding a new timed event in the event handler is so easy to do if needed) (This used to be commit d7b4b6de51342a65bf46fce772d313f92f8d73d3) --- source4/lib/messaging/messaging.c | 76 ++++++++++++++------------------------- 1 file changed, 26 insertions(+), 50 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 09d30027b0..53b6f434f0 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -122,9 +122,9 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r handle IO for a single message */ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags) + struct timeval t, uint16_t flags, void *private) { - struct messaging_rec *rec = fde->private; + struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); struct messaging_context *msg = rec->msg; NTSTATUS status; @@ -192,12 +192,12 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd handle a new incoming connection */ static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags) + struct timeval t, uint16_t flags, void *private) { - struct messaging_context *msg = fde->private; + struct messaging_context *msg = talloc_get_type(private, + struct messaging_context); struct messaging_rec *rec; NTSTATUS status; - struct fd_event fde2; rec = talloc(msg, struct messaging_rec); if (rec == NULL) { @@ -210,17 +210,12 @@ static void messaging_listen_handler(struct event_context *ev, struct fd_event * } talloc_steal(rec, rec->sock); - rec->msg = msg; - rec->ndone = 0; + rec->msg = msg; + rec->ndone = 0; rec->header.length = 0; - rec->path = msg->path; - - fde2.private = rec; - fde2.fd = socket_get_fd(rec->sock); - fde2.flags = EVENT_FD_READ; - fde2.handler = messaging_recv_handler; - - rec->fde = event_add_fd(msg->event.ev, &fde2, rec); + rec->path = msg->path; + rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), + EVENT_FD_READ, messaging_recv_handler, rec); } /* @@ -262,9 +257,9 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void handle IO for sending a message */ static void messaging_send_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags) + struct timeval t, uint16_t flags, void *private) { - struct messaging_rec *rec = fde->private; + struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); NTSTATUS status; if (rec->ndone < sizeof(rec->header)) { @@ -330,17 +325,18 @@ static NTSTATUS try_connect(struct messaging_rec *rec) when the servers listen queue is full we use this to backoff the message */ static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, - struct timeval t) + struct timeval t, void *private) { - struct messaging_rec *rec = te->private; + struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); struct messaging_context *msg = rec->msg; NTSTATUS status; - struct fd_event fde; status = try_connect(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { /* backoff again */ - te->next_event = timeval_add(&t, 0, MESSAGING_BACKOFF); + event_add_timed(msg->event.ev, rec, + timeval_add(&t, 0, MESSAGING_BACKOFF), + messaging_backoff_handler, rec); return; } @@ -351,14 +347,8 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve return; } - fde.private = rec; - fde.fd = socket_get_fd(rec->sock); - fde.flags = EVENT_FD_WRITE; - fde.handler = messaging_send_handler; - - rec->fde = event_add_fd(msg->event.ev, &fde, rec); - - messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); + rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), + EVENT_FD_WRITE, messaging_send_handler, rec); } @@ -369,7 +359,6 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t { struct messaging_rec *rec; NTSTATUS status; - struct fd_event fde; rec = talloc(msg, struct messaging_rec); if (rec == NULL) { @@ -401,11 +390,9 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t status = try_connect(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { /* backoff on this message - the servers listen queue is full */ - struct timed_event te; - te.next_event = timeval_current_ofs(0, MESSAGING_BACKOFF); - te.handler = messaging_backoff_handler; - te.private = rec; - event_add_timed(msg->event.ev, &te, rec); + event_add_timed(msg->event.ev, rec, + timeval_current_ofs(0, MESSAGING_BACKOFF), + messaging_backoff_handler, rec); return NT_STATUS_OK; } @@ -414,14 +401,8 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t return status; } - fde.private = rec; - fde.fd = socket_get_fd(rec->sock); - fde.flags = EVENT_FD_WRITE; - fde.handler = messaging_send_handler; - - rec->fde = event_add_fd(msg->event.ev, &fde, rec); - - messaging_send_handler(msg->event.ev, rec->fde, timeval_zero(), EVENT_FD_WRITE); + rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), + EVENT_FD_WRITE, messaging_send_handler, rec); return NT_STATUS_OK; } @@ -458,7 +439,6 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id { struct messaging_context *msg; NTSTATUS status; - struct fd_event fde; msg = talloc(mem_ctx, struct messaging_context); if (msg == NULL) { @@ -491,13 +471,9 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id return NULL; } - fde.private = msg; - fde.fd = socket_get_fd(msg->sock); - fde.flags = EVENT_FD_READ; - fde.handler = messaging_listen_handler; - msg->event.ev = talloc_reference(msg, ev); - msg->event.fde = event_add_fd(ev, &fde, msg); + msg->event.fde = event_add_fd(ev, msg, socket_get_fd(msg->sock), + EVENT_FD_READ, messaging_listen_handler, msg); talloc_set_destructor(msg, messaging_destructor); -- cgit From 0798d54b4fc28be881e2c4012663b1461bc85ba7 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 3 Feb 2005 11:25:52 +0000 Subject: r5195: most events don't need the time of the event, so save a gettimeofday() call and just use timeval_current() when its actually needed (This used to be commit 236403cc4dc2924ed6a898acae0bb44cc1688dcc) --- source4/lib/messaging/messaging.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 53b6f434f0..24205e5151 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -122,7 +122,7 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r handle IO for a single message */ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags, void *private) + uint16_t flags, void *private) { struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); struct messaging_context *msg = rec->msg; @@ -192,7 +192,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd handle a new incoming connection */ static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags, void *private) + uint16_t flags, void *private) { struct messaging_context *msg = talloc_get_type(private, struct messaging_context); @@ -257,7 +257,7 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void handle IO for sending a message */ static void messaging_send_handler(struct event_context *ev, struct fd_event *fde, - struct timeval t, uint16_t flags, void *private) + uint16_t flags, void *private) { struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); NTSTATUS status; -- cgit From 131dc76d56df40b3511c47e54f15412a25b491f8 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 3 Feb 2005 11:56:03 +0000 Subject: r5197: moved events code to lib/events/ (suggestion from metze) (This used to be commit 7f54c8a339f36aa43c9340be70ab7f0067593ef2) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 24205e5151..aab13ba8af 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -21,7 +21,7 @@ */ #include "includes.h" -#include "events.h" +#include "lib/events/events.h" #include "system/time.h" #include "messages.h" #include "dlinklist.h" -- cgit From e82aad1ce39a6b7a2e51b9e2cb494d74ec70e158 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 10 Feb 2005 05:09:35 +0000 Subject: r5298: - got rid of pstring.h from includes.h. This at least makes it a bit less likely that anyone will use pstring for new code - got rid of winbind_client.h from includes.h. This one triggered a huge change, as winbind_client.h was including system/filesys.h and defining the old uint32 and uint16 types, as well as its own pstring and fstring. (This used to be commit 9db6c79e902ec538108d6b7d3324039aabe1704f) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index aab13ba8af..df0216617d 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -22,6 +22,7 @@ #include "includes.h" #include "lib/events/events.h" +#include "system/filesys.h" #include "system/time.h" #include "messages.h" #include "dlinklist.h" -- cgit From bed7c9ec32b7d4083ba4ed2abbf3b6126bee7a25 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 10 Feb 2005 06:59:29 +0000 Subject: r5304: removed lib/socket/socket.h from includes.h (This used to be commit b902ea546d2d1327b23f40ddaeeaa8e7e3662454) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index df0216617d..8127e7e8fc 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -26,6 +26,7 @@ #include "system/time.h" #include "messages.h" #include "dlinklist.h" +#include "lib/socket/socket.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From 7282ddda0a38139fa457e6451f100f6d1792d927 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 1 May 2005 18:49:07 +0000 Subject: r6561: re-did the internal message system based on DGRAM unix domain sockets. This gains us about 40% in messaging speed. (This used to be commit f244a64ed537447e44229172427b5b6a5c64800c) --- source4/lib/messaging/messaging.c | 202 ++++++++++++-------------------------- 1 file changed, 64 insertions(+), 138 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 8127e7e8fc..c95028bea5 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -34,10 +34,13 @@ /* the number of microseconds to backoff in retrying to send a message */ #define MESSAGING_BACKOFF 250000 +/* maximum message size */ +#define MESSAGING_MAX_SIZE 512 + struct messaging_context { uint32_t server_id; struct socket_context *sock; - char *path; + const char *path; struct dispatch_fn *dispatch; struct { @@ -60,7 +63,6 @@ struct dispatch_fn { struct messaging_rec { struct messaging_context *msg; struct socket_context *sock; - struct fd_event *fde; const char *path; struct { @@ -72,8 +74,6 @@ struct messaging_rec { } header; DATA_BLOB data; - - uint32_t ndone; }; /* @@ -112,112 +112,58 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r } } - /* we don't free the record itself here as there may - be more messages from this client */ - data_blob_free(&rec->data); rec->header.length = 0; - rec->ndone = 0; } /* - handle IO for a single message + handle a new incoming connection */ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, uint16_t flags, void *private) { - struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); - struct messaging_context *msg = rec->msg; + struct messaging_context *msg = talloc_get_type(private, + struct messaging_context); + struct messaging_rec *rec; NTSTATUS status; + uint8_t data[MESSAGING_MAX_SIZE]; + size_t msize; - if (rec->ndone < sizeof(rec->header)) { - /* receive the header */ - size_t nread; - - status = socket_recv(rec->sock, - rec->ndone + (char *)&rec->header, - sizeof(rec->header) - rec->ndone, &nread, 0); - if (NT_STATUS_IS_ERR(status)) { - talloc_free(rec); - return; - } - - if (nread == 0) { - return; - } - - rec->ndone += nread; - - if (rec->ndone == sizeof(rec->header)) { - if (rec->header.version != MESSAGING_VERSION) { - DEBUG(0,("meessage with wrong version %u\n", - rec->header.version)); - talloc_free(rec); - } - rec->data = data_blob_talloc(rec, NULL, rec->header.length); - if (rec->data.length != rec->header.length) { - DEBUG(0,("Unable to allocate message of size %u\n", - rec->header.length)); - talloc_free(rec); - } - } - } - - if (rec->ndone >= sizeof(rec->header) && - rec->ndone < sizeof(rec->header) + rec->header.length) { - /* receive the body, if any */ - size_t nread; - - status = socket_recv(rec->sock, - rec->data.data + (rec->ndone - sizeof(rec->header)), - sizeof(rec->header) + rec->header.length - rec->ndone, - &nread, 0); - if (NT_STATUS_IS_ERR(status)) { - talloc_free(rec); - return; - } - - if (nread == 0) { - return; - } - - rec->ndone += nread; + status = socket_recv(msg->sock, data, sizeof(data), &msize, 0); + if (!NT_STATUS_IS_OK(status)) { + return; } - if (rec->ndone == sizeof(rec->header) + rec->header.length) { - /* we've got the whole message */ - messaging_dispatch(msg, rec); + if (msize < sizeof(rec->header)) { + DEBUG(0,("messaging: bad message of size %d\n", msize)); + return; } -} - -/* - handle a new incoming connection -*/ -static void messaging_listen_handler(struct event_context *ev, struct fd_event *fde, - uint16_t flags, void *private) -{ - struct messaging_context *msg = talloc_get_type(private, - struct messaging_context); - struct messaging_rec *rec; - NTSTATUS status; rec = talloc(msg, struct messaging_rec); if (rec == NULL) { smb_panic("Unable to allocate messaging_rec"); } - status = socket_accept(msg->sock, &rec->sock); - if (!NT_STATUS_IS_OK(status)) { - smb_panic("Unable to accept messaging_rec"); - } - talloc_steal(rec, rec->sock); - rec->msg = msg; - rec->ndone = 0; - rec->header.length = 0; rec->path = msg->path; - rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), - EVENT_FD_READ, messaging_recv_handler, rec); + rec->sock = NULL; + + memcpy(&rec->header, data, sizeof(rec->header)); + if (msize != sizeof(rec->header) + rec->header.length) { + DEBUG(0,("messaging: bad message header size %d should be %d\n", + rec->header.length, msize - sizeof(rec->header))); + talloc_free(rec); + return; + } + + rec->data = data_blob_talloc(rec, data, rec->header.length); + if (rec->data.data == NULL) { + talloc_free(rec); + return; + } + + messaging_dispatch(msg, rec); + talloc_free(rec); } /* @@ -262,49 +208,28 @@ static void messaging_send_handler(struct event_context *ev, struct fd_event *fd uint16_t flags, void *private) { struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); + uint8_t data[MESSAGING_MAX_SIZE]; + DATA_BLOB blob; + size_t nsent; NTSTATUS status; - if (rec->ndone < sizeof(rec->header)) { - /* send the header */ - size_t nsent; - DATA_BLOB blob; - - blob.data = rec->ndone + (uint8_t *)&rec->header; - blob.length = sizeof(rec->header) - rec->ndone; - - status = socket_send(rec->sock, &blob, &nsent, 0); - if (NT_STATUS_IS_ERR(status)) { - talloc_free(rec); - return; - } - - if (nsent == 0) { - return; - } - - rec->ndone += nsent; - } - - if (rec->ndone >= sizeof(rec->header) && - rec->ndone < sizeof(rec->header) + rec->header.length) { - /* send the body, if any */ - DATA_BLOB blob; - size_t nsent; - - blob.data = rec->data.data + (rec->ndone - sizeof(rec->header)); - blob.length = rec->header.length - (rec->ndone - sizeof(rec->header)); + memcpy(data, &rec->header, sizeof(rec->header)); + memcpy(data + sizeof(rec->header), rec->data.data, rec->data.length); - status = socket_send(rec->sock, &blob, &nsent, 0); - if (NT_STATUS_IS_ERR(status)) { - talloc_free(rec); - return; - } + blob.data = data; + blob.length = sizeof(rec->header) + rec->header.length; - rec->ndone += nsent; + status = socket_send(rec->sock, &blob, &nsent, 0); + if (NT_STATUS_IS_ERR(status)) { + DEBUG(3,("Unable to send message of type %d length %d - %s\n", + rec->header.msg_type, + rec->header.length, + nt_errstr(status))); + talloc_free(rec); + return; } - if (rec->ndone == sizeof(rec->header) + rec->header.length) { - /* we've done the whole message */ + if (NT_STATUS_IS_OK(status)) { talloc_free(rec); } } @@ -349,8 +274,8 @@ static void messaging_backoff_handler(struct event_context *ev, struct timed_eve return; } - rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), - EVENT_FD_WRITE, messaging_send_handler, rec); + event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), + EVENT_FD_WRITE, messaging_send_handler, rec); } @@ -378,9 +303,8 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t } else { rec->data = data_blob(NULL, 0); } - rec->ndone = 0; - status = socket_create("unix", SOCKET_TYPE_STREAM, &rec->sock, 0); + status = socket_create("unix", SOCKET_TYPE_DGRAM, &rec->sock, 0); if (!NT_STATUS_IS_OK(status)) { talloc_free(rec); return status; @@ -403,8 +327,8 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t return status; } - rec->fde = event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), - EVENT_FD_WRITE, messaging_send_handler, rec); + event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), + EVENT_FD_WRITE, messaging_send_handler, rec); return NT_STATUS_OK; } @@ -437,10 +361,12 @@ static int messaging_destructor(void *ptr) /* create the listening socket and setup the dispatcher */ -struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id, struct event_context *ev) +struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id, + struct event_context *ev) { struct messaging_context *msg; NTSTATUS status; + char *path; msg = talloc(mem_ctx, struct messaging_context); if (msg == NULL) { @@ -448,15 +374,15 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id } /* create the messaging directory if needed */ - msg->path = smbd_tmp_path(msg, "messaging"); - mkdir(msg->path, 0700); - talloc_free(msg->path); + path = smbd_tmp_path(msg, "messaging"); + mkdir(path, 0700); + talloc_free(path); + msg->path = messaging_path(msg, server_id); msg->server_id = server_id; msg->dispatch = NULL; - msg->path = messaging_path(msg, server_id); - status = socket_create("unix", SOCKET_TYPE_STREAM, &msg->sock, 0); + status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { talloc_free(msg); return NULL; @@ -475,7 +401,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id msg->event.ev = talloc_reference(msg, ev); msg->event.fde = event_add_fd(ev, msg, socket_get_fd(msg->sock), - EVENT_FD_READ, messaging_listen_handler, msg); + EVENT_FD_READ, messaging_recv_handler, msg); talloc_set_destructor(msg, messaging_destructor); -- cgit From fc5c075cff223d36f25b79650c3f739e8d79a801 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 2 May 2005 15:58:03 +0000 Subject: r6578: brown paper bag time with the new messaging code .... (This used to be commit d465ff67bd10340ecd46480039f483daa82c7ebe) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index c95028bea5..2130958b36 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -156,7 +156,7 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd return; } - rec->data = data_blob_talloc(rec, data, rec->header.length); + rec->data = data_blob_talloc(rec, data+sizeof(rec->header), rec->header.length); if (rec->data.data == NULL) { talloc_free(rec); return; -- cgit From dd43abbd325874b7b6bcfdad453b7507ace4314a Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 3 Jun 2005 04:21:25 +0000 Subject: r7206: changed the messaging library to use sendto instead of a connected send on the unix domain datagram socket. This gains us about 50% in speed, and also means that we don't run the risk of running out of file descriptors due to heavy messaging traffic. We now use a single file descriptor no matter how many messages are pending to any number of servers. (This used to be commit 2369170fc1b4ff9a48284779fa6d3a6254177ec1) --- source4/lib/messaging/messaging.c | 213 +++++++++++++++++--------------------- 1 file changed, 94 insertions(+), 119 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 2130958b36..4d2cd9c910 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -31,9 +31,6 @@ /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -/* the number of microseconds to backoff in retrying to send a message */ -#define MESSAGING_BACKOFF 250000 - /* maximum message size */ #define MESSAGING_MAX_SIZE 512 @@ -42,6 +39,7 @@ struct messaging_context { struct socket_context *sock; const char *path; struct dispatch_fn *dispatch; + struct messaging_rec *pending; struct { struct event_context *ev; @@ -61,8 +59,8 @@ struct dispatch_fn { /* an individual message */ struct messaging_rec { + struct messaging_rec *next, *prev; struct messaging_context *msg; - struct socket_context *sock; const char *path; struct { @@ -76,6 +74,7 @@ struct messaging_rec { DATA_BLOB data; }; + /* A useful function for testing the message system. */ @@ -111,19 +110,67 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r d->fn(msg, d->private, d->msg_type, rec->header.from, &rec->data); } } - rec->header.length = 0; } /* - handle a new incoming connection + try to send the message */ -static void messaging_recv_handler(struct event_context *ev, struct fd_event *fde, - uint16_t flags, void *private) +static NTSTATUS try_send(struct messaging_rec *rec) +{ + struct messaging_context *msg = rec->msg; + DATA_BLOB blob; + size_t nsent; + void *priv; + NTSTATUS status; + + blob = data_blob_talloc(rec, NULL, sizeof(rec->header) + rec->data.length); + NT_STATUS_HAVE_NO_MEMORY(blob.data); + + memcpy(blob.data, &rec->header, sizeof(rec->header)); + memcpy(blob.data + sizeof(rec->header), rec->data.data, rec->data.length); + + /* we send with privileges so messages work from any context */ + priv = root_privileges(); + status = socket_sendto(msg->sock, &blob, &nsent, 0, rec->path, 0); + talloc_free(priv); + + data_blob_free(&blob); + + return status; +} + +/* + handle a socket write event +*/ +static void messaging_send_handler(struct messaging_context *msg) +{ + while (msg->pending) { + struct messaging_rec *rec = msg->pending; + NTSTATUS status; + status = try_send(rec); + if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { + break; + } + if (!NT_STATUS_IS_OK(status)) { + DEBUG(1,("messaging: Lost message from %u to %u of type %u - %s\n", + rec->header.from, rec->header.to, rec->header.msg_type, + nt_errstr(status))); + } + DLIST_REMOVE(msg->pending, rec); + talloc_free(rec); + } + if (msg->pending == NULL) { + EVENT_FD_NOT_WRITEABLE(msg->event.fde); + } +} + +/* + handle a new incoming packet +*/ +static void messaging_recv_handler(struct messaging_context *msg) { - struct messaging_context *msg = talloc_get_type(private, - struct messaging_context); struct messaging_rec *rec; NTSTATUS status; uint8_t data[MESSAGING_MAX_SIZE]; @@ -146,7 +193,6 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd rec->msg = msg; rec->path = msg->path; - rec->sock = NULL; memcpy(&rec->header, data, sizeof(rec->header)); if (msize != sizeof(rec->header) + rec->header.length) { @@ -166,6 +212,24 @@ static void messaging_recv_handler(struct event_context *ev, struct fd_event *fd talloc_free(rec); } + +/* + handle a socket event +*/ +static void messaging_handler(struct event_context *ev, struct fd_event *fde, + uint16_t flags, void *private) +{ + struct messaging_context *msg = talloc_get_type(private, + struct messaging_context); + if (flags & EVENT_FD_WRITE) { + messaging_send_handler(msg); + } + if (flags & EVENT_FD_READ) { + messaging_recv_handler(msg); + } +} + + /* Register a dispatch function for a particular message type. */ @@ -200,89 +264,11 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void } - -/* - handle IO for sending a message -*/ -static void messaging_send_handler(struct event_context *ev, struct fd_event *fde, - uint16_t flags, void *private) -{ - struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); - uint8_t data[MESSAGING_MAX_SIZE]; - DATA_BLOB blob; - size_t nsent; - NTSTATUS status; - - memcpy(data, &rec->header, sizeof(rec->header)); - memcpy(data + sizeof(rec->header), rec->data.data, rec->data.length); - - blob.data = data; - blob.length = sizeof(rec->header) + rec->header.length; - - status = socket_send(rec->sock, &blob, &nsent, 0); - if (NT_STATUS_IS_ERR(status)) { - DEBUG(3,("Unable to send message of type %d length %d - %s\n", - rec->header.msg_type, - rec->header.length, - nt_errstr(status))); - talloc_free(rec); - return; - } - - if (NT_STATUS_IS_OK(status)) { - talloc_free(rec); - } -} - - -/* - wrapper around socket_connect with raised privileges -*/ -static NTSTATUS try_connect(struct messaging_rec *rec) -{ - NTSTATUS status; - void *priv = root_privileges(); - status = socket_connect(rec->sock, NULL, 0, rec->path, 0, 0); - talloc_free(priv); - return status; -} - - -/* - when the servers listen queue is full we use this to backoff the message -*/ -static void messaging_backoff_handler(struct event_context *ev, struct timed_event *te, - struct timeval t, void *private) -{ - struct messaging_rec *rec = talloc_get_type(private, struct messaging_rec); - struct messaging_context *msg = rec->msg; - NTSTATUS status; - - status = try_connect(rec); - if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { - /* backoff again */ - event_add_timed(msg->event.ev, rec, - timeval_add(&t, 0, MESSAGING_BACKOFF), - messaging_backoff_handler, rec); - return; - } - - if (!NT_STATUS_IS_OK(status)) { - DEBUG(1,("messaging: Lost message from %u to %u of type %u after backoff - %s\n", - rec->header.from, rec->header.to, rec->header.msg_type, nt_errstr(status))); - talloc_free(rec); - return; - } - - event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), - EVENT_FD_WRITE, messaging_send_handler, rec); -} - - /* Send a message to a particular server */ -NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t msg_type, DATA_BLOB *data) +NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, + uint32_t msg_type, DATA_BLOB *data) { struct messaging_rec *rec; NTSTATUS status; @@ -292,45 +278,32 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, uint32_t return NT_STATUS_NO_MEMORY; } - rec->msg = msg; - rec->header.version = MESSAGING_VERSION; + rec->msg = msg; + rec->header.version = MESSAGING_VERSION; rec->header.msg_type = msg_type; - rec->header.from = msg->server_id; - rec->header.to = server; - rec->header.length = data?data->length:0; + rec->header.from = msg->server_id; + rec->header.to = server; + rec->header.length = data?data->length:0; if (rec->header.length != 0) { rec->data = data_blob_talloc(rec, data->data, data->length); } else { rec->data = data_blob(NULL, 0); } - status = socket_create("unix", SOCKET_TYPE_DGRAM, &rec->sock, 0); - if (!NT_STATUS_IS_OK(status)) { - talloc_free(rec); - return status; - } - talloc_steal(rec, rec->sock); - rec->path = messaging_path(rec, server); - status = try_connect(rec); + status = try_send(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { - /* backoff on this message - the servers listen queue is full */ - event_add_timed(msg->event.ev, rec, - timeval_current_ofs(0, MESSAGING_BACKOFF), - messaging_backoff_handler, rec); + if (msg->pending == NULL) { + EVENT_FD_WRITEABLE(msg->event.fde); + } + DLIST_ADD(msg->pending, rec); return NT_STATUS_OK; } - if (!NT_STATUS_IS_OK(status)) { - talloc_free(rec); - return status; - } - - event_add_fd(msg->event.ev, rec, socket_get_fd(rec->sock), - EVENT_FD_WRITE, messaging_send_handler, rec); + talloc_free(rec); - return NT_STATUS_OK; + return status; } /* @@ -381,6 +354,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id msg->path = messaging_path(msg, server_id); msg->server_id = server_id; msg->dispatch = NULL; + msg->pending = NULL; status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { @@ -399,9 +373,12 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id return NULL; } + /* it needs to be non blocking for sends */ + set_blocking(socket_get_fd(msg->sock), False); + msg->event.ev = talloc_reference(msg, ev); msg->event.fde = event_add_fd(ev, msg, socket_get_fd(msg->sock), - EVENT_FD_READ, messaging_recv_handler, msg); + EVENT_FD_READ, messaging_handler, msg); talloc_set_destructor(msg, messaging_destructor); @@ -409,5 +386,3 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id return msg; } - - -- cgit From f1ade86d756a242e41d610981b948d03c68fbd4b Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 3 Jun 2005 06:04:34 +0000 Subject: r7211: - use ioctl(FIONREAD) to remove the artificial limit on messaging size - avoid a memcpy (This used to be commit 753839c358f45c02927b137092828f3a79158083) --- source4/lib/messaging/messaging.c | 93 +++++++++++++++++++++------------------ 1 file changed, 51 insertions(+), 42 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 4d2cd9c910..eb526fd391 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -31,9 +31,6 @@ /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -/* maximum message size */ -#define MESSAGING_MAX_SIZE 512 - struct messaging_context { uint32_t server_id; struct socket_context *sock; @@ -63,15 +60,15 @@ struct messaging_rec { struct messaging_context *msg; const char *path; - struct { + struct messaging_header { uint32_t version; uint32_t msg_type; uint32_t from; uint32_t to; uint32_t length; - } header; + } *header; - DATA_BLOB data; + DATA_BLOB packet; }; @@ -106,11 +103,14 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r struct dispatch_fn *d, *next; for (d=msg->dispatch;d;d=next) { next = d->next; - if (d->msg_type == rec->header.msg_type) { - d->fn(msg, d->private, d->msg_type, rec->header.from, &rec->data); + if (d->msg_type == rec->header->msg_type) { + DATA_BLOB data; + data.data = rec->packet.data + sizeof(*rec->header); + data.length = rec->header->length; + d->fn(msg, d->private, d->msg_type, rec->header->from, &data); } } - rec->header.length = 0; + rec->header->length = 0; } @@ -120,24 +120,15 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r static NTSTATUS try_send(struct messaging_rec *rec) { struct messaging_context *msg = rec->msg; - DATA_BLOB blob; size_t nsent; void *priv; NTSTATUS status; - blob = data_blob_talloc(rec, NULL, sizeof(rec->header) + rec->data.length); - NT_STATUS_HAVE_NO_MEMORY(blob.data); - - memcpy(blob.data, &rec->header, sizeof(rec->header)); - memcpy(blob.data + sizeof(rec->header), rec->data.data, rec->data.length); - /* we send with privileges so messages work from any context */ priv = root_privileges(); - status = socket_sendto(msg->sock, &blob, &nsent, 0, rec->path, 0); + status = socket_sendto(msg->sock, &rec->packet, &nsent, 0, rec->path, 0); talloc_free(priv); - data_blob_free(&blob); - return status; } @@ -155,7 +146,7 @@ static void messaging_send_handler(struct messaging_context *msg) } if (!NT_STATUS_IS_OK(status)) { DEBUG(1,("messaging: Lost message from %u to %u of type %u - %s\n", - rec->header.from, rec->header.to, rec->header.msg_type, + rec->header->from, rec->header->to, rec->header->msg_type, nt_errstr(status))); } DLIST_REMOVE(msg->pending, rec); @@ -173,16 +164,31 @@ static void messaging_recv_handler(struct messaging_context *msg) { struct messaging_rec *rec; NTSTATUS status; - uint8_t data[MESSAGING_MAX_SIZE]; + DATA_BLOB packet; size_t msize; + int dsize=0; - status = socket_recv(msg->sock, data, sizeof(data), &msize, 0); + /* see how many bytes are in the next packet */ + if (ioctl(socket_get_fd(msg->sock), FIONREAD, &dsize) != 0) { + DEBUG(0,("FIONREAD failed in messaging - %s\n", strerror(errno))); + return; + } + + packet = data_blob_talloc(msg, NULL, dsize); + if (packet.data == NULL) { + /* assume this is temporary and retry */ + return; + } + + status = socket_recv(msg->sock, packet.data, dsize, &msize, 0); if (!NT_STATUS_IS_OK(status)) { + data_blob_free(&packet); return; } - if (msize < sizeof(rec->header)) { + if (msize < sizeof(*rec->header)) { DEBUG(0,("messaging: bad message of size %d\n", msize)); + data_blob_free(&packet); return; } @@ -191,19 +197,15 @@ static void messaging_recv_handler(struct messaging_context *msg) smb_panic("Unable to allocate messaging_rec"); } + talloc_steal(rec, packet.data); rec->msg = msg; rec->path = msg->path; + rec->header = (struct messaging_header *)packet.data; + rec->packet = packet; - memcpy(&rec->header, data, sizeof(rec->header)); - if (msize != sizeof(rec->header) + rec->header.length) { + if (msize != sizeof(*rec->header) + rec->header->length) { DEBUG(0,("messaging: bad message header size %d should be %d\n", - rec->header.length, msize - sizeof(rec->header))); - talloc_free(rec); - return; - } - - rec->data = data_blob_talloc(rec, data+sizeof(rec->header), rec->header.length); - if (rec->data.data == NULL) { + rec->header->length, msize - sizeof(*rec->header))); talloc_free(rec); return; } @@ -272,22 +274,29 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, { struct messaging_rec *rec; NTSTATUS status; + size_t dlength = data?data->length:0; rec = talloc(msg, struct messaging_rec); if (rec == NULL) { return NT_STATUS_NO_MEMORY; } - rec->msg = msg; - rec->header.version = MESSAGING_VERSION; - rec->header.msg_type = msg_type; - rec->header.from = msg->server_id; - rec->header.to = server; - rec->header.length = data?data->length:0; - if (rec->header.length != 0) { - rec->data = data_blob_talloc(rec, data->data, data->length); - } else { - rec->data = data_blob(NULL, 0); + rec->packet = data_blob_talloc(rec, NULL, sizeof(*rec->header) + dlength); + if (rec->packet.data == NULL) { + talloc_free(rec); + return NT_STATUS_NO_MEMORY; + } + + rec->msg = msg; + rec->header = (struct messaging_header *)rec->packet.data; + rec->header->version = MESSAGING_VERSION; + rec->header->msg_type = msg_type; + rec->header->from = msg->server_id; + rec->header->to = server; + rec->header->length = dlength; + if (dlength != 0) { + memcpy(rec->packet.data + sizeof(*rec->header), + data->data, dlength); } rec->path = messaging_path(rec, server); -- cgit From a8feef8d3647d25b3f5f572139acb1bab361055e Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 3 Jun 2005 13:20:45 +0000 Subject: r7228: use socket_pending() instead of the direct ioctl in the messaging code (This used to be commit ca3c4e961713ffd8952fca328e27196ba2ccc0c9) --- source4/lib/messaging/messaging.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index eb526fd391..936e3b9515 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -166,21 +166,22 @@ static void messaging_recv_handler(struct messaging_context *msg) NTSTATUS status; DATA_BLOB packet; size_t msize; - int dsize=0; /* see how many bytes are in the next packet */ - if (ioctl(socket_get_fd(msg->sock), FIONREAD, &dsize) != 0) { - DEBUG(0,("FIONREAD failed in messaging - %s\n", strerror(errno))); + status = socket_pending(msg->sock, &msize); + if (!NT_STATUS_IS_OK(status)) { + DEBUG(0,("socket_pending failed in messaging - %s\n", + nt_errstr(status))); return; } - packet = data_blob_talloc(msg, NULL, dsize); + packet = data_blob_talloc(msg, NULL, msize); if (packet.data == NULL) { /* assume this is temporary and retry */ return; } - status = socket_recv(msg->sock, packet.data, dsize, &msize, 0); + status = socket_recv(msg->sock, packet.data, msize, &msize, 0); if (!NT_STATUS_IS_OK(status)) { data_blob_free(&packet); return; -- cgit From bf1ffa283caef6a3c98b5cc7f5bc8205c2818b06 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 5 Jun 2005 06:53:07 +0000 Subject: r7294: implemented the irpc messaging system. This is the core of the management system I proposed on samba-technical a couple of days ago. Essentially it is a very lightweight way for any code in Samba to make IDL based rpc calls to anywhere else in the code, without the client or server having to go to the trouble of setting up a full rpc service. It can be used with any of our existing IDL, but I expect it will mostly be used for a new set of Samba specific management calls. The LOCAL-IRPC torture test demonstrates how it can be used by calling the echo_AddOne() call over this transport. (This used to be commit 3d589a09954eb8b318f567e1150b0c27412fb942) --- source4/lib/messaging/messaging.c | 283 +++++++++++++++++++++++++++++++++++++- 1 file changed, 281 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 936e3b9515..b605fa0494 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -27,6 +27,8 @@ #include "messages.h" #include "dlinklist.h" #include "lib/socket/socket.h" +#include "librpc/gen_ndr/ndr_irpc.h" +#include "lib/messaging/irpc.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 @@ -37,6 +39,8 @@ struct messaging_context { const char *path; struct dispatch_fn *dispatch; struct messaging_rec *pending; + struct irpc_list *irpc; + struct idr_context *idr; struct { struct event_context *ev; @@ -72,6 +76,10 @@ struct messaging_rec { }; +static void irpc_handler(struct messaging_context *, void *, + uint32_t, uint32_t, DATA_BLOB *); + + /* A useful function for testing the message system. */ @@ -363,8 +371,10 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id msg->path = messaging_path(msg, server_id); msg->server_id = server_id; - msg->dispatch = NULL; - msg->pending = NULL; + msg->dispatch = NULL; + msg->pending = NULL; + msg->idr = idr_init(msg); + msg->irpc = NULL; status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { @@ -393,6 +403,275 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id talloc_set_destructor(msg, messaging_destructor); messaging_register(msg, NULL, MSG_PING, ping_message); + messaging_register(msg, NULL, MSG_IRPC, irpc_handler); return msg; } + + +/* + a list of registered irpc server functions +*/ +struct irpc_list { + struct irpc_list *next, *prev; + struct GUID uuid; + const struct dcerpc_interface_table *table; + int callnum; + irpc_function_t fn; +}; + + +/* + register a irpc server function +*/ +NTSTATUS irpc_register(struct messaging_context *msg_ctx, + const struct dcerpc_interface_table *table, + int call, irpc_function_t fn) +{ + struct irpc_list *irpc; + + irpc = talloc(msg_ctx, struct irpc_list); + NT_STATUS_HAVE_NO_MEMORY(irpc); + + irpc->table = table; + irpc->callnum = call; + irpc->fn = fn; + GUID_from_string(irpc->table->uuid, &irpc->uuid); + + DLIST_ADD(msg_ctx->irpc, irpc); + + return NT_STATUS_OK; +} + + +/* + handle an incoming irpc reply message +*/ +static void irpc_handler_reply(struct messaging_context *msg_ctx, + struct ndr_pull *ndr, struct irpc_header *header) +{ + struct irpc_request *irpc; + + irpc = idr_find(msg_ctx->idr, header->callid); + if (irpc == NULL) return; + + /* parse the reply data */ + irpc->status = irpc->table->calls[irpc->callnum].ndr_pull(ndr, NDR_OUT, irpc->r); + if (NT_STATUS_IS_OK(irpc->status)) { + irpc->status = header->status; + } + irpc->done = True; + if (irpc->async.fn) { + irpc->async.fn(irpc); + } +} + + +/* + handle an incoming irpc request message +*/ +static void irpc_handler_request(struct messaging_context *msg_ctx, + struct ndr_pull *ndr, struct irpc_header *header, + uint32_t src) +{ + struct irpc_list *i; + void *r; + NTSTATUS status; + struct irpc_message m; + struct ndr_push *push; + DATA_BLOB packet; + + for (i=msg_ctx->irpc; i; i=i->next) { + if (GUID_equal(&i->uuid, &header->uuid) && + i->table->if_version == header->if_version && + i->callnum == header->callnum) { + break; + } + } + + if (i == NULL) { + /* no registered handler for this message */ + return; + } + + /* allocate space for the structure */ + r = talloc_zero_size(ndr, i->table->calls[header->callnum].struct_size); + if (r == NULL) goto failed; + + /* parse the request data */ + status = i->table->calls[i->callnum].ndr_pull(ndr, NDR_IN, r); + if (!NT_STATUS_IS_OK(status)) goto failed; + + /* make the call */ + m.from = src; + header->status = i->fn(&m, r); + + /* setup the reply */ + push = ndr_push_init_ctx(ndr); + if (push == NULL) goto failed; + + header->flags |= IRPC_FLAG_REPLY; + + /* construct the packet */ + status = ndr_push_irpc_header(push, NDR_SCALARS|NDR_BUFFERS, header); + if (!NT_STATUS_IS_OK(status)) goto failed; + + status = i->table->calls[i->callnum].ndr_push(push, NDR_OUT, r); + if (!NT_STATUS_IS_OK(status)) goto failed; + + /* send the reply message */ + packet = ndr_push_blob(push); + status = messaging_send(msg_ctx, src, MSG_IRPC, &packet); + if (!NT_STATUS_IS_OK(status)) goto failed; + +failed: + /* nothing to clean up */ + return; +} + +/* + handle an incoming irpc message +*/ +static void irpc_handler(struct messaging_context *msg_ctx, void *private, + uint32_t msg_type, uint32_t src, DATA_BLOB *packet) +{ + struct irpc_header header; + struct ndr_pull *ndr; + NTSTATUS status; + + ndr = ndr_pull_init_blob(packet, msg_ctx); + if (ndr == NULL) goto failed; + + status = ndr_pull_irpc_header(ndr, NDR_BUFFERS|NDR_SCALARS, &header); + if (!NT_STATUS_IS_OK(status)) goto failed; + + if (header.flags & IRPC_FLAG_REPLY) { + irpc_handler_reply(msg_ctx, ndr, &header); + } else { + irpc_handler_request(msg_ctx, ndr, &header, src); + } + +failed: + talloc_free(ndr); +} + + +/* + destroy a irpc request +*/ +static int irpc_destructor(void *ptr) +{ + struct irpc_request *irpc = talloc_get_type(ptr, struct irpc_request); + idr_remove(irpc->msg_ctx->idr, irpc->callid); + return 0; +} + +/* + timeout a irpc request +*/ +static void irpc_timeout(struct event_context *ev, struct timed_event *te, + struct timeval t, void *private) +{ + struct irpc_request *irpc = talloc_get_type(private, struct irpc_request); + irpc->status = NT_STATUS_IO_TIMEOUT; + irpc->done = True; + if (irpc->async.fn) { + irpc->async.fn(irpc); + } +} + + +/* + make a irpc call - async send +*/ +struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, + uint32_t server_id, + const struct dcerpc_interface_table *table, + int callnum, void *r) +{ + struct irpc_header header; + struct ndr_push *ndr; + NTSTATUS status; + DATA_BLOB packet; + struct irpc_request *irpc; + + irpc = talloc(msg_ctx, struct irpc_request); + if (irpc == NULL) goto failed; + + irpc->msg_ctx = msg_ctx; + irpc->table = table; + irpc->callnum = callnum; + irpc->callid = idr_get_new(msg_ctx->idr, irpc, UINT16_MAX); + if (irpc->callid == -1) goto failed; + irpc->r = r; + irpc->done = False; + irpc->async.fn = NULL; + + talloc_set_destructor(irpc, irpc_destructor); + + /* setup the header */ + status = GUID_from_string(table->uuid, &header.uuid); + if (!NT_STATUS_IS_OK(status)) goto failed; + + header.if_version = table->if_version; + header.callid = irpc->callid; + header.callnum = callnum; + header.flags = 0; + header.status = NT_STATUS_OK; + + /* construct the irpc packet */ + ndr = ndr_push_init_ctx(irpc); + if (ndr == NULL) goto failed; + + status = ndr_push_irpc_header(ndr, NDR_SCALARS|NDR_BUFFERS, &header); + if (!NT_STATUS_IS_OK(status)) goto failed; + + status = table->calls[callnum].ndr_push(ndr, NDR_IN, r); + if (!NT_STATUS_IS_OK(status)) goto failed; + + /* and send it */ + packet = ndr_push_blob(ndr); + status = messaging_send(msg_ctx, server_id, MSG_IRPC, &packet); + if (!NT_STATUS_IS_OK(status)) goto failed; + + event_add_timed(msg_ctx->event.ev, irpc, + timeval_current_ofs(IRPC_CALL_TIMEOUT, 0), + irpc_timeout, irpc); + + talloc_free(ndr); + return irpc; + +failed: + talloc_free(irpc); + return NULL; +} + +/* + wait for a irpc reply +*/ +NTSTATUS irpc_call_recv(struct irpc_request *irpc) +{ + NTSTATUS status; + NT_STATUS_HAVE_NO_MEMORY(irpc); + while (!irpc->done) { + if (event_loop_once(irpc->msg_ctx->event.ev) != 0) { + return NT_STATUS_CONNECTION_DISCONNECTED; + } + } + status = irpc->status; + talloc_free(irpc); + return status; +} + +/* + perform a synchronous irpc request +*/ +NTSTATUS irpc_call(struct messaging_context *msg_ctx, + uint32_t server_id, + const struct dcerpc_interface_table *table, + int callnum, void *r) +{ + struct irpc_request *irpc = irpc_call_send(msg_ctx, server_id, + table, callnum, r); + return irpc_call_recv(irpc); +} -- cgit From d934cb71d0bd2d6ad7a2908cc3c3802cb37e922c Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 5 Jun 2005 07:30:44 +0000 Subject: r7295: added an irpc benchmark. It gets about 16k messages/sec on my laptop, compared to about 20k messages/sec for the raw messaging layer. I think that is quite acceptable given the extra functionality. (This used to be commit a05d38d1d91f1f54d3e3794a596b468992594852) --- source4/lib/messaging/messaging.c | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index b605fa0494..be89c97e5b 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -315,7 +315,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, if (msg->pending == NULL) { EVENT_FD_WRITEABLE(msg->event.fde); } - DLIST_ADD(msg->pending, rec); + DLIST_ADD_END(msg->pending, rec, struct messaging_rec *); return NT_STATUS_OK; } @@ -426,20 +426,27 @@ struct irpc_list { */ NTSTATUS irpc_register(struct messaging_context *msg_ctx, const struct dcerpc_interface_table *table, - int call, irpc_function_t fn) + int callnum, irpc_function_t fn) { struct irpc_list *irpc; - irpc = talloc(msg_ctx, struct irpc_list); - NT_STATUS_HAVE_NO_MEMORY(irpc); + /* override an existing handler, if any */ + for (irpc=msg_ctx->irpc; irpc; irpc=irpc->next) { + if (irpc->table == table && irpc->callnum == callnum) { + break; + } + } + if (irpc == NULL) { + irpc = talloc(msg_ctx, struct irpc_list); + NT_STATUS_HAVE_NO_MEMORY(irpc); + DLIST_ADD(msg_ctx->irpc, irpc); + } irpc->table = table; - irpc->callnum = call; + irpc->callnum = callnum; irpc->fn = fn; GUID_from_string(irpc->table->uuid, &irpc->uuid); - DLIST_ADD(msg_ctx->irpc, irpc); - return NT_STATUS_OK; } -- cgit From b4a95b949ee15054cf503029327bde9e75b7d17b Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 5 Jun 2005 07:37:27 +0000 Subject: r7296: avoid two stat() calls per message. This increases the raw message rate from 20k/sec to 55k/sec. The irpc rate goes from 16k/sec to 34k/sec. I should have run strace -T on this a long time ago. (This used to be commit b9281668bb0c971af14df37ec3e979b9d5ef276e) --- source4/lib/messaging/messaging.c | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index be89c97e5b..4c4b6ea8da 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -36,6 +36,7 @@ struct messaging_context { uint32_t server_id; struct socket_context *sock; + const char *base_path; const char *path; struct dispatch_fn *dispatch; struct messaging_rec *pending; @@ -94,13 +95,9 @@ static void ping_message(struct messaging_context *msg, void *private, /* return the path to a messaging socket */ -static char *messaging_path(TALLOC_CTX *mem_ctx, uint32_t server_id) +static char *messaging_path(struct messaging_context *msg, uint32_t server_id) { - char *name = talloc_asprintf(mem_ctx, "messaging/msg.%u", (unsigned)server_id); - char *ret; - ret = smbd_tmp_path(mem_ctx, name); - talloc_free(name); - return ret; + return talloc_asprintf(msg, "%s/msg.%u", msg->base_path, (unsigned)server_id); } /* @@ -308,7 +305,8 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, data->data, dlength); } - rec->path = messaging_path(rec, server); + rec->path = messaging_path(msg, server); + talloc_steal(rec, rec->path); status = try_send(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { @@ -369,7 +367,8 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id mkdir(path, 0700); talloc_free(path); - msg->path = messaging_path(msg, server_id); + msg->base_path = smbd_tmp_path(msg, "messaging"); + msg->path = messaging_path(msg, server_id); msg->server_id = server_id; msg->dispatch = NULL; msg->pending = NULL; -- cgit From 37fdb858b069d862d53edae11dff42a4696c78a4 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 5 Jun 2005 07:44:51 +0000 Subject: r7298: ensure messages are sent in order even when under extreme load. This fixes a IO_TIMEOUT problem in the messaging benchmarks (This used to be commit c8b220b65de00418d19347cf298cc80d86e8accb) --- source4/lib/messaging/messaging.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 4c4b6ea8da..823058b0cf 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -308,7 +308,12 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, rec->path = messaging_path(msg, server); talloc_steal(rec, rec->path); - status = try_send(rec); + if (msg->pending != NULL) { + status = STATUS_MORE_ENTRIES; + } else { + status = try_send(rec); + } + if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { if (msg->pending == NULL) { EVENT_FD_WRITEABLE(msg->event.fde); -- cgit From 0093e1b62cf02d1c3bdc3f18c8c4cc3d0abbf776 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 6 Jun 2005 05:47:14 +0000 Subject: r7320: added support for a private pointer in irpc registered handlers (This used to be commit eec521dffd4ca9efa7f6e31c50cf1ff365aae209) --- source4/lib/messaging/messaging.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 823058b0cf..70eb2e7680 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -422,6 +422,7 @@ struct irpc_list { const struct dcerpc_interface_table *table; int callnum; irpc_function_t fn; + void *private; }; @@ -430,7 +431,7 @@ struct irpc_list { */ NTSTATUS irpc_register(struct messaging_context *msg_ctx, const struct dcerpc_interface_table *table, - int callnum, irpc_function_t fn) + int callnum, irpc_function_t fn, void *private) { struct irpc_list *irpc; @@ -449,6 +450,7 @@ NTSTATUS irpc_register(struct messaging_context *msg_ctx, irpc->table = table; irpc->callnum = callnum; irpc->fn = fn; + irpc->private = private; GUID_from_string(irpc->table->uuid, &irpc->uuid); return NT_STATUS_OK; @@ -514,7 +516,8 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, if (!NT_STATUS_IS_OK(status)) goto failed; /* make the call */ - m.from = src; + m.from = src; + m.private = i->private; header->status = i->fn(&m, r); /* setup the reply */ -- cgit From 66a52992ff6a9f2f926249ac428d6fad72303637 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Thu, 23 Jun 2005 22:30:26 +0000 Subject: r7850: Support mkdir() with just one parameter. Patch from Steven Edwards . I've moved the Win32-specific tests to win32.m4 so it does not make any of the POSIX configure stuff more complicated. (This used to be commit bf85fdd01552f75b745fdf3159a7a87cd6521ed2) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 70eb2e7680..6209c36554 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -22,6 +22,7 @@ #include "includes.h" #include "lib/events/events.h" +#include "system/dir.h" #include "system/filesys.h" #include "system/time.h" #include "messages.h" -- cgit From 4a8c3a9e623e40a3fd927c4ed5fa3a8fa41f3012 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Fri, 1 Jul 2005 08:14:21 +0000 Subject: r8042: give better error message metze (This used to be commit 70118e9529aaf7af9129df7cb3a6749598b17568) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6209c36554..7cf488c7d0 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -393,7 +393,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id status = socket_listen(msg->sock, msg->path, 0, 50, 0); if (!NT_STATUS_IS_OK(status)) { - DEBUG(0,("Unable to setup messaging listener for '%s'\n", msg->path)); + DEBUG(0,("Unable to setup messaging listener for '%s':%s\n", msg->path, nt_errstr(status))); talloc_free(msg); return NULL; } -- cgit From c6881d1e650fd284a366af76f5a214a5de05cc0c Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 10 Jul 2005 01:08:10 +0000 Subject: r8272: added the hooks for adding a name to a messaging context, so we will be able to send a message to the "ldap_server" task without having to know its task ID. (This used to be commit 8f69867867857e0c9a9246c2dec9612ccc234724) --- source4/lib/messaging/messaging.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 7cf488c7d0..9bf5071e90 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -690,3 +690,13 @@ NTSTATUS irpc_call(struct messaging_context *msg_ctx, table, callnum, r); return irpc_call_recv(irpc); } + +/* + add a string name that this irpc server can be called on +*/ +NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) +{ + return NT_STATUS_OK; +} + + -- cgit From 144b88b3a0ac91ef8263cdb8cc044d04c2d65f62 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 10 Jul 2005 04:54:21 +0000 Subject: r8277: filled in the code for finding irpc server ids by name, storing the names in a tdb (This used to be commit b603a52f27bf90e71d605440d44267dcd94c6939) --- source4/lib/messaging/messaging.c | 123 +++++++++++++++++++++++++++++++++++++- 1 file changed, 122 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 9bf5071e90..8345c79c77 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -30,6 +30,9 @@ #include "lib/socket/socket.h" #include "librpc/gen_ndr/ndr_irpc.h" #include "lib/messaging/irpc.h" +#include "db_wrap.h" +#include "lib/tdb/include/tdb.h" +#include "lib/tdb/include/tdbutil.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 @@ -43,6 +46,7 @@ struct messaging_context { struct messaging_rec *pending; struct irpc_list *irpc; struct idr_context *idr; + const char **names; struct { struct event_context *ev; @@ -350,6 +354,9 @@ static int messaging_destructor(void *ptr) { struct messaging_context *msg = ptr; unlink(msg->path); + while (msg->names && msg->names[0]) { + irpc_remove_name(msg, msg->names[0]); + } return 0; } @@ -380,6 +387,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id msg->pending = NULL; msg->idr = idr_init(msg); msg->irpc = NULL; + msg->names = NULL; status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { @@ -691,12 +699,125 @@ NTSTATUS irpc_call(struct messaging_context *msg_ctx, return irpc_call_recv(irpc); } +/* + open the naming database +*/ +static struct tdb_wrap *irpc_namedb_open(struct messaging_context *msg_ctx) +{ + struct tdb_wrap *t; + char *path = talloc_asprintf(msg_ctx, "%s/names.tdb", msg_ctx->base_path); + if (path == NULL) { + return NULL; + } + t = tdb_wrap_open(msg_ctx, path, 0, 0, O_RDWR|O_CREAT, 0660); + talloc_free(path); + return t; +} + + /* add a string name that this irpc server can be called on */ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) { - return NT_STATUS_OK; + struct tdb_wrap *t; + TDB_DATA rec; + int count; + NTSTATUS status = NT_STATUS_OK; + + t = irpc_namedb_open(msg_ctx); + NT_STATUS_HAVE_NO_MEMORY(t); + + rec = tdb_fetch_bystring(t->tdb, name); + count = rec.dsize / sizeof(uint32_t); + rec.dptr = (char *)realloc_p(rec.dptr, uint32_t, count+1); + rec.dsize += sizeof(uint32_t); + if (rec.dptr == NULL) { + talloc_free(t); + return NT_STATUS_NO_MEMORY; + } + ((uint32_t *)rec.dptr)[count] = msg_ctx->server_id; + if (tdb_store_bystring(t->tdb, name, rec, 0) != 0) { + status = NT_STATUS_INTERNAL_ERROR; + } + free(rec.dptr); + talloc_free(t); + + msg_ctx->names = str_list_add(msg_ctx->names, name); + talloc_steal(msg_ctx, msg_ctx->names); + + return status; } +/* + return a list of server ids for a server name +*/ +uint32_t *irpc_servers_byname(struct messaging_context *msg_ctx, const char *name) +{ + struct tdb_wrap *t; + TDB_DATA rec; + int count, i; + uint32_t *ret; + + t = irpc_namedb_open(msg_ctx); + if (t == NULL) { + return NULL; + } + rec = tdb_fetch_bystring(t->tdb, name); + if (rec.dptr == NULL) { + talloc_free(t); + return NULL; + } + count = rec.dsize / sizeof(uint32_t); + ret = talloc_array(msg_ctx, uint32_t, count); + if (ret == NULL) { + talloc_free(t); + return NULL; + } + for (i=0;inames, name); + + t = irpc_namedb_open(msg_ctx); + if (t == NULL) { + return; + } + + rec = tdb_fetch_bystring(t->tdb, name); + count = rec.dsize / sizeof(uint32_t); + if (count == 0) { + talloc_free(t); + return; + } + ids = (uint32_t *)rec.dptr; + for (i=0;iserver_id) { + if (i < count-1) { + memmove(ids+i, ids+i+1, count-(i+1)); + } + rec.dsize -= sizeof(uint32_t); + break; + } + } + tdb_store_bystring(t->tdb, name, rec, 0); + free(rec.dptr); + talloc_free(t); +} -- cgit From d084d6d24109ae615af89776519e7ebd722e9a4c Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 10 Jul 2005 06:17:39 +0000 Subject: r8279: make sure we hold a lock when manipulating the irpc names db (This used to be commit 9c408d5d7cb82e910ffb5963ddc78e5759513385) --- source4/lib/messaging/messaging.c | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 8345c79c77..5afcf91bab 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -728,11 +728,16 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) t = irpc_namedb_open(msg_ctx); NT_STATUS_HAVE_NO_MEMORY(t); + if (tdb_lock_bystring(t->tdb, name) != 0) { + talloc_free(t); + return NT_STATUS_LOCK_NOT_GRANTED; + } rec = tdb_fetch_bystring(t->tdb, name); count = rec.dsize / sizeof(uint32_t); rec.dptr = (char *)realloc_p(rec.dptr, uint32_t, count+1); rec.dsize += sizeof(uint32_t); if (rec.dptr == NULL) { + tdb_unlock_bystring(t->tdb, name); talloc_free(t); return NT_STATUS_NO_MEMORY; } @@ -741,6 +746,7 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) status = NT_STATUS_INTERNAL_ERROR; } free(rec.dptr); + tdb_unlock_bystring(t->tdb, name); talloc_free(t); msg_ctx->names = str_list_add(msg_ctx->names, name); @@ -764,21 +770,29 @@ uint32_t *irpc_servers_byname(struct messaging_context *msg_ctx, const char *nam return NULL; } + if (tdb_lock_bystring(t->tdb, name) != 0) { + talloc_free(t); + return NULL; + } rec = tdb_fetch_bystring(t->tdb, name); if (rec.dptr == NULL) { + tdb_unlock_bystring(t->tdb, name); talloc_free(t); return NULL; } count = rec.dsize / sizeof(uint32_t); - ret = talloc_array(msg_ctx, uint32_t, count); + ret = talloc_array(msg_ctx, uint32_t, count+1); if (ret == NULL) { + tdb_unlock_bystring(t->tdb, name); talloc_free(t); return NULL; } for (i=0;itdb, name); talloc_free(t); return ret; @@ -801,9 +815,14 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) return; } + if (tdb_lock_bystring(t->tdb, name) != 0) { + talloc_free(t); + return; + } rec = tdb_fetch_bystring(t->tdb, name); count = rec.dsize / sizeof(uint32_t); if (count == 0) { + tdb_unlock_bystring(t->tdb, name); talloc_free(t); return; } @@ -819,5 +838,6 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) } tdb_store_bystring(t->tdb, name, rec, 0); free(rec.dptr); + tdb_unlock_bystring(t->tdb, name); talloc_free(t); } -- cgit From 056096c30ba73cbc5304c99af5d5a08d89111aab Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 10 Jul 2005 08:35:18 +0000 Subject: r8284: - fixed some uninitialised variables in the irpc code - added code to send multiple irpc calls in parallel, to all servers that have registered the given name, with output going in io.results[i]. This allows you to make rpc calls to multiple servers at once, which is needed for clients like smbstatus (This used to be commit 061e20e509d95ffe16d7dd6fba7db39fc7a165ed) --- source4/lib/messaging/messaging.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 5afcf91bab..a29f14f065 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -375,6 +375,10 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id return NULL; } + if (ev == NULL) { + ev = event_context_init(msg); + } + /* create the messaging directory if needed */ path = smbd_tmp_path(msg, "messaging"); mkdir(path, 0700); @@ -483,6 +487,7 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, irpc->status = header->status; } irpc->done = True; + talloc_steal(irpc, ndr); if (irpc->async.fn) { irpc->async.fn(irpc); } @@ -572,7 +577,9 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, irpc_handler_reply(msg_ctx, ndr, &header); } else { irpc_handler_request(msg_ctx, ndr, &header, src); + talloc_free(ndr); } + return; failed: talloc_free(ndr); @@ -674,16 +681,13 @@ failed: */ NTSTATUS irpc_call_recv(struct irpc_request *irpc) { - NTSTATUS status; NT_STATUS_HAVE_NO_MEMORY(irpc); while (!irpc->done) { if (event_loop_once(irpc->msg_ctx->event.ev) != 0) { return NT_STATUS_CONNECTION_DISCONNECTED; } } - status = irpc->status; - talloc_free(irpc); - return status; + return irpc->status; } /* -- cgit From e835621799647ee70630b389fb53d15b15d68355 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 17 Jul 2005 09:20:52 +0000 Subject: r8520: fixed a pile of warnings from the build farm gcc -Wall output on S390. This is an attempt to avoid the panic we're seeing in the automatic builds. The main fixes are: - assumptions that sizeof(size_t) == sizeof(int), mostly in printf formats - use of NULL format statements to perform dn searches. - assumption that sizeof() returns an int (This used to be commit a58ea6b3854973b694d2b1e22323ed7eb00e3a3f) --- source4/lib/messaging/messaging.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index a29f14f065..4f1589a9ba 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -93,7 +93,8 @@ static void ping_message(struct messaging_context *msg, void *private, uint32_t msg_type, uint32_t src, DATA_BLOB *data) { DEBUG(1,("INFO: Received PING message from server %u [%.*s]\n", - (uint_t)src, data->length, data->data?(const char *)data->data:"")); + (uint_t)src, (int)data->length, + data->data?(const char *)data->data:"")); messaging_send(msg, src, MSG_PONG, data); } @@ -198,7 +199,7 @@ static void messaging_recv_handler(struct messaging_context *msg) } if (msize < sizeof(*rec->header)) { - DEBUG(0,("messaging: bad message of size %d\n", msize)); + DEBUG(0,("messaging: bad message of size %d\n", (int)msize)); data_blob_free(&packet); return; } @@ -216,7 +217,7 @@ static void messaging_recv_handler(struct messaging_context *msg) if (msize != sizeof(*rec->header) + rec->header->length) { DEBUG(0,("messaging: bad message header size %d should be %d\n", - rec->header->length, msize - sizeof(*rec->header))); + rec->header->length, (int)(msize - sizeof(*rec->header)))); talloc_free(rec); return; } -- cgit From 7ee2babcfe2ffb956a9013a2364c038021b77ae3 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 19 Jul 2005 09:28:13 +0000 Subject: r8587: - fixed ref allocation in irpc replies - make every irpc server support the irpc_uptime() call (This used to be commit eee90448268b9f673cc43076ad87529aa80d17ae) --- source4/lib/messaging/messaging.c | 32 ++++++++++++++++++++++++-------- 1 file changed, 24 insertions(+), 8 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 4f1589a9ba..1a2485d700 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -47,6 +47,7 @@ struct messaging_context { struct irpc_list *irpc; struct idr_context *idr; const char **names; + struct timeval start_time; struct { struct event_context *ev; @@ -98,6 +99,17 @@ static void ping_message(struct messaging_context *msg, void *private, messaging_send(msg, src, MSG_PONG, data); } +/* + return uptime of messaging server via irpc +*/ +static NTSTATUS irpc_uptime(struct irpc_message *msg, + struct irpc_uptime *r) +{ + struct messaging_context *ctx = talloc_get_type(msg->private, struct messaging_context); + *r->out.start_time = timeval_to_nttime(&ctx->start_time); + return NT_STATUS_OK; +} + /* return the path to a messaging socket */ @@ -385,14 +397,15 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id mkdir(path, 0700); talloc_free(path); - msg->base_path = smbd_tmp_path(msg, "messaging"); - msg->path = messaging_path(msg, server_id); - msg->server_id = server_id; - msg->dispatch = NULL; - msg->pending = NULL; - msg->idr = idr_init(msg); - msg->irpc = NULL; - msg->names = NULL; + msg->base_path = smbd_tmp_path(msg, "messaging"); + msg->path = messaging_path(msg, server_id); + msg->server_id = server_id; + msg->dispatch = NULL; + msg->pending = NULL; + msg->idr = idr_init(msg); + msg->irpc = NULL; + msg->names = NULL; + msg->start_time = timeval_current(); status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { @@ -422,6 +435,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id messaging_register(msg, NULL, MSG_PING, ping_message); messaging_register(msg, NULL, MSG_IRPC, irpc_handler); + IRPC_REGISTER(msg, irpc, IRPC_UPTIME, irpc_uptime, msg); return msg; } @@ -571,6 +585,8 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, ndr = ndr_pull_init_blob(packet, msg_ctx); if (ndr == NULL) goto failed; + ndr->flags |= LIBNDR_FLAG_REF_ALLOC; + status = ndr_pull_irpc_header(ndr, NDR_BUFFERS|NDR_SCALARS, &header); if (!NT_STATUS_IS_OK(status)) goto failed; -- cgit From ba759b4c86efbf386bc20c1a10ff1996715af132 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 28 Jul 2005 04:09:11 +0000 Subject: r8819: fixed a memory leak in irpc_call() (This used to be commit 25b7524ce5029eadd48c3046297ca6bd3260b013) --- source4/lib/messaging/messaging.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 1a2485d700..911d439de1 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -717,7 +717,9 @@ NTSTATUS irpc_call(struct messaging_context *msg_ctx, { struct irpc_request *irpc = irpc_call_send(msg_ctx, server_id, table, callnum, r); - return irpc_call_recv(irpc); + NTSTATUS status = irpc_call_recv(irpc); + talloc_free(irpc); + return status; } /* -- cgit From fc585709402e6840a5dd16c9a3fb22792ddacf3e Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Mon, 1 Aug 2005 17:33:43 +0000 Subject: r8887: fixed the irpc error that caused ia64 to fail the LOCAL-IRPC test (This used to be commit ce9a262d379b946717d0d4be4731c837e6f7373d) --- source4/lib/messaging/messaging.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 911d439de1..6cabb4c63b 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -500,9 +500,11 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, irpc->status = irpc->table->calls[irpc->callnum].ndr_pull(ndr, NDR_OUT, irpc->r); if (NT_STATUS_IS_OK(irpc->status)) { irpc->status = header->status; + talloc_steal(irpc->mem_ctx, ndr); + } else { + talloc_steal(irpc, ndr); } irpc->done = True; - talloc_steal(irpc, ndr); if (irpc->async.fn) { irpc->async.fn(irpc); } @@ -634,7 +636,7 @@ static void irpc_timeout(struct event_context *ev, struct timed_event *te, struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, uint32_t server_id, const struct dcerpc_interface_table *table, - int callnum, void *r) + int callnum, void *r, TALLOC_CTX *ctx) { struct irpc_header header; struct ndr_push *ndr; @@ -653,6 +655,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, irpc->r = r; irpc->done = False; irpc->async.fn = NULL; + irpc->mem_ctx = ctx; talloc_set_destructor(irpc, irpc_destructor); @@ -713,10 +716,11 @@ NTSTATUS irpc_call_recv(struct irpc_request *irpc) NTSTATUS irpc_call(struct messaging_context *msg_ctx, uint32_t server_id, const struct dcerpc_interface_table *table, - int callnum, void *r) + int callnum, void *r, + TALLOC_CTX *mem_ctx) { struct irpc_request *irpc = irpc_call_send(msg_ctx, server_id, - table, callnum, r); + table, callnum, r, mem_ctx); NTSTATUS status = irpc_call_recv(irpc); talloc_free(irpc); return status; -- cgit From 87f71eb8ad90cdf9ed7d3cd79d6211908a7d2d92 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 25 Sep 2005 13:01:26 +0000 Subject: r10489: added the ability for irpc server to defer replies instead of replying immediately. They set m->defer_reply = True; (This used to be commit 3dcd800a5d3340d0f4855f9f08e73896ad8c3d83) --- source4/lib/messaging/messaging.c | 125 +++++++++++++++++++++++--------------- 1 file changed, 76 insertions(+), 49 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6cabb4c63b..9fcfd58972 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -488,21 +488,20 @@ NTSTATUS irpc_register(struct messaging_context *msg_ctx, /* handle an incoming irpc reply message */ -static void irpc_handler_reply(struct messaging_context *msg_ctx, - struct ndr_pull *ndr, struct irpc_header *header) +static void irpc_handler_reply(struct messaging_context *msg_ctx, struct irpc_message *m) { struct irpc_request *irpc; - irpc = idr_find(msg_ctx->idr, header->callid); + irpc = idr_find(msg_ctx->idr, m->header.callid); if (irpc == NULL) return; /* parse the reply data */ - irpc->status = irpc->table->calls[irpc->callnum].ndr_pull(ndr, NDR_OUT, irpc->r); + irpc->status = irpc->table->calls[irpc->callnum].ndr_pull(m->ndr, NDR_OUT, irpc->r); if (NT_STATUS_IS_OK(irpc->status)) { - irpc->status = header->status; - talloc_steal(irpc->mem_ctx, ndr); + irpc->status = m->header.status; + talloc_steal(irpc->mem_ctx, m); } else { - talloc_steal(irpc, ndr); + talloc_steal(irpc, m); } irpc->done = True; if (irpc->async.fn) { @@ -510,68 +509,93 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, } } +/* + send a irpc reply +*/ +NTSTATUS irpc_send_reply(struct irpc_message *m) +{ + struct ndr_push *push; + NTSTATUS status; + DATA_BLOB packet; + + /* setup the reply */ + push = ndr_push_init_ctx(m->ndr); + if (push == NULL) { + status = NT_STATUS_NO_MEMORY; + goto failed; + } + + m->header.flags |= IRPC_FLAG_REPLY; + + /* construct the packet */ + status = ndr_push_irpc_header(push, NDR_SCALARS|NDR_BUFFERS, &m->header); + if (!NT_STATUS_IS_OK(status)) goto failed; + + status = m->irpc->table->calls[m->irpc->callnum].ndr_push(push, NDR_OUT, m->data); + if (!NT_STATUS_IS_OK(status)) goto failed; + + /* send the reply message */ + packet = ndr_push_blob(push); + status = messaging_send(m->msg_ctx, m->from, MSG_IRPC, &packet); + if (!NT_STATUS_IS_OK(status)) goto failed; + +failed: + talloc_free(m); + return status; +} /* handle an incoming irpc request message */ static void irpc_handler_request(struct messaging_context *msg_ctx, - struct ndr_pull *ndr, struct irpc_header *header, - uint32_t src) + struct irpc_message *m) { struct irpc_list *i; void *r; NTSTATUS status; - struct irpc_message m; - struct ndr_push *push; - DATA_BLOB packet; for (i=msg_ctx->irpc; i; i=i->next) { - if (GUID_equal(&i->uuid, &header->uuid) && - i->table->if_version == header->if_version && - i->callnum == header->callnum) { + if (GUID_equal(&i->uuid, &m->header.uuid) && + i->table->if_version == m->header.if_version && + i->callnum == m->header.callnum) { break; } } if (i == NULL) { /* no registered handler for this message */ + talloc_free(m); return; } /* allocate space for the structure */ - r = talloc_zero_size(ndr, i->table->calls[header->callnum].struct_size); + r = talloc_zero_size(m->ndr, i->table->calls[m->header.callnum].struct_size); if (r == NULL) goto failed; /* parse the request data */ - status = i->table->calls[i->callnum].ndr_pull(ndr, NDR_IN, r); + status = i->table->calls[i->callnum].ndr_pull(m->ndr, NDR_IN, r); if (!NT_STATUS_IS_OK(status)) goto failed; /* make the call */ - m.from = src; - m.private = i->private; - header->status = i->fn(&m, r); + m->private = i->private; + m->defer_reply = False; + m->msg_ctx = msg_ctx; + m->irpc = i; + m->data = r; - /* setup the reply */ - push = ndr_push_init_ctx(ndr); - if (push == NULL) goto failed; - - header->flags |= IRPC_FLAG_REPLY; + m->header.status = i->fn(m, r); - /* construct the packet */ - status = ndr_push_irpc_header(push, NDR_SCALARS|NDR_BUFFERS, header); - if (!NT_STATUS_IS_OK(status)) goto failed; - - status = i->table->calls[i->callnum].ndr_push(push, NDR_OUT, r); - if (!NT_STATUS_IS_OK(status)) goto failed; + if (m->defer_reply) { + /* the server function has asked to defer the reply to later */ + talloc_steal(msg_ctx, m); + return; + } - /* send the reply message */ - packet = ndr_push_blob(push); - status = messaging_send(msg_ctx, src, MSG_IRPC, &packet); - if (!NT_STATUS_IS_OK(status)) goto failed; + irpc_send_reply(m); + return; failed: - /* nothing to clean up */ - return; + talloc_free(m); } /* @@ -580,28 +604,31 @@ failed: static void irpc_handler(struct messaging_context *msg_ctx, void *private, uint32_t msg_type, uint32_t src, DATA_BLOB *packet) { - struct irpc_header header; - struct ndr_pull *ndr; + struct irpc_message *m; NTSTATUS status; - ndr = ndr_pull_init_blob(packet, msg_ctx); - if (ndr == NULL) goto failed; + m = talloc(msg_ctx, struct irpc_message); + if (m == NULL) goto failed; + + m->from = src; - ndr->flags |= LIBNDR_FLAG_REF_ALLOC; + m->ndr = ndr_pull_init_blob(packet, m); + if (m->ndr == NULL) goto failed; - status = ndr_pull_irpc_header(ndr, NDR_BUFFERS|NDR_SCALARS, &header); + m->ndr->flags |= LIBNDR_FLAG_REF_ALLOC; + + status = ndr_pull_irpc_header(m->ndr, NDR_BUFFERS|NDR_SCALARS, &m->header); if (!NT_STATUS_IS_OK(status)) goto failed; - if (header.flags & IRPC_FLAG_REPLY) { - irpc_handler_reply(msg_ctx, ndr, &header); + if (m->header.flags & IRPC_FLAG_REPLY) { + irpc_handler_reply(msg_ctx, m); } else { - irpc_handler_request(msg_ctx, ndr, &header, src); - talloc_free(ndr); + irpc_handler_request(msg_ctx, m); } return; failed: - talloc_free(ndr); + talloc_free(m); } @@ -761,7 +788,7 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) } rec = tdb_fetch_bystring(t->tdb, name); count = rec.dsize / sizeof(uint32_t); - rec.dptr = (char *)realloc_p(rec.dptr, uint32_t, count+1); + rec.dptr = (unsigned char *)realloc_p(rec.dptr, uint32_t, count+1); rec.dsize += sizeof(uint32_t); if (rec.dptr == NULL) { tdb_unlock_bystring(t->tdb, name); -- cgit From 06085e7bc09e46c74fbe050633203fab619d501c Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 25 Sep 2005 13:17:03 +0000 Subject: r10490: - allow deferred irpc replies to set the status - add an example of deferred reply for echodata in LOCAL-IRPC (This used to be commit 858a757a6d0a614b8f13bfb6217034e8a8b69554) --- source4/lib/messaging/messaging.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 9fcfd58972..c3d3ba7899 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -512,12 +512,13 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, struct irpc_me /* send a irpc reply */ -NTSTATUS irpc_send_reply(struct irpc_message *m) +NTSTATUS irpc_send_reply(struct irpc_message *m, NTSTATUS status) { struct ndr_push *push; - NTSTATUS status; DATA_BLOB packet; + m->header.status = status; + /* setup the reply */ push = ndr_push_init_ctx(m->ndr); if (push == NULL) { @@ -582,6 +583,7 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, m->msg_ctx = msg_ctx; m->irpc = i; m->data = r; + m->ev = msg_ctx->event.ev; m->header.status = i->fn(m, r); @@ -591,7 +593,7 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, return; } - irpc_send_reply(m); + irpc_send_reply(m, m->header.status); return; failed: -- cgit From 150848248a8b97c58a6f09c83a8784e61f858170 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Fri, 2 Dec 2005 07:30:34 +0000 Subject: r12014: free the irpc_request structure with the irpc_call_recv functions, to match all other _recv functions we have metze (This used to be commit bd4f85ab5f60c7430ac88062fa6a9f6cffa9596f) --- source4/lib/messaging/messaging.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index c3d3ba7899..06eed05404 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -730,13 +730,18 @@ failed: */ NTSTATUS irpc_call_recv(struct irpc_request *irpc) { + NTSTATUS status; + NT_STATUS_HAVE_NO_MEMORY(irpc); + while (!irpc->done) { if (event_loop_once(irpc->msg_ctx->event.ev) != 0) { return NT_STATUS_CONNECTION_DISCONNECTED; - } + } } - return irpc->status; + status = irpc->status; + talloc_free(irpc); + return status; } /* @@ -750,9 +755,7 @@ NTSTATUS irpc_call(struct messaging_context *msg_ctx, { struct irpc_request *irpc = irpc_call_send(msg_ctx, server_id, table, callnum, r, mem_ctx); - NTSTATUS status = irpc_call_recv(irpc); - talloc_free(irpc); - return status; + return irpc_call_recv(irpc); } /* -- cgit From d658de65d32e6746ac51aeb4da7aa74b3da40c2b Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Tue, 27 Dec 2005 16:22:35 +0000 Subject: r12512: Use GUID structs in API functions everywhere rather then converting back and forth between GUID structs and strings in several places. (This used to be commit 3564e2f967ef72d6301b4f7e9a311cebcded4d75) --- source4/lib/messaging/messaging.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 06eed05404..e3ad8e7e25 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -479,7 +479,7 @@ NTSTATUS irpc_register(struct messaging_context *msg_ctx, irpc->callnum = callnum; irpc->fn = fn; irpc->private = private; - GUID_from_string(irpc->table->uuid, &irpc->uuid); + irpc->uuid = irpc->table->uuid; return NT_STATUS_OK; } @@ -689,8 +689,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, talloc_set_destructor(irpc, irpc_destructor); /* setup the header */ - status = GUID_from_string(table->uuid, &header.uuid); - if (!NT_STATUS_IS_OK(status)) goto failed; + header.uuid = table->uuid; header.if_version = table->if_version; header.callid = irpc->callid; -- cgit From d4de4c2d210d2e8c9b5aedf70695594809ad6a0b Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Fri, 30 Dec 2005 13:16:54 +0000 Subject: r12608: Remove some unused #include lines. (This used to be commit 70e7449318aa0e9d2639c76730a7d1683b2f4981) --- source4/lib/messaging/messaging.c | 3 --- 1 file changed, 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index e3ad8e7e25..c7cce9c133 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -22,16 +22,13 @@ #include "includes.h" #include "lib/events/events.h" -#include "system/dir.h" #include "system/filesys.h" -#include "system/time.h" #include "messages.h" #include "dlinklist.h" #include "lib/socket/socket.h" #include "librpc/gen_ndr/ndr_irpc.h" #include "lib/messaging/irpc.h" #include "db_wrap.h" -#include "lib/tdb/include/tdb.h" #include "lib/tdb/include/tdbutil.h" /* change the message version with any incompatible changes in the protocol */ -- cgit From 78c50015bb8bd5a1d831a6e7ec796b3367c73145 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Tue, 3 Jan 2006 15:40:05 +0000 Subject: r12694: Move some headers to the directory of the subsystem they belong to. (This used to be commit c722f665c90103f3ed57621c460e32ad33e7a8a3) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index c7cce9c133..ea345ff881 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -23,7 +23,7 @@ #include "includes.h" #include "lib/events/events.h" #include "system/filesys.h" -#include "messages.h" +#include "messaging/messaging.h" #include "dlinklist.h" #include "lib/socket/socket.h" #include "librpc/gen_ndr/ndr_irpc.h" -- cgit From dc0dde70d8a310f2897a22643d8da2b53bfd5910 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sun, 8 Jan 2006 22:58:59 +0000 Subject: r12783: add a comment about matching more than 1 handler per message (andrew thought this might be a bug) (This used to be commit e1cd3f4b89e10c9a42f5939377df0eafb8c184a4) --- source4/lib/messaging/messaging.c | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index ea345ff881..aa2fe0b150 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -117,6 +117,10 @@ static char *messaging_path(struct messaging_context *msg, uint32_t server_id) /* dispatch a fully received message + + note that this deliberately can match more than one message handler + per message. That allows a single messasging context to register + (for example) a debug handler for more than one piece of code */ static void messaging_dispatch(struct messaging_context *msg, struct messaging_rec *rec) { -- cgit From f55ea8bb3dca868e21663cd90eaea7a35cd7886c Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Mon, 9 Jan 2006 22:12:53 +0000 Subject: r12804: This patch reworks the Samba4 sockets layer to use a socket_address structure that is more generic than just 'IP/port'. It now passes make test, and has been reviewed and updated by metze. (Thankyou *very* much). This passes 'make test' as well as kerberos use (not currently in the testsuite). The original purpose of this patch was to have Samba able to pass a socket address stucture from the BSD layer into the kerberos routines and back again. It also removes nbt_peer_addr, which was being used for a similar purpose. It is a large change, but worthwhile I feel. Andrew Bartlett (This used to be commit 88198c4881d8620a37086f80e4da5a5b71c5bbb2) --- source4/lib/messaging/messaging.c | 30 ++++++++++++++++++++++++------ 1 file changed, 24 insertions(+), 6 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index aa2fe0b150..df15928235 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -147,10 +147,20 @@ static NTSTATUS try_send(struct messaging_rec *rec) size_t nsent; void *priv; NTSTATUS status; + struct socket_address *path; + + /* rec->path is the path of the *other* socket, where we want + * this to end up */ + path = socket_address_from_strings(msg, msg->sock->backend_name, + rec->path, 0); + if (!path) { + return NT_STATUS_NO_MEMORY; + } /* we send with privileges so messages work from any context */ priv = root_privileges(); - status = socket_sendto(msg->sock, &rec->packet, &nsent, 0, rec->path, 0); + status = socket_sendto(msg->sock, &rec->packet, &nsent, 0, path); + talloc_free(path); talloc_free(priv); return status; @@ -382,7 +392,8 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id { struct messaging_context *msg; NTSTATUS status; - char *path; + struct socket_address *path; + char *dir; msg = talloc(mem_ctx, struct messaging_context); if (msg == NULL) { @@ -394,9 +405,9 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id } /* create the messaging directory if needed */ - path = smbd_tmp_path(msg, "messaging"); - mkdir(path, 0700); - talloc_free(path); + dir = smbd_tmp_path(msg, "messaging"); + mkdir(dir, 0700); + talloc_free(dir); msg->base_path = smbd_tmp_path(msg, "messaging"); msg->path = messaging_path(msg, server_id); @@ -418,7 +429,14 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id deleted) on exit */ talloc_steal(msg, msg->sock); - status = socket_listen(msg->sock, msg->path, 0, 50, 0); + path = socket_address_from_strings(msg, msg->sock->backend_name, + msg->path, 0); + if (!path) { + talloc_free(msg); + return NULL; + } + + status = socket_listen(msg->sock, path, 50, 0); if (!NT_STATUS_IS_OK(status)) { DEBUG(0,("Unable to setup messaging listener for '%s':%s\n", msg->path, nt_errstr(status))); talloc_free(msg); -- cgit From 34aa19cafe8d19412123d92b735e8afda5e0a87d Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Fri, 3 Feb 2006 22:30:30 +0000 Subject: r13317: Create a new function messaging_client_init() which can be used when we don't have a server messaging context. We should replace the datagram messages with stream sockets in this case, so we don't have to create a unique socket. Andrew Bartlett (This used to be commit fd974fb64792f8f6c532b01d2a2e012be18eef7e) --- source4/lib/messaging/messaging.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index df15928235..6f00ba30ed 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -459,7 +459,14 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id return msg; } - +/* + A hack, for the short term until we get 'client only' messaging in place +*/ +struct messaging_context *messaging_client_init(TALLOC_CTX *mem_ctx, + struct event_context *ev) +{ + return messaging_init(mem_ctx, random() % 0x10000000, ev); +} /* a list of registered irpc server functions */ -- cgit From f8fdbc967c774a1d62f87a534e4990d83ecc6b67 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Tue, 7 Mar 2006 14:34:32 +0000 Subject: r13944: Yet another round of splitups. (This used to be commit f87debeb12cebd734b47314554ab671c9e06237e) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6f00ba30ed..8432eadf5e 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -30,6 +30,7 @@ #include "lib/messaging/irpc.h" #include "db_wrap.h" #include "lib/tdb/include/tdbutil.h" +#include "util/unix_privs.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From 35349a58df5b69446607fbd742a05f57f3515319 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Sat, 18 Mar 2006 15:42:57 +0000 Subject: r14542: Remove librpc, libndr and libnbt from includes.h (This used to be commit 51b4270513752d2eafbe77f9de598de16ef84a1f) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 8432eadf5e..5680060ee4 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -31,6 +31,7 @@ #include "db_wrap.h" #include "lib/tdb/include/tdbutil.h" #include "util/unix_privs.h" +#include "librpc/rpc/dcerpc.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From c84cfc0ecc46ef05dc7997a128ba9486516cb112 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Sun, 19 Mar 2006 02:23:52 +0000 Subject: r14554: Write out header dependencies. This means all C files affected will be rebuilt when a header file is changed. It also means parallel builds work now. It will take a minute or so to generate all the dependency information, but there should be no need to rebuild that information later on, unless a file changes. This behaviour is only enabled when building in developer mode (--enable-developer) and requires a GNU make (or compatible). In all other cases, the file 'static_deps.mk' is included, which contains some basic hardcoded dependency information. (This used to be commit eb435386f015ce1d89eb6f7e7837622ebd9e1951) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 5680060ee4..ff5127e79a 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -30,7 +30,7 @@ #include "lib/messaging/irpc.h" #include "db_wrap.h" #include "lib/tdb/include/tdbutil.h" -#include "util/unix_privs.h" +#include "lib/util/unix_privs.h" #include "librpc/rpc/dcerpc.h" /* change the message version with any incompatible changes in the protocol */ -- cgit From 42da534d66c14c60844568246a2862da7b49f1d5 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Sun, 26 Mar 2006 00:59:17 +0000 Subject: r14735: Use dcerpc_syntax_id rather then seperate GUID + if_version everywhere (This used to be commit a316b33057f3ec8532677980e093cd327d33f257) --- source4/lib/messaging/messaging.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index ff5127e79a..f3296c6938 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -507,7 +507,7 @@ NTSTATUS irpc_register(struct messaging_context *msg_ctx, irpc->callnum = callnum; irpc->fn = fn; irpc->private = private; - irpc->uuid = irpc->table->uuid; + irpc->uuid = irpc->table->syntax_id.uuid; return NT_STATUS_OK; } @@ -585,7 +585,7 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, for (i=msg_ctx->irpc; i; i=i->next) { if (GUID_equal(&i->uuid, &m->header.uuid) && - i->table->if_version == m->header.if_version && + i->table->syntax_id.if_version == m->header.if_version && i->callnum == m->header.callnum) { break; } @@ -717,9 +717,9 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, talloc_set_destructor(irpc, irpc_destructor); /* setup the header */ - header.uuid = table->uuid; + header.uuid = table->syntax_id.uuid; - header.if_version = table->if_version; + header.if_version = table->syntax_id.if_version; header.callid = irpc->callid; header.callnum = callnum; header.flags = 0; -- cgit From c8610144f73a6cbc26c58f57a527f7cbcb44b265 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Wed, 12 Apr 2006 06:08:24 +0000 Subject: r15049: for really efficient oplock handling with thousands of open files we will need a separate messaging endpoint per open file. To make this efficient extend the messaging layer to have a new registration function for temporary message types that maps via an idtree. I have updated the LOCAL-MESSAGING test to use the new function. (This used to be commit 4b976851d8b7ccd2c40010be095cef7fecf9e722) --- source4/lib/messaging/messaging.c | 132 +++++++++++++++++++++++++++++--------- 1 file changed, 100 insertions(+), 32 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index f3296c6938..f8f998f5cf 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -41,7 +41,9 @@ struct messaging_context { struct socket_context *sock; const char *base_path; const char *path; - struct dispatch_fn *dispatch; + struct dispatch_fn **dispatch; + uint32_t num_types; + struct idr_context *dispatch_tree; struct messaging_rec *pending; struct irpc_list *irpc; struct idr_context *idr; @@ -54,14 +56,13 @@ struct messaging_context { } event; }; -/* we have a linked list of dispatch handlers that this messaging - server can deal with */ +/* we have a linked list of dispatch handlers for each msg_type that + this messaging server can deal with */ struct dispatch_fn { struct dispatch_fn *next, *prev; uint32_t msg_type; void *private; - void (*fn)(struct messaging_context *msg, void *private, - uint32_t msg_type, uint32_t server_id, DATA_BLOB *data); + msg_callback_t fn; }; /* an individual message */ @@ -127,14 +128,22 @@ static char *messaging_path(struct messaging_context *msg, uint32_t server_id) static void messaging_dispatch(struct messaging_context *msg, struct messaging_rec *rec) { struct dispatch_fn *d, *next; - for (d=msg->dispatch;d;d=next) { + + /* temporary IDs use an idtree, the rest use a array of pointers */ + if (rec->header->msg_type >= MSG_TMP_BASE) { + d = idr_find(msg->dispatch_tree, rec->header->msg_type); + } else if (rec->header->msg_type < msg->num_types) { + d = msg->dispatch[rec->header->msg_type]; + } else { + d = NULL; + } + + for (; d; d = next) { + DATA_BLOB data; next = d->next; - if (d->msg_type == rec->header->msg_type) { - DATA_BLOB data; - data.data = rec->packet.data + sizeof(*rec->header); - data.length = rec->header->length; - d->fn(msg, d->private, d->msg_type, rec->header->from, &data); - } + data.data = rec->packet.data + sizeof(*rec->header); + data.length = rec->header->length; + d->fn(msg, d->private, d->msg_type, rec->header->from, &data); } rec->header->length = 0; } @@ -272,17 +281,61 @@ static void messaging_handler(struct event_context *ev, struct fd_event *fde, /* Register a dispatch function for a particular message type. */ -void messaging_register(struct messaging_context *msg, void *private, - uint32_t msg_type, - void (*fn)(struct messaging_context *, void *, uint32_t, uint32_t, DATA_BLOB *)) +NTSTATUS messaging_register(struct messaging_context *msg, void *private, + uint32_t msg_type, msg_callback_t fn) { struct dispatch_fn *d; - d = talloc(msg, struct dispatch_fn); + /* possibly expand dispatch array */ + if (msg_type >= msg->num_types) { + struct dispatch_fn **dp; + int i; + dp = talloc_realloc(msg, msg->dispatch, struct dispatch_fn *, msg_type+1); + NT_STATUS_HAVE_NO_MEMORY(dp); + msg->dispatch = dp; + for (i=msg->num_types;i<=msg_type;i++) { + msg->dispatch[i] = NULL; + } + msg->num_types = msg_type+1; + } + + + d = talloc(msg->dispatch, struct dispatch_fn); + NT_STATUS_HAVE_NO_MEMORY(d); d->msg_type = msg_type; d->private = private; d->fn = fn; - DLIST_ADD(msg->dispatch, d); + + DLIST_ADD(msg->dispatch[msg_type], d); + + return NT_STATUS_OK; +} + +/* + register a temporary message handler. The msg_type is allocated + above MSG_TMP_BASE +*/ +NTSTATUS messaging_register_tmp(struct messaging_context *msg, void *private, + msg_callback_t fn, uint32_t *msg_type) +{ + struct dispatch_fn *d; + int id; + + d = talloc_zero(msg->dispatch, struct dispatch_fn); + NT_STATUS_HAVE_NO_MEMORY(d); + d->private = private; + d->fn = fn; + + id = idr_get_new_above(msg->dispatch_tree, d, MSG_TMP_BASE, UINT16_MAX); + if (id == -1) { + talloc_free(d); + return NT_STATUS_TOO_MANY_CONTEXT_IDS; + } + + d->msg_type = (uint32_t)id; + (*msg_type) = d->msg_type; + + return NT_STATUS_OK; } /* @@ -290,16 +343,34 @@ void messaging_register(struct messaging_context *msg, void *private, */ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void *private) { - struct dispatch_fn *d, *next; + struct dispatch_fn *d, *list, *next; - for (d = msg->dispatch; d; d = next) { + if (msg_type >= msg->num_types) { + list = idr_find(msg->dispatch_tree, msg_type); + } else { + list = msg->dispatch[msg_type]; + } + + if (list == NULL) { + return; + } + + for (d = list; d; d = next) { next = d->next; - if (d->msg_type == msg_type && - d->private == private) { - DLIST_REMOVE(msg->dispatch, d); + if (d->private == private) { + DLIST_REMOVE(list, d); talloc_free(d); } } + + /* the list base possibly changed */ + if (list == NULL) { + if (msg_type >= msg->num_types) { + idr_remove(msg->dispatch_tree, msg_type); + } else { + msg->dispatch[msg_type] = NULL; + } + } } @@ -397,7 +468,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id struct socket_address *path; char *dir; - msg = talloc(mem_ctx, struct messaging_context); + msg = talloc_zero(mem_ctx, struct messaging_context); if (msg == NULL) { return NULL; } @@ -411,15 +482,12 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id mkdir(dir, 0700); talloc_free(dir); - msg->base_path = smbd_tmp_path(msg, "messaging"); - msg->path = messaging_path(msg, server_id); - msg->server_id = server_id; - msg->dispatch = NULL; - msg->pending = NULL; - msg->idr = idr_init(msg); - msg->irpc = NULL; - msg->names = NULL; - msg->start_time = timeval_current(); + msg->base_path = smbd_tmp_path(msg, "messaging"); + msg->path = messaging_path(msg, server_id); + msg->server_id = server_id; + msg->idr = idr_init(msg); + msg->dispatch_tree = idr_init(msg); + msg->start_time = timeval_current(); status = socket_create("unix", SOCKET_TYPE_DGRAM, &msg->sock, 0); if (!NT_STATUS_IS_OK(status)) { -- cgit From 35cb099357028535ae8b968465edfcaa7ad1a1fd Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Wed, 12 Apr 2006 09:38:07 +0000 Subject: r15050: fixed a double free in the new messaging code. (This used to be commit ee7869bb3c901fb91efedc8208aa56df927987c5) --- source4/lib/messaging/messaging.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index f8f998f5cf..c02a79ab8d 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -364,12 +364,12 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void } /* the list base possibly changed */ - if (list == NULL) { - if (msg_type >= msg->num_types) { + if (msg_type >= msg->num_types) { + if (list == NULL) { idr_remove(msg->dispatch_tree, msg_type); - } else { - msg->dispatch[msg_type] = NULL; } + } else { + msg->dispatch[msg_type] = list; } } -- cgit From 4f972f5c3363863d24cc07a348993d9ed8a9c830 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Wed, 12 Apr 2006 15:52:17 +0000 Subject: r15055: this was my version for the crash bug in the messaging code... it also makes the function a bit shorter and clearer, as the tmp msg_types only have one handler and not a list metze (This used to be commit 7e709fd04dc4fb083bd8b01b3f0fa88b932aa9b7) --- source4/lib/messaging/messaging.c | 29 ++++++++--------------------- 1 file changed, 8 insertions(+), 21 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index c02a79ab8d..62170b64f3 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -299,8 +299,7 @@ NTSTATUS messaging_register(struct messaging_context *msg, void *private, msg->num_types = msg_type+1; } - - d = talloc(msg->dispatch, struct dispatch_fn); + d = talloc_zero(msg->dispatch, struct dispatch_fn); NT_STATUS_HAVE_NO_MEMORY(d); d->msg_type = msg_type; d->private = private; @@ -343,37 +342,25 @@ NTSTATUS messaging_register_tmp(struct messaging_context *msg, void *private, */ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void *private) { - struct dispatch_fn *d, *list, *next; + struct dispatch_fn *d, *next; if (msg_type >= msg->num_types) { - list = idr_find(msg->dispatch_tree, msg_type); - } else { - list = msg->dispatch[msg_type]; - } - - if (list == NULL) { + d = idr_find(msg->dispatch_tree, msg_type); + if (!d) return; + idr_remove(msg->dispatch_tree, msg_type); + talloc_free(d); return; } - for (d = list; d; d = next) { + for (d = msg->dispatch[msg_type]; d; d = next) { next = d->next; if (d->private == private) { - DLIST_REMOVE(list, d); + DLIST_REMOVE(msg->dispatch[msg_type], d); talloc_free(d); } - } - - /* the list base possibly changed */ - if (msg_type >= msg->num_types) { - if (list == NULL) { - idr_remove(msg->dispatch_tree, msg_type); - } - } else { - msg->dispatch[msg_type] = list; } } - /* Send a message to a particular server */ -- cgit From c2cc10c7869221c7f43cbbb151feb4c4db173cb9 Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Sun, 30 Apr 2006 05:58:31 +0000 Subject: r15356: Remove unused 'flags' argument from socket_send() and friends. This is in preperation for making TLS a socket library. Andrew Bartlett (This used to be commit a312812b92f5ac7e6bd2c4af725dbbbc900d4452) --- source4/lib/messaging/messaging.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 62170b64f3..bf06d68a33 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -170,7 +170,7 @@ static NTSTATUS try_send(struct messaging_rec *rec) /* we send with privileges so messages work from any context */ priv = root_privileges(); - status = socket_sendto(msg->sock, &rec->packet, &nsent, 0, path); + status = socket_sendto(msg->sock, &rec->packet, &nsent, path); talloc_free(path); talloc_free(priv); @@ -226,7 +226,7 @@ static void messaging_recv_handler(struct messaging_context *msg) return; } - status = socket_recv(msg->sock, packet.data, msize, &msize, 0); + status = socket_recv(msg->sock, packet.data, msize, &msize); if (!NT_STATUS_IS_OK(status)) { data_blob_free(&packet); return; -- cgit From 971d30bb201f5c3faff5f575d26882eb79f7955a Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Wed, 24 May 2006 07:34:11 +0000 Subject: r15854: more talloc_set_destructor() typesafe fixes (This used to be commit 61c6100617589ac6df4f527877241464cacbf8b3) --- source4/lib/messaging/messaging.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index bf06d68a33..6bd331c247 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -434,9 +434,8 @@ NTSTATUS messaging_send_ptr(struct messaging_context *msg, uint32_t server, /* destroy the messaging context */ -static int messaging_destructor(void *ptr) +static int messaging_destructor(struct messaging_context *msg) { - struct messaging_context *msg = ptr; unlink(msg->path); while (msg->names && msg->names[0]) { irpc_remove_name(msg, msg->names[0]); @@ -720,9 +719,8 @@ failed: /* destroy a irpc request */ -static int irpc_destructor(void *ptr) +static int irpc_destructor(struct irpc_request *irpc) { - struct irpc_request *irpc = talloc_get_type(ptr, struct irpc_request); idr_remove(irpc->msg_ctx->idr, irpc->callid); return 0; } -- cgit From 0329d755a7611ba3897fc1ee9bdce410cc33d7f8 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Wed, 30 Aug 2006 11:29:34 +0000 Subject: r17930: Merge noinclude branch: * Move dlinklist.h, smb.h to subsystem-specific directories * Clean up ads.h and move what is left of it to dsdb/ (only place where it's used) (This used to be commit f7afa1cb77f3cfa7020b57de12e6003db7cfcc42) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6bd331c247..00b33017d8 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -24,7 +24,7 @@ #include "lib/events/events.h" #include "system/filesys.h" #include "messaging/messaging.h" -#include "dlinklist.h" +#include "lib/util/dlinklist.h" #include "lib/socket/socket.h" #include "librpc/gen_ndr/ndr_irpc.h" #include "lib/messaging/irpc.h" -- cgit From af870da6194b47c6cd09445c1e03832d00e951bb Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 20 Oct 2006 23:32:23 +0000 Subject: r19428: moved tdbutil.c from lib/tdb/common/ to lib/util/util_tdb.c tdbutil.c is Samba specific, so should not be part of the generic tdb library (This used to be commit 979dd24f5e44605fc1603b690913b8c31be7478f) --- source4/lib/messaging/messaging.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 00b33017d8..09e04fda9b 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -29,9 +29,10 @@ #include "librpc/gen_ndr/ndr_irpc.h" #include "lib/messaging/irpc.h" #include "db_wrap.h" -#include "lib/tdb/include/tdbutil.h" #include "lib/util/unix_privs.h" #include "librpc/rpc/dcerpc.h" +#include "lib/tdb/include/tdb.h" +#include "lib/util/util_tdb.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From 1cd4339b9a2786aa26691ca4f02fa93ab0958b88 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Wed, 10 Jan 2007 10:52:09 +0000 Subject: r20646: first preparations for cluster enablement. This changes " uint32_t server_id to struct server_id server_id; which allows a server ID to have an node number. The node number will be zero in non-clustered case. This is the most basic hook needed for clustering, and ctdb. (This used to be commit 2365abaa991d57d68c6ebe9be608e01c907102eb) --- source4/lib/messaging/messaging.c | 75 ++++++++++++++++++++++----------------- 1 file changed, 42 insertions(+), 33 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 09e04fda9b..691db2b961 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -33,12 +33,14 @@ #include "librpc/rpc/dcerpc.h" #include "lib/tdb/include/tdb.h" #include "lib/util/util_tdb.h" +#include "lib/util/util_tdb.h" +#include "cluster/cluster.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 struct messaging_context { - uint32_t server_id; + struct server_id server_id; struct socket_context *sock; const char *base_path; const char *path; @@ -75,8 +77,8 @@ struct messaging_rec { struct messaging_header { uint32_t version; uint32_t msg_type; - uint32_t from; - uint32_t to; + struct server_id from; + struct server_id to; uint32_t length; } *header; @@ -85,17 +87,17 @@ struct messaging_rec { static void irpc_handler(struct messaging_context *, void *, - uint32_t, uint32_t, DATA_BLOB *); + uint32_t, struct server_id, DATA_BLOB *); /* A useful function for testing the message system. */ static void ping_message(struct messaging_context *msg, void *private, - uint32_t msg_type, uint32_t src, DATA_BLOB *data) + uint32_t msg_type, struct server_id src, DATA_BLOB *data) { - DEBUG(1,("INFO: Received PING message from server %u [%.*s]\n", - (uint_t)src, (int)data->length, + DEBUG(1,("INFO: Received PING message from server %u.%u [%.*s]\n", + (uint_t)src.node, (uint_t)src.id, (int)data->length, data->data?(const char *)data->data:"")); messaging_send(msg, src, MSG_PONG, data); } @@ -114,9 +116,10 @@ static NTSTATUS irpc_uptime(struct irpc_message *msg, /* return the path to a messaging socket */ -static char *messaging_path(struct messaging_context *msg, uint32_t server_id) +static char *messaging_path(struct messaging_context *msg, struct server_id server_id) { - return talloc_asprintf(msg, "%s/msg.%u", msg->base_path, (unsigned)server_id); + return talloc_asprintf(msg, "%s/msg.%u.%u", msg->base_path, + (unsigned)server_id.node, (unsigned)server_id.id); } /* @@ -192,7 +195,7 @@ static void messaging_send_handler(struct messaging_context *msg) } if (!NT_STATUS_IS_OK(status)) { DEBUG(1,("messaging: Lost message from %u to %u of type %u - %s\n", - rec->header->from, rec->header->to, rec->header->msg_type, + rec->header->from.id, rec->header->to.id, rec->header->msg_type, nt_errstr(status))); } DLIST_REMOVE(msg->pending, rec); @@ -365,7 +368,7 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void /* Send a message to a particular server */ -NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, +NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, uint32_t msg_type, DATA_BLOB *data) { struct messaging_rec *rec; @@ -420,7 +423,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, uint32_t server, /* Send a message to a particular server, with the message containing a single pointer */ -NTSTATUS messaging_send_ptr(struct messaging_context *msg, uint32_t server, +NTSTATUS messaging_send_ptr(struct messaging_context *msg, struct server_id server, uint32_t msg_type, void *ptr) { DATA_BLOB blob; @@ -447,7 +450,8 @@ static int messaging_destructor(struct messaging_context *msg) /* create the listening socket and setup the dispatcher */ -struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id, +struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, + struct server_id server_id, struct event_context *ev) { struct messaging_context *msg; @@ -522,7 +526,10 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, uint32_t server_id struct messaging_context *messaging_client_init(TALLOC_CTX *mem_ctx, struct event_context *ev) { - return messaging_init(mem_ctx, random() % 0x10000000, ev); + struct server_id id; + ZERO_STRUCT(id); + id.id = random() % 0x10000000; + return messaging_init(mem_ctx, id, ev); } /* a list of registered irpc server functions @@ -687,7 +694,7 @@ failed: handle an incoming irpc message */ static void irpc_handler(struct messaging_context *msg_ctx, void *private, - uint32_t msg_type, uint32_t src, DATA_BLOB *packet) + uint32_t msg_type, struct server_id src, DATA_BLOB *packet) { struct irpc_message *m; NTSTATUS status; @@ -745,7 +752,7 @@ static void irpc_timeout(struct event_context *ev, struct timed_event *te, make a irpc call - async send */ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, - uint32_t server_id, + struct server_id server_id, const struct dcerpc_interface_table *table, int callnum, void *r, TALLOC_CTX *ctx) { @@ -829,7 +836,7 @@ NTSTATUS irpc_call_recv(struct irpc_request *irpc) perform a synchronous irpc request */ NTSTATUS irpc_call(struct messaging_context *msg_ctx, - uint32_t server_id, + struct server_id server_id, const struct dcerpc_interface_table *table, int callnum, void *r, TALLOC_CTX *mem_ctx) @@ -873,15 +880,15 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) return NT_STATUS_LOCK_NOT_GRANTED; } rec = tdb_fetch_bystring(t->tdb, name); - count = rec.dsize / sizeof(uint32_t); - rec.dptr = (unsigned char *)realloc_p(rec.dptr, uint32_t, count+1); - rec.dsize += sizeof(uint32_t); + count = rec.dsize / sizeof(struct server_id); + rec.dptr = (unsigned char *)realloc_p(rec.dptr, struct server_id, count+1); + rec.dsize += sizeof(struct server_id); if (rec.dptr == NULL) { tdb_unlock_bystring(t->tdb, name); talloc_free(t); return NT_STATUS_NO_MEMORY; } - ((uint32_t *)rec.dptr)[count] = msg_ctx->server_id; + ((struct server_id *)rec.dptr)[count] = msg_ctx->server_id; if (tdb_store_bystring(t->tdb, name, rec, 0) != 0) { status = NT_STATUS_INTERNAL_ERROR; } @@ -898,12 +905,13 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) /* return a list of server ids for a server name */ -uint32_t *irpc_servers_byname(struct messaging_context *msg_ctx, const char *name) +struct server_id *irpc_servers_byname(struct messaging_context *msg_ctx, + const char *name) { struct tdb_wrap *t; TDB_DATA rec; int count, i; - uint32_t *ret; + struct server_id *ret; t = irpc_namedb_open(msg_ctx); if (t == NULL) { @@ -920,17 +928,17 @@ uint32_t *irpc_servers_byname(struct messaging_context *msg_ctx, const char *nam talloc_free(t); return NULL; } - count = rec.dsize / sizeof(uint32_t); - ret = talloc_array(msg_ctx, uint32_t, count+1); + count = rec.dsize / sizeof(struct server_id); + ret = talloc_array(msg_ctx, struct server_id, count+1); if (ret == NULL) { tdb_unlock_bystring(t->tdb, name); talloc_free(t); return NULL; } for (i=0;itdb, name); talloc_free(t); @@ -946,7 +954,7 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) struct tdb_wrap *t; TDB_DATA rec; int count, i; - uint32_t *ids; + struct server_id *ids; str_list_remove(msg_ctx->names, name); @@ -960,19 +968,20 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) return; } rec = tdb_fetch_bystring(t->tdb, name); - count = rec.dsize / sizeof(uint32_t); + count = rec.dsize / sizeof(struct server_id); if (count == 0) { tdb_unlock_bystring(t->tdb, name); talloc_free(t); return; } - ids = (uint32_t *)rec.dptr; + ids = (struct server_id *)rec.dptr; for (i=0;iserver_id) { + if (cluster_id_equal(&ids[i], &msg_ctx->server_id)) { if (i < count-1) { - memmove(ids+i, ids+i+1, count-(i+1)); + memmove(ids+i, ids+i+1, + sizeof(struct server_id) * (count-(i+1))); } - rec.dsize -= sizeof(uint32_t); + rec.dsize -= sizeof(struct server_id); break; } } -- cgit From 07478016d7354274cd53ff2b4ec1dda3f0f439d1 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 8 Feb 2007 00:58:17 +0000 Subject: r21230: added the hooks needed in the cluster layer and the messaging code for handling messages to remote nodes. Implemented dummy functions in the 'local' cluster backend for the messaging hooks, and modified the messaging layer to check if the destination is remote and redirect messages via the cluster layer (This used to be commit 4474552e8fb73efebef32ad8480d7fe9a1e379ef) --- source4/lib/messaging/messaging.c | 44 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 44 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 691db2b961..a043937733 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -152,6 +152,37 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r rec->header->length = 0; } +/* + handler for messages that arrive from other nodes in the cluster +*/ +static void cluster_message_handler(struct messaging_context *msg, struct server_id from, + uint32_t msg_type, DATA_BLOB packet) +{ + struct messaging_rec *rec; + + rec = talloc(msg, struct messaging_rec); + if (rec == NULL) { + smb_panic("Unable to allocate messaging_rec"); + } + + talloc_steal(rec, packet.data); + rec->msg = msg; + rec->path = msg->path; + rec->header = (struct messaging_header *)packet.data; + rec->packet = packet; + + if (packet.length != sizeof(*rec->header) + rec->header->length) { + DEBUG(0,("messaging: bad message header size %d should be %d\n", + rec->header->length, (int)(packet.length - sizeof(*rec->header)))); + talloc_free(rec); + return; + } + + messaging_dispatch(msg, rec); + talloc_free(rec); +} + + /* try to send the message @@ -375,6 +406,12 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, NTSTATUS status; size_t dlength = data?data->length:0; + if (!cluster_node_equal(&msg->server_id, &server)) { + /* the destination is on another node - dispatch via + the cluster layer */ + return cluster_message_send(server, msg_type, data); + } + rec = talloc(msg, struct messaging_rec); if (rec == NULL) { return NT_STATUS_NO_MEMORY; @@ -464,6 +501,13 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, return NULL; } + /* setup a handler for messages from other cluster nodes, if appropriate */ + status = cluster_message_init(msg, server_id, cluster_message_handler); + if (!NT_STATUS_IS_OK(status)) { + talloc_free(msg); + return NULL; + } + if (ev == NULL) { ev = event_context_init(msg); } -- cgit From a2eff69b4b26ba6b3227b4bbe4557bc9b618d400 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Thu, 8 Feb 2007 02:59:58 +0000 Subject: r21233: first version of samba4 messaging using ctdb is working. This means we should now work on a real cluster, and not just a localhost simulator (This used to be commit f05072ad74fb08fd906bc500c5e89930bcc3387f) --- source4/lib/messaging/messaging.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index a043937733..03bfb6b571 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -155,8 +155,7 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r /* handler for messages that arrive from other nodes in the cluster */ -static void cluster_message_handler(struct messaging_context *msg, struct server_id from, - uint32_t msg_type, DATA_BLOB packet) +static void cluster_message_handler(struct messaging_context *msg, DATA_BLOB packet) { struct messaging_rec *rec; @@ -165,7 +164,6 @@ static void cluster_message_handler(struct messaging_context *msg, struct server smb_panic("Unable to allocate messaging_rec"); } - talloc_steal(rec, packet.data); rec->msg = msg; rec->path = msg->path; rec->header = (struct messaging_header *)packet.data; @@ -406,12 +404,6 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, NTSTATUS status; size_t dlength = data?data->length:0; - if (!cluster_node_equal(&msg->server_id, &server)) { - /* the destination is on another node - dispatch via - the cluster layer */ - return cluster_message_send(server, msg_type, data); - } - rec = talloc(msg, struct messaging_rec); if (rec == NULL) { return NT_STATUS_NO_MEMORY; @@ -435,6 +427,14 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, data->data, dlength); } + if (!cluster_node_equal(&msg->server_id, &server)) { + /* the destination is on another node - dispatch via + the cluster layer */ + status = cluster_message_send(server, msg_type, &rec->packet); + talloc_free(rec); + return status; + } + rec->path = messaging_path(msg, server); talloc_steal(rec, rec->path); -- cgit From 8de4c33d8f089f2f47817278f8781f194da898d0 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Fri, 9 Feb 2007 01:52:13 +0000 Subject: r21256: - msg_type is not needed in the cluster messaging API - merge ctdb_get_num_nodes() from bzr tree (This used to be commit 3df7527aedeba7ce2f4a6ca2d3b7167f58c6b68a) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 03bfb6b571..04b340eb5a 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -430,7 +430,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, if (!cluster_node_equal(&msg->server_id, &server)) { /* the destination is on another node - dispatch via the cluster layer */ - status = cluster_message_send(server, msg_type, &rec->packet); + status = cluster_message_send(server, &rec->packet); talloc_free(rec); return status; } -- cgit From de9768764d08e954cd000a04e9646a828917d876 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Tue, 1 May 2007 09:55:36 +0000 Subject: r22629: if irpc gets freed within event_loop_once() we crash... so deferr the freeing metze (This used to be commit 3a30bc0d6137fe2b7440106b35dd0a9175cc8057) --- source4/lib/messaging/messaging.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 04b340eb5a..705fdcc465 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -773,7 +773,14 @@ failed: */ static int irpc_destructor(struct irpc_request *irpc) { - idr_remove(irpc->msg_ctx->idr, irpc->callid); + if (irpc->callid != -1) { + idr_remove(irpc->msg_ctx->idr, irpc->callid); + irpc->callid = -1; + } + + if (irpc->reject_free) { + return -1; + } return 0; } @@ -866,11 +873,16 @@ NTSTATUS irpc_call_recv(struct irpc_request *irpc) NT_STATUS_HAVE_NO_MEMORY(irpc); + irpc->reject_free = true; + while (!irpc->done) { if (event_loop_once(irpc->msg_ctx->event.ev) != 0) { return NT_STATUS_CONNECTION_DISCONNECTED; } } + + irpc->reject_free = false; + status = irpc->status; talloc_free(irpc); return status; -- cgit From 68b531e81784d218b598e4ec403443bbc039ca77 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Mon, 7 May 2007 15:19:53 +0000 Subject: r22748: fix memleaks by passing an mem_ctx to irpc_servers_byname() metze (This used to be commit b54584dfabee77ec7743cab431bda9765057a295) --- source4/lib/messaging/messaging.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 705fdcc465..9b4f4b49c4 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -961,7 +961,8 @@ NTSTATUS irpc_add_name(struct messaging_context *msg_ctx, const char *name) /* return a list of server ids for a server name */ -struct server_id *irpc_servers_byname(struct messaging_context *msg_ctx, +struct server_id *irpc_servers_byname(struct messaging_context *msg_ctx, + TALLOC_CTX *mem_ctx, const char *name) { struct tdb_wrap *t; @@ -985,7 +986,7 @@ struct server_id *irpc_servers_byname(struct messaging_context *msg_ctx, return NULL; } count = rec.dsize / sizeof(struct server_id); - ret = talloc_array(msg_ctx, struct server_id, count+1); + ret = talloc_array(mem_ctx, struct server_id, count+1); if (ret == NULL) { tdb_unlock_bystring(t->tdb, name); talloc_free(t); -- cgit From 145a9dd010498440f5f5367eb1f28b05a9178462 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 22 May 2007 01:02:00 +0000 Subject: r23059: reject_free needs to be initialised (This used to be commit ffb8b493161f6951dabb94f2e9ee4c2f2c11b4e0) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 9b4f4b49c4..58b5e5243e 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -825,6 +825,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, irpc->done = False; irpc->async.fn = NULL; irpc->mem_ctx = ctx; + irpc->reject_free = False; talloc_set_destructor(irpc, irpc_destructor); -- cgit From de8b793050edebb711fe51a898e51bed627992fe Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Sat, 26 May 2007 08:47:27 +0000 Subject: r23153: a first cut at a fix for the dgram flood problem that volker found. Not sure this is the best solution, but it should work. (This used to be commit 80002cd12a64fa2679e48c58906cb9b26ad17e49) --- source4/lib/messaging/messaging.c | 42 ++++++++++++++++++++++++++++++++++++++- 1 file changed, 41 insertions(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 58b5e5243e..ab94a30ace 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -48,11 +48,12 @@ struct messaging_context { uint32_t num_types; struct idr_context *dispatch_tree; struct messaging_rec *pending; + struct messaging_rec *retry_queue; struct irpc_list *irpc; struct idr_context *idr; const char **names; struct timeval start_time; - + struct timed_event *retry_te; struct { struct event_context *ev; struct fd_event *fde; @@ -83,6 +84,7 @@ struct messaging_rec { } *header; DATA_BLOB packet; + uint32_t retries; }; @@ -168,6 +170,7 @@ static void cluster_message_handler(struct messaging_context *msg, DATA_BLOB pac rec->path = msg->path; rec->header = (struct messaging_header *)packet.data; rec->packet = packet; + rec->retries = 0; if (packet.length != sizeof(*rec->header) + rec->header->length) { DEBUG(0,("messaging: bad message header size %d should be %d\n", @@ -210,6 +213,26 @@ static NTSTATUS try_send(struct messaging_rec *rec) return status; } +/* + retry backed off messages +*/ +static void msg_retry_timer(struct event_context *ev, struct timed_event *te, + struct timeval t, void *private) +{ + struct messaging_context *msg = talloc_get_type(private, + struct messaging_context); + msg->retry_te = NULL; + + /* put the messages back on the main queue */ + while (msg->retry_queue) { + struct messaging_rec *rec = msg->retry_queue; + DLIST_REMOVE(msg->retry_queue, rec); + DLIST_ADD_END(msg->pending, rec, struct messaging_rec *); + } + + EVENT_FD_WRITEABLE(msg->event.fde); +} + /* handle a socket write event */ @@ -220,8 +243,23 @@ static void messaging_send_handler(struct messaging_context *msg) NTSTATUS status; status = try_send(rec); if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) { + rec->retries++; + if (rec->retries > 3) { + /* we're getting continuous write errors - + backoff this record */ + DLIST_REMOVE(msg->pending, rec); + DLIST_ADD_END(msg->retry_queue, rec, + struct messaging_rec *); + if (msg->retry_te == NULL) { + msg->retry_te = + event_add_timed(msg->event.ev, msg, + timeval_current_ofs(1, 0), + msg_retry_timer, msg); + } + } break; } + rec->retries = 0; if (!NT_STATUS_IS_OK(status)) { DEBUG(1,("messaging: Lost message from %u to %u of type %u - %s\n", rec->header->from.id, rec->header->to.id, rec->header->msg_type, @@ -281,6 +319,7 @@ static void messaging_recv_handler(struct messaging_context *msg) rec->path = msg->path; rec->header = (struct messaging_header *)packet.data; rec->packet = packet; + rec->retries = 0; if (msize != sizeof(*rec->header) + rec->header->length) { DEBUG(0,("messaging: bad message header size %d should be %d\n", @@ -415,6 +454,7 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, return NT_STATUS_NO_MEMORY; } + rec->retries = 0; rec->msg = msg; rec->header = (struct messaging_header *)rec->packet.data; rec->header->version = MESSAGING_VERSION; -- cgit From 0479a2f1cbae51fcd8dbdc3c148c808421fb4d25 Mon Sep 17 00:00:00 2001 From: Andrew Tridgell Date: Tue, 10 Jul 2007 02:07:03 +0000 Subject: r23792: convert Samba4 to GPLv3 There are still a few tidyups of old FSF addresses to come (in both s3 and s4). More commits soon. (This used to be commit fcf38a38ac691abd0fa51b89dc951a08e89fdafa) --- source4/lib/messaging/messaging.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index ab94a30ace..2a5c941584 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -7,7 +7,7 @@ This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or + the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, @@ -16,8 +16,7 @@ GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + along with this program. If not, see . */ #include "includes.h" -- cgit From b8cdadced4d2a26a63b8bbe397c12df949783ed4 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Sun, 19 Aug 2007 20:46:45 +0000 Subject: r24551: rename dcerpc_interface_table -> ndr_interface_table rename dcerpc_interface_list -> ndr_interface_list and move them to libndr.h metze (This used to be commit 4adbebef5df2f833d2d4bfcdda72a34179d52f5c) --- source4/lib/messaging/messaging.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 2a5c941584..24b5ff408d 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -620,7 +620,7 @@ struct messaging_context *messaging_client_init(TALLOC_CTX *mem_ctx, struct irpc_list { struct irpc_list *next, *prev; struct GUID uuid; - const struct dcerpc_interface_table *table; + const struct ndr_interface_table *table; int callnum; irpc_function_t fn; void *private; @@ -631,7 +631,7 @@ struct irpc_list { register a irpc server function */ NTSTATUS irpc_register(struct messaging_context *msg_ctx, - const struct dcerpc_interface_table *table, + const struct ndr_interface_table *table, int callnum, irpc_function_t fn, void *private) { struct irpc_list *irpc; @@ -843,7 +843,7 @@ static void irpc_timeout(struct event_context *ev, struct timed_event *te, */ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, struct server_id server_id, - const struct dcerpc_interface_table *table, + const struct ndr_interface_table *table, int callnum, void *r, TALLOC_CTX *ctx) { struct irpc_header header; @@ -933,7 +933,7 @@ NTSTATUS irpc_call_recv(struct irpc_request *irpc) */ NTSTATUS irpc_call(struct messaging_context *msg_ctx, struct server_id server_id, - const struct dcerpc_interface_table *table, + const struct ndr_interface_table *table, int callnum, void *r, TALLOC_CTX *mem_ctx) { -- cgit From ed8d04ead92839d54ca67f55a8e2be9723dc6b0d Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Mon, 27 Aug 2007 18:43:18 +0000 Subject: r24717: Some more easy bool conversions, update TODO for registry (This used to be commit fc8771fb6aab815e63334da0159032f7ecd0a931) --- source4/lib/messaging/messaging.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 24b5ff408d..c4c0d0e059 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -588,7 +588,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, } /* it needs to be non blocking for sends */ - set_blocking(socket_get_fd(msg->sock), False); + set_blocking(socket_get_fd(msg->sock), false); msg->event.ev = talloc_reference(msg, ev); msg->event.fde = event_add_fd(ev, msg, socket_get_fd(msg->sock), @@ -676,7 +676,7 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, struct irpc_me } else { talloc_steal(irpc, m); } - irpc->done = True; + irpc->done = true; if (irpc->async.fn) { irpc->async.fn(irpc); } @@ -752,7 +752,7 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, /* make the call */ m->private = i->private; - m->defer_reply = False; + m->defer_reply = false; m->msg_ctx = msg_ctx; m->irpc = i; m->data = r; @@ -831,7 +831,7 @@ static void irpc_timeout(struct event_context *ev, struct timed_event *te, { struct irpc_request *irpc = talloc_get_type(private, struct irpc_request); irpc->status = NT_STATUS_IO_TIMEOUT; - irpc->done = True; + irpc->done = true; if (irpc->async.fn) { irpc->async.fn(irpc); } @@ -861,10 +861,10 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, irpc->callid = idr_get_new(msg_ctx->idr, irpc, UINT16_MAX); if (irpc->callid == -1) goto failed; irpc->r = r; - irpc->done = False; + irpc->done = false; irpc->async.fn = NULL; irpc->mem_ctx = ctx; - irpc->reject_free = False; + irpc->reject_free = false; talloc_set_destructor(irpc, irpc_destructor); -- cgit From cd962355abad90a2161765a7be7d26e63572cab7 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Fri, 7 Sep 2007 15:08:14 +0000 Subject: r25000: Fix some more C++ compatibility warnings. (This used to be commit 08bb1ef643ab906f1645cf6f32763dc73b1884e4) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index c4c0d0e059..4b609b09e9 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -504,7 +504,7 @@ NTSTATUS messaging_send_ptr(struct messaging_context *msg, struct server_id serv { DATA_BLOB blob; - blob.data = (void *)&ptr; + blob.data = (uint8_t *)&ptr; blob.length = sizeof(void *); return messaging_send(msg, server, msg_type, &blob); -- cgit From ffeee68e4b72dd94fee57366bd8d38b8c284c3d4 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Sat, 8 Sep 2007 12:42:09 +0000 Subject: r25026: Move param/param.h out of includes.h (This used to be commit abe8349f9b4387961ff3665d8c589d61cd2edf31) --- source4/lib/messaging/messaging.c | 1 + 1 file changed, 1 insertion(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 4b609b09e9..2ad5e3bed0 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -34,6 +34,7 @@ #include "lib/util/util_tdb.h" #include "lib/util/util_tdb.h" #include "cluster/cluster.h" +#include "param/param.h" /* change the message version with any incompatible changes in the protocol */ #define MESSAGING_VERSION 1 -- cgit From 7e297ecfa4db2c7ab720a63c7764bc0e20f8058c Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Sun, 9 Sep 2007 19:34:30 +0000 Subject: r25047: Fix more warnings. (This used to be commit 69de86d2d2e49439760fbc61901eb87fb7fc5d55) --- source4/lib/messaging/messaging.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 2ad5e3bed0..e398b16d72 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -137,7 +137,8 @@ static void messaging_dispatch(struct messaging_context *msg, struct messaging_r /* temporary IDs use an idtree, the rest use a array of pointers */ if (rec->header->msg_type >= MSG_TMP_BASE) { - d = idr_find(msg->dispatch_tree, rec->header->msg_type); + d = (struct dispatch_fn *)idr_find(msg->dispatch_tree, + rec->header->msg_type); } else if (rec->header->msg_type < msg->num_types) { d = msg->dispatch[rec->header->msg_type]; } else { @@ -417,7 +418,8 @@ void messaging_deregister(struct messaging_context *msg, uint32_t msg_type, void struct dispatch_fn *d, *next; if (msg_type >= msg->num_types) { - d = idr_find(msg->dispatch_tree, msg_type); + d = (struct dispatch_fn *)idr_find(msg->dispatch_tree, + msg_type); if (!d) return; idr_remove(msg->dispatch_tree, msg_type); talloc_free(d); @@ -666,7 +668,7 @@ static void irpc_handler_reply(struct messaging_context *msg_ctx, struct irpc_me { struct irpc_request *irpc; - irpc = idr_find(msg_ctx->idr, m->header.callid); + irpc = (struct irpc_request *)idr_find(msg_ctx->idr, m->header.callid); if (irpc == NULL) return; /* parse the reply data */ -- cgit From 2f3551ca7cee59d4d053cceb87abdf1da1b3a1ad Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Mon, 1 Oct 2007 18:52:55 +0000 Subject: r25446: Merge some changes I made on the way home from SFO: 2007-09-29 More higher-level passing around of lp_ctx. 2007-09-29 Fix warning. 2007-09-29 Pass loadparm contexts on a higher level. 2007-09-29 Avoid using global loadparm context. (This used to be commit 3468952e771ab31f90b6c374ade01c5550810f42) --- source4/lib/messaging/messaging.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index e398b16d72..36cf9aa609 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -530,13 +530,13 @@ static int messaging_destructor(struct messaging_context *msg) create the listening socket and setup the dispatcher */ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, + const char *dir, struct server_id server_id, struct event_context *ev) { struct messaging_context *msg; NTSTATUS status; struct socket_address *path; - char *dir; msg = talloc_zero(mem_ctx, struct messaging_context); if (msg == NULL) { @@ -555,11 +555,9 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, } /* create the messaging directory if needed */ - dir = smbd_tmp_path(msg, "messaging"); mkdir(dir, 0700); - talloc_free(dir); - msg->base_path = smbd_tmp_path(msg, "messaging"); + msg->base_path = talloc_reference(msg, dir); msg->path = messaging_path(msg, server_id); msg->server_id = server_id; msg->idr = idr_init(msg); @@ -610,12 +608,13 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, A hack, for the short term until we get 'client only' messaging in place */ struct messaging_context *messaging_client_init(TALLOC_CTX *mem_ctx, + const char *dir, struct event_context *ev) { struct server_id id; ZERO_STRUCT(id); id.id = random() % 0x10000000; - return messaging_init(mem_ctx, id, ev); + return messaging_init(mem_ctx, dir, id, ev); } /* a list of registered irpc server functions -- cgit From 529763a9aa192a6785ba878aceeb1683c2510913 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Fri, 9 Nov 2007 19:24:51 +0100 Subject: r25920: ndr: change NTSTAUS into enum ndr_err_code (samba4 callers) lib/messaging/ lib/registry/ lib/ldb-samba/ librpc/rpc/ auth/auth_winbind.c auth/gensec/ auth/kerberos/ dsdb/repl/ dsdb/samdb/ dsdb/schema/ torture/ cluster/ctdb/ kdc/ ntvfs/ipc/ torture/rap/ ntvfs/ utils/getntacl.c ntptr/ smb_server/ libcli/wrepl/ wrepl_server/ libcli/cldap/ libcli/dgram/ libcli/ldap/ libcli/raw/ libcli/nbt/ libnet/ winbind/ rpc_server/ metze (This used to be commit 6223c7fddc972687eb577e04fc1c8e0604c35435) --- source4/lib/messaging/messaging.c | 42 ++++++++++++++++++++++++--------------- 1 file changed, 26 insertions(+), 16 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 36cf9aa609..963dfe4f0c 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -666,16 +666,18 @@ NTSTATUS irpc_register(struct messaging_context *msg_ctx, static void irpc_handler_reply(struct messaging_context *msg_ctx, struct irpc_message *m) { struct irpc_request *irpc; + enum ndr_err_code ndr_err; irpc = (struct irpc_request *)idr_find(msg_ctx->idr, m->header.callid); if (irpc == NULL) return; /* parse the reply data */ - irpc->status = irpc->table->calls[irpc->callnum].ndr_pull(m->ndr, NDR_OUT, irpc->r); - if (NT_STATUS_IS_OK(irpc->status)) { + ndr_err = irpc->table->calls[irpc->callnum].ndr_pull(m->ndr, NDR_OUT, irpc->r); + if (NDR_ERR_CODE_IS_SUCCESS(ndr_err)) { irpc->status = m->header.status; talloc_steal(irpc->mem_ctx, m); } else { + irpc->status = ndr_map_error2ntstatus(ndr_err); talloc_steal(irpc, m); } irpc->done = true; @@ -691,6 +693,7 @@ NTSTATUS irpc_send_reply(struct irpc_message *m, NTSTATUS status) { struct ndr_push *push; DATA_BLOB packet; + enum ndr_err_code ndr_err; m->header.status = status; @@ -704,11 +707,17 @@ NTSTATUS irpc_send_reply(struct irpc_message *m, NTSTATUS status) m->header.flags |= IRPC_FLAG_REPLY; /* construct the packet */ - status = ndr_push_irpc_header(push, NDR_SCALARS|NDR_BUFFERS, &m->header); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = ndr_push_irpc_header(push, NDR_SCALARS|NDR_BUFFERS, &m->header); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) { + status = ndr_map_error2ntstatus(ndr_err); + goto failed; + } - status = m->irpc->table->calls[m->irpc->callnum].ndr_push(push, NDR_OUT, m->data); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = m->irpc->table->calls[m->irpc->callnum].ndr_push(push, NDR_OUT, m->data); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) { + status = ndr_map_error2ntstatus(ndr_err); + goto failed; + } /* send the reply message */ packet = ndr_push_blob(push); @@ -728,7 +737,7 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, { struct irpc_list *i; void *r; - NTSTATUS status; + enum ndr_err_code ndr_err; for (i=msg_ctx->irpc; i; i=i->next) { if (GUID_equal(&i->uuid, &m->header.uuid) && @@ -749,8 +758,8 @@ static void irpc_handler_request(struct messaging_context *msg_ctx, if (r == NULL) goto failed; /* parse the request data */ - status = i->table->calls[i->callnum].ndr_pull(m->ndr, NDR_IN, r); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = i->table->calls[i->callnum].ndr_pull(m->ndr, NDR_IN, r); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) goto failed; /* make the call */ m->private = i->private; @@ -782,7 +791,7 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, uint32_t msg_type, struct server_id src, DATA_BLOB *packet) { struct irpc_message *m; - NTSTATUS status; + enum ndr_err_code ndr_err; m = talloc(msg_ctx, struct irpc_message); if (m == NULL) goto failed; @@ -794,8 +803,8 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, m->ndr->flags |= LIBNDR_FLAG_REF_ALLOC; - status = ndr_pull_irpc_header(m->ndr, NDR_BUFFERS|NDR_SCALARS, &m->header); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = ndr_pull_irpc_header(m->ndr, NDR_BUFFERS|NDR_SCALARS, &m->header); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) goto failed; if (m->header.flags & IRPC_FLAG_REPLY) { irpc_handler_reply(msg_ctx, m); @@ -853,6 +862,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, NTSTATUS status; DATA_BLOB packet; struct irpc_request *irpc; + enum ndr_err_code ndr_err; irpc = talloc(msg_ctx, struct irpc_request); if (irpc == NULL) goto failed; @@ -883,11 +893,11 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, ndr = ndr_push_init_ctx(irpc); if (ndr == NULL) goto failed; - status = ndr_push_irpc_header(ndr, NDR_SCALARS|NDR_BUFFERS, &header); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = ndr_push_irpc_header(ndr, NDR_SCALARS|NDR_BUFFERS, &header); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) goto failed; - status = table->calls[callnum].ndr_push(ndr, NDR_IN, r); - if (!NT_STATUS_IS_OK(status)) goto failed; + ndr_err = table->calls[callnum].ndr_push(ndr, NDR_IN, r); + if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) goto failed; /* and send it */ packet = ndr_push_blob(ndr); -- cgit From ca0b72a1fdb7bd965065e833df34662afef0423e Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Fri, 16 Nov 2007 20:12:00 +0100 Subject: r26003: Split up DB_WRAP, as first step in an attempt to sanitize dependencies. (This used to be commit 56dfcb4f2f8e74c9d8b2fe3a0df043781188a555) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 963dfe4f0c..df0bfa32a6 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -27,7 +27,7 @@ #include "lib/socket/socket.h" #include "librpc/gen_ndr/ndr_irpc.h" #include "lib/messaging/irpc.h" -#include "db_wrap.h" +#include "tdb_wrap.h" #include "lib/util/unix_privs.h" #include "librpc/rpc/dcerpc.h" #include "lib/tdb/include/tdb.h" -- cgit From 61873ce94c172c801a4831de5550a8e0fe54c5f5 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Thu, 13 Dec 2007 22:46:23 +0100 Subject: r26431: Require ndr_push creators to specify a iconv_convenience context. (This used to be commit 7352206f4450fdf881b95bda064cedd9d2477e4c) --- source4/lib/messaging/messaging.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index df0bfa32a6..9497e5248c 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -698,7 +698,7 @@ NTSTATUS irpc_send_reply(struct irpc_message *m, NTSTATUS status) m->header.status = status; /* setup the reply */ - push = ndr_push_init_ctx(m->ndr); + push = ndr_push_init_ctx(m->ndr, lp_iconv_convenience(global_loadparm)); if (push == NULL) { status = NT_STATUS_NO_MEMORY; goto failed; @@ -890,7 +890,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, header.status = NT_STATUS_OK; /* construct the irpc packet */ - ndr = ndr_push_init_ctx(irpc); + ndr = ndr_push_init_ctx(irpc, lp_iconv_convenience(global_loadparm)); if (ndr == NULL) goto failed; ndr_err = ndr_push_irpc_header(ndr, NDR_SCALARS|NDR_BUFFERS, &header); -- cgit From d1e716cf4331bf09cfe15a6634bc5887aff81d20 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Thu, 13 Dec 2007 22:46:27 +0100 Subject: r26432: Require ndr_pull users to specify iconv_convenience. (This used to be commit 28b1d36551b75241c1cf9fca5d74f45a6dc884ab) --- source4/lib/messaging/messaging.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 9497e5248c..af742f7374 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -798,7 +798,7 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, m->from = src; - m->ndr = ndr_pull_init_blob(packet, m); + m->ndr = ndr_pull_init_blob(packet, m, lp_iconv_convenience(global_loadparm)); if (m->ndr == NULL) goto failed; m->ndr->flags |= LIBNDR_FLAG_REF_ALLOC; -- cgit From 84b476394713d4f2b84782c59dcc084a25af360f Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Thu, 13 Dec 2007 23:23:25 +0100 Subject: r26441: Remove global_loadparm uses. (This used to be commit 32007c6277efa46341da7741b749a98633d71640) --- source4/lib/messaging/messaging.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index af742f7374..811d5a85bf 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -49,6 +49,7 @@ struct messaging_context { struct idr_context *dispatch_tree; struct messaging_rec *pending; struct messaging_rec *retry_queue; + struct smb_iconv_convenience *iconv_convenience; struct irpc_list *irpc; struct idr_context *idr; const char **names; @@ -532,6 +533,7 @@ static int messaging_destructor(struct messaging_context *msg) struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, const char *dir, struct server_id server_id, + struct smb_iconv_convenience *iconv_convenience, struct event_context *ev) { struct messaging_context *msg; @@ -560,6 +562,7 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, msg->base_path = talloc_reference(msg, dir); msg->path = messaging_path(msg, server_id); msg->server_id = server_id; + msg->iconv_convenience = iconv_convenience; msg->idr = idr_init(msg); msg->dispatch_tree = idr_init(msg); msg->start_time = timeval_current(); @@ -609,12 +612,13 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, */ struct messaging_context *messaging_client_init(TALLOC_CTX *mem_ctx, const char *dir, + struct smb_iconv_convenience *iconv_convenience, struct event_context *ev) { struct server_id id; ZERO_STRUCT(id); id.id = random() % 0x10000000; - return messaging_init(mem_ctx, dir, id, ev); + return messaging_init(mem_ctx, dir, id, iconv_convenience, ev); } /* a list of registered irpc server functions @@ -698,7 +702,7 @@ NTSTATUS irpc_send_reply(struct irpc_message *m, NTSTATUS status) m->header.status = status; /* setup the reply */ - push = ndr_push_init_ctx(m->ndr, lp_iconv_convenience(global_loadparm)); + push = ndr_push_init_ctx(m->ndr, m->msg_ctx->iconv_convenience); if (push == NULL) { status = NT_STATUS_NO_MEMORY; goto failed; @@ -798,7 +802,7 @@ static void irpc_handler(struct messaging_context *msg_ctx, void *private, m->from = src; - m->ndr = ndr_pull_init_blob(packet, m, lp_iconv_convenience(global_loadparm)); + m->ndr = ndr_pull_init_blob(packet, m, msg_ctx->iconv_convenience); if (m->ndr == NULL) goto failed; m->ndr->flags |= LIBNDR_FLAG_REF_ALLOC; @@ -890,7 +894,7 @@ struct irpc_request *irpc_call_send(struct messaging_context *msg_ctx, header.status = NT_STATUS_OK; /* construct the irpc packet */ - ndr = ndr_push_init_ctx(irpc, lp_iconv_convenience(global_loadparm)); + ndr = ndr_push_init_ctx(irpc, msg_ctx->iconv_convenience); if (ndr == NULL) goto failed; ndr_err = ndr_push_irpc_header(ndr, NDR_SCALARS|NDR_BUFFERS, &header); -- cgit From 77f71c1b65358723771354fd9ff1dc418b227ccc Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Mon, 4 Feb 2008 17:51:38 +1100 Subject: Rework cluster_id() to take an additional argument, as we need .. to be unique in a prefork process environment. Andrew Bartlett and David Disseldorp (This used to be commit 931994a7f185bbc98924823e9e8cef1011dd0957) --- source4/lib/messaging/messaging.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 811d5a85bf..9cb10f961c 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -263,8 +263,10 @@ static void messaging_send_handler(struct messaging_context *msg) } rec->retries = 0; if (!NT_STATUS_IS_OK(status)) { - DEBUG(1,("messaging: Lost message from %u to %u of type %u - %s\n", - rec->header->from.id, rec->header->to.id, rec->header->msg_type, + DEBUG(1,("messaging: Lost message from %s to %s of type %u - %s\n", + cluster_id_string(debug_ctx(), rec->header->from), + cluster_id_string(debug_ctx(), rec->header->to), + rec->header->msg_type, nt_errstr(status))); } DLIST_REMOVE(msg->pending, rec); @@ -1051,7 +1053,7 @@ struct server_id *irpc_servers_byname(struct messaging_context *msg_ctx, for (i=0;itdb, name); talloc_free(t); -- cgit From 7e15e09f677f0167dd6b1cec2ccacdd8608e02c7 Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Mon, 4 Feb 2008 23:04:35 +1100 Subject: Fix a few more breakages from our recent changes to the server_id structure. The BASE-TORTURE test found this problem - caused because the messaging path was not unique. If we didn't use a macro for cluster_id_equal(), we could make it opaque, and avoid this... Andrew Bartlett (This used to be commit c3387545c57d2dd4922b4f3806b4552cee8035a3) --- source4/lib/messaging/messaging.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 9cb10f961c..6a879ab962 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -121,8 +121,8 @@ static NTSTATUS irpc_uptime(struct irpc_message *msg, */ static char *messaging_path(struct messaging_context *msg, struct server_id server_id) { - return talloc_asprintf(msg, "%s/msg.%u.%u", msg->base_path, - (unsigned)server_id.node, (unsigned)server_id.id); + return talloc_asprintf(msg, "%s/msg.%s", msg->base_path, + cluster_id_string(msg, server_id)); } /* -- cgit From caea7508102c2ebbe03e9de5d761ac96490c9a06 Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Sat, 15 Mar 2008 12:21:06 +0100 Subject: messaging: fix a valgrind warning on 64bit hosts zero out padding metze (This used to be commit f555b8e4c35f69fdc1fb34427d882580eecad284) --- source4/lib/messaging/messaging.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 6a879ab962..29d6e00247 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -462,6 +462,8 @@ NTSTATUS messaging_send(struct messaging_context *msg, struct server_id server, rec->retries = 0; rec->msg = msg; rec->header = (struct messaging_header *)rec->packet.data; + /* zero padding */ + ZERO_STRUCTP(rec->header); rec->header->version = MESSAGING_VERSION; rec->header->msg_type = msg_type; rec->header->from = msg->server_id; -- cgit From 4e83011f72ba3df387512755a17760b42a7bf2f2 Mon Sep 17 00:00:00 2001 From: Simo Sorce Date: Mon, 21 Apr 2008 17:58:23 -0400 Subject: Remove more event_context_init() uses from function calls within deep down the code. Make sure we pass around the event_context where we need it instead. All test but a few python ones fail. Jelmer promised to fix them. (This used to be commit 3045d391626fba169aa26be52174883e18d323e9) --- source4/lib/messaging/messaging.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 29d6e00247..19284461ee 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -544,6 +544,10 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, NTSTATUS status; struct socket_address *path; + if (ev == NULL) { + return NULL; + } + msg = talloc_zero(mem_ctx, struct messaging_context); if (msg == NULL) { return NULL; @@ -556,10 +560,6 @@ struct messaging_context *messaging_init(TALLOC_CTX *mem_ctx, return NULL; } - if (ev == NULL) { - ev = event_context_init(msg); - } - /* create the messaging directory if needed */ mkdir(dir, 0700); -- cgit From d817b435342956295f0a31b91203d1a63ae12063 Mon Sep 17 00:00:00 2001 From: Volker Lendecke Date: Mon, 19 May 2008 15:53:09 +0200 Subject: Fix a memleak in irpc_remove_name First, even when length==0 tdb_fetch might return something. Second, for some weird reason there might be less data than necessary for a single server id. (This used to be commit 49b04ca7aadf264e500d83bc8d3cb5173a86184e) --- source4/lib/messaging/messaging.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index 19284461ee..e7b654894f 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -1085,8 +1085,14 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) return; } rec = tdb_fetch_bystring(t->tdb, name); + if (rec.dptr == NULL) { + tdb_unlock_bystring(t->tdb, name); + talloc_free(t); + return; + } count = rec.dsize / sizeof(struct server_id); if (count == 0) { + free(rec.dptr); tdb_unlock_bystring(t->tdb, name); talloc_free(t); return; -- cgit From d9a6f04ddd8074c36fc8073ec9bd183438801817 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Mon, 26 May 2008 01:52:35 +0200 Subject: Provide access to server_id from python bindings, add more tests. (This used to be commit adcd87ad07abbf60a0152deae4b975a2401d701b) --- source4/lib/messaging/messaging.c | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'source4/lib/messaging/messaging.c') diff --git a/source4/lib/messaging/messaging.c b/source4/lib/messaging/messaging.c index e7b654894f..4b90e8c4fd 100644 --- a/source4/lib/messaging/messaging.c +++ b/source4/lib/messaging/messaging.c @@ -1113,3 +1113,8 @@ void irpc_remove_name(struct messaging_context *msg_ctx, const char *name) tdb_unlock_bystring(t->tdb, name); talloc_free(t); } + +struct server_id messaging_get_server_id(struct messaging_context *msg_ctx) +{ + return msg_ctx->server_id; +} -- cgit