diff options
Diffstat (limited to 'source4/libcli')
-rw-r--r-- | source4/libcli/cliconnect.c | 4 | ||||
-rw-r--r-- | source4/libcli/finddcs.c | 8 | ||||
-rw-r--r-- | source4/libcli/ldap/ldap_client.c | 5 | ||||
-rw-r--r-- | source4/libcli/raw/clisocket.c | 6 | ||||
-rw-r--r-- | source4/libcli/raw/libcliraw.h | 1 | ||||
-rw-r--r-- | source4/libcli/resolve/bcast.c | 8 | ||||
-rw-r--r-- | source4/libcli/resolve/host.c | 9 | ||||
-rw-r--r-- | source4/libcli/resolve/resolve.c | 110 | ||||
-rw-r--r-- | source4/libcli/resolve/resolve.h | 2 | ||||
-rw-r--r-- | source4/libcli/resolve/testsuite.c | 2 | ||||
-rw-r--r-- | source4/libcli/resolve/wins.c | 26 | ||||
-rw-r--r-- | source4/libcli/smb2/connect.c | 8 | ||||
-rw-r--r-- | source4/libcli/smb2/smb2_calls.h | 1 | ||||
-rw-r--r-- | source4/libcli/smb_composite/connect.c | 3 | ||||
-rw-r--r-- | source4/libcli/wrepl/winsrepl.c | 3 |
15 files changed, 133 insertions, 63 deletions
diff --git a/source4/libcli/cliconnect.c b/source4/libcli/cliconnect.c index b9fd06db1a..d70f592d9d 100644 --- a/source4/libcli/cliconnect.c +++ b/source4/libcli/cliconnect.c @@ -31,12 +31,12 @@ wrapper around smbcli_sock_connect() */ bool smbcli_socket_connect(struct smbcli_state *cli, const char *server, - const char **name_resolve_order, + struct resolve_context *resolve_ctx, int max_xmit, int max_mux) { struct smbcli_socket *sock; - sock = smbcli_sock_connect_byname(server, 0, NULL, name_resolve_order, + sock = smbcli_sock_connect_byname(server, 0, NULL, resolve_ctx, NULL); if (sock == NULL) return false; diff --git a/source4/libcli/finddcs.c b/source4/libcli/finddcs.c index 83bf9837f9..415c84a6bd 100644 --- a/source4/libcli/finddcs.c +++ b/source4/libcli/finddcs.c @@ -65,7 +65,7 @@ struct composite_context *finddcs_send(TALLOC_CTX *mem_ctx, const char *domain_name, int name_type, struct dom_sid *domain_sid, - const char **methods, + struct resolve_context *resolve_ctx, struct event_context *event_ctx, struct messaging_context *msg_ctx) { @@ -96,7 +96,7 @@ struct composite_context *finddcs_send(TALLOC_CTX *mem_ctx, state->msg_ctx = msg_ctx; make_nbt_name(&name, state->domain_name, name_type); - creq = resolve_name_send(&name, event_ctx, methods); + creq = resolve_name_send(resolve_ctx, &name, event_ctx); composite_continue(c, creq, finddcs_name_resolved, state); return c; } @@ -249,7 +249,7 @@ NTSTATUS finddcs(TALLOC_CTX *mem_ctx, const char *my_netbios_name, const char *domain_name, int name_type, struct dom_sid *domain_sid, - const char **methods, + struct resolve_context *resolve_ctx, struct event_context *event_ctx, struct messaging_context *msg_ctx, int *num_dcs, struct nbt_dc_name **dcs) @@ -257,7 +257,7 @@ NTSTATUS finddcs(TALLOC_CTX *mem_ctx, struct composite_context *c = finddcs_send(mem_ctx, my_netbios_name, domain_name, name_type, - domain_sid, methods, + domain_sid, resolve_ctx, event_ctx, msg_ctx); return finddcs_recv(c, mem_ctx, num_dcs, dcs); } diff --git a/source4/libcli/ldap/ldap_client.c b/source4/libcli/ldap/ldap_client.c index 906e9c2574..6b8a7a3f28 100644 --- a/source4/libcli/ldap/ldap_client.c +++ b/source4/libcli/ldap/ldap_client.c @@ -35,6 +35,7 @@ #include "auth/gensec/gensec.h" #include "system/time.h" #include "param/param.h" +#include "libcli/resolve/resolve.h" /** @@ -355,7 +356,7 @@ struct composite_context *ldap_connect_send(struct ldap_connection *conn, } ctx = socket_connect_send(conn->sock, NULL, unix_addr, - 0, lp_name_resolve_order(conn->lp_ctx), conn->event.event_ctx); + 0, lp_resolve_context(conn->lp_ctx), conn->event.event_ctx); ctx->async.fn = ldap_connect_recv_unix_conn; ctx->async.private_data = state; return result; @@ -368,7 +369,7 @@ struct composite_context *ldap_connect_send(struct ldap_connection *conn, } ctx = socket_connect_multi_send(state, conn->host, 1, &conn->port, - lp_name_resolve_order(conn->lp_ctx), conn->event.event_ctx); + lp_resolve_context(conn->lp_ctx), conn->event.event_ctx); if (ctx == NULL) goto failed; ctx->async.fn = ldap_connect_recv_tcp_conn; diff --git a/source4/libcli/raw/clisocket.c b/source4/libcli/raw/clisocket.c index 9b744dcc18..c09104e256 100644 --- a/source4/libcli/raw/clisocket.c +++ b/source4/libcli/raw/clisocket.c @@ -96,7 +96,7 @@ struct composite_context *smbcli_sock_connect_send(TALLOC_CTX *mem_ctx, ctx = socket_connect_multi_send(state, host_addr, state->num_ports, state->ports, - lp_name_resolve_order(global_loadparm), + lp_resolve_context(global_loadparm), state->ctx->event_ctx); if (ctx == NULL) goto failed; ctx->async.fn = smbcli_sock_connect_recv_conn; @@ -200,7 +200,7 @@ resolve a hostname and connect ****************************************************************************/ struct smbcli_socket *smbcli_sock_connect_byname(const char *host, int port, TALLOC_CTX *mem_ctx, - const char **name_resolve_order, + struct resolve_context *resolve_ctx, struct event_context *event_ctx) { int name_type = NBT_NAME_SERVER; @@ -241,7 +241,7 @@ struct smbcli_socket *smbcli_sock_connect_byname(const char *host, int port, make_nbt_name(&nbt_name, host, name_type); - status = resolve_name(&nbt_name, tmp_ctx, &address, event_ctx, name_resolve_order); + status = resolve_name(resolve_ctx, &nbt_name, tmp_ctx, &address, event_ctx); if (!NT_STATUS_IS_OK(status)) { talloc_free(tmp_ctx); return NULL; diff --git a/source4/libcli/raw/libcliraw.h b/source4/libcli/raw/libcliraw.h index a11a9c9e58..6c97e61f04 100644 --- a/source4/libcli/raw/libcliraw.h +++ b/source4/libcli/raw/libcliraw.h @@ -30,6 +30,7 @@ struct smbcli_request; /* forward declare */ struct smbcli_session; /* forward declare */ struct smbcli_transport; /* forward declare */ +struct resolve_context; struct cli_credentials; /* default timeout for all smb requests */ diff --git a/source4/libcli/resolve/bcast.c b/source4/libcli/resolve/bcast.c index ad574e4c9e..5a2c49c5ad 100644 --- a/source4/libcli/resolve/bcast.c +++ b/source4/libcli/resolve/bcast.c @@ -30,6 +30,7 @@ */ struct composite_context *resolve_name_bcast_send(TALLOC_CTX *mem_ctx, struct event_context *event_ctx, + void *userdata, struct nbt_name *name) { int num_interfaces = iface_count(global_loadparm); @@ -74,7 +75,12 @@ NTSTATUS resolve_name_bcast(struct nbt_name *name, TALLOC_CTX *mem_ctx, const char **reply_addr) { - struct composite_context *c = resolve_name_bcast_send(mem_ctx, NULL, name); + struct composite_context *c = resolve_name_bcast_send(mem_ctx, NULL, NULL, name); return resolve_name_bcast_recv(c, mem_ctx, reply_addr); } +bool resolve_context_add_bcast_method(struct resolve_context *ctx) +{ + return resolve_context_add_method(ctx, resolve_name_bcast_send, resolve_name_bcast_recv, + NULL); +} diff --git a/source4/libcli/resolve/host.c b/source4/libcli/resolve/host.c index e98bbc51b2..4b8f3f9553 100644 --- a/source4/libcli/resolve/host.c +++ b/source4/libcli/resolve/host.c @@ -34,6 +34,7 @@ #include "system/filesys.h" #include "libcli/composite/composite.h" #include "librpc/gen_ndr/ndr_nbt.h" +#include "libcli/resolve/resolve.h" struct host_state { struct nbt_name name; @@ -123,6 +124,7 @@ static void pipe_handler(struct event_context *ev, struct fd_event *fde, */ struct composite_context *resolve_name_host_send(TALLOC_CTX *mem_ctx, struct event_context *event_ctx, + void *privdata, struct nbt_name *name) { struct composite_context *c; @@ -213,7 +215,12 @@ NTSTATUS resolve_name_host(struct nbt_name *name, TALLOC_CTX *mem_ctx, const char **reply_addr) { - struct composite_context *c = resolve_name_host_send(mem_ctx, NULL, name); + struct composite_context *c = resolve_name_host_send(mem_ctx, NULL, NULL, name); return resolve_name_host_recv(c, mem_ctx, reply_addr); } +bool resolve_context_add_host_method(struct resolve_context *ctx) +{ + return resolve_context_add_method(ctx, resolve_name_host_send, resolve_name_host_recv, + NULL); +} diff --git a/source4/libcli/resolve/resolve.c b/source4/libcli/resolve/resolve.c index 0f8839a3b7..f0d9c07874 100644 --- a/source4/libcli/resolve/resolve.c +++ b/source4/libcli/resolve/resolve.c @@ -4,6 +4,7 @@ general name resolution interface Copyright (C) Andrew Tridgell 2005 + Copyright (C) Jelmer Vernooij 2007 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 @@ -26,57 +27,67 @@ #include "librpc/gen_ndr/ndr_nbt.h" #include "param/param.h" #include "system/network.h" +#include "util/dlinklist.h" struct resolve_state { + struct resolve_context *ctx; + struct resolve_method *method; struct nbt_name name; - const char **methods; struct composite_context *creq; const char *reply_addr; }; static struct composite_context *setup_next_method(struct composite_context *c); -/* pointers to the resolver backends */ -static const struct resolve_method { - const char *name; - struct composite_context *(*send_fn)(TALLOC_CTX *mem_ctx, struct event_context *, struct nbt_name *); - NTSTATUS (*recv_fn)(struct composite_context *, TALLOC_CTX *, const char **); -} resolve_methods[] = { - { "bcast", resolve_name_bcast_send, resolve_name_bcast_recv }, - { "wins", resolve_name_wins_send, resolve_name_wins_recv }, - { "host", resolve_name_host_send, resolve_name_host_recv } +struct resolve_context { + struct resolve_method { + resolve_name_send_fn send_fn; + resolve_name_recv_fn recv_fn; + void *privdata; + struct resolve_method *prev, *next; + } *methods; }; +/** + * Initialize a resolve context + */ +struct resolve_context *resolve_context_init(TALLOC_CTX *mem_ctx) +{ + return talloc_zero(mem_ctx, struct resolve_context); +} -/* - find a matching backend -*/ -static const struct resolve_method *find_method(const char *name) +/** + * Add a resolve method + */ +bool resolve_context_add_method(struct resolve_context *ctx, resolve_name_send_fn send_fn, + resolve_name_recv_fn recv_fn, void *userdata) { - int i; - if (name == NULL) return NULL; - for (i=0;i<ARRAY_SIZE(resolve_methods);i++) { - if (strcasecmp(name, resolve_methods[i].name) == 0) { - return &resolve_methods[i]; - } - } - return NULL; + struct resolve_method *method = talloc_zero(ctx, struct resolve_method); + + if (method == NULL) + return false; + + method->send_fn = send_fn; + method->recv_fn = recv_fn; + method->privdata = userdata; + DLIST_ADD_END(ctx->methods, method, struct resolve_method *); + return true; } -/* +/** handle completion of one name resolve method */ static void resolve_handler(struct composite_context *creq) { struct composite_context *c = (struct composite_context *)creq->async.private_data; struct resolve_state *state = talloc_get_type(c->private_data, struct resolve_state); - const struct resolve_method *method = find_method(state->methods[0]); + const struct resolve_method *method = state->method; c->status = method->recv_fn(creq, state, &state->reply_addr); if (!NT_STATUS_IS_OK(c->status)) { - state->methods++; + state->method = state->method->next; state->creq = setup_next_method(c); if (state->creq != NULL) { return; @@ -100,13 +111,12 @@ static struct composite_context *setup_next_method(struct composite_context *c) struct composite_context *creq = NULL; do { - const struct resolve_method *method = find_method(state->methods[0]); - if (method) { - creq = method->send_fn(c, c->event_ctx, &state->name); + if (state->method) { + creq = state->method->send_fn(c, c->event_ctx, state->method->privdata, &state->name); } - if (creq == NULL && state->methods[0]) state->methods++; + if (creq == NULL && state->method) state->method = state->method->next; - } while (!creq && state->methods[0]); + } while (!creq && state->method); if (creq) { creq->async.fn = resolve_handler; @@ -119,8 +129,9 @@ static struct composite_context *setup_next_method(struct composite_context *c) /* general name resolution - async send */ -struct composite_context *resolve_name_send(struct nbt_name *name, struct event_context *event_ctx, - const char **methods) +struct composite_context *resolve_name_send(struct resolve_context *ctx, + struct nbt_name *name, + struct event_context *event_ctx) { struct composite_context *c; struct resolve_state *state; @@ -128,7 +139,7 @@ struct composite_context *resolve_name_send(struct nbt_name *name, struct event_ c = composite_create(event_ctx, event_ctx); if (c == NULL) return NULL; - if (methods == NULL) { + if (ctx == NULL) { composite_error(c, NT_STATUS_INVALID_PARAMETER); return c; } @@ -147,8 +158,8 @@ struct composite_context *resolve_name_send(struct nbt_name *name, struct event_ c->status = nbt_name_dup(state, name, &state->name); if (!composite_is_ok(c)) return c; - state->methods = str_list_copy(state, methods); - if (composite_nomem(state->methods, c)) return c; + state->ctx = talloc_reference(state, ctx); + if (composite_nomem(state->ctx, c)) return c; if (is_ipaddress(state->name.name) || strcasecmp(state->name.name, "localhost") == 0) { @@ -159,6 +170,7 @@ struct composite_context *resolve_name_send(struct nbt_name *name, struct event_ return c; } + state->method = ctx->methods; state->creq = setup_next_method(c); if (composite_nomem(state->creq, c)) return c; @@ -187,9 +199,9 @@ NTSTATUS resolve_name_recv(struct composite_context *c, /* general name resolution - sync call */ -NTSTATUS resolve_name(struct nbt_name *name, TALLOC_CTX *mem_ctx, const char **reply_addr, struct event_context *ev, const char **name_resolve_order) +NTSTATUS resolve_name(struct resolve_context *ctx, struct nbt_name *name, TALLOC_CTX *mem_ctx, const char **reply_addr, struct event_context *ev) { - struct composite_context *c = resolve_name_send(name, ev, name_resolve_order); + struct composite_context *c = resolve_name_send(ctx, name, ev); return resolve_name_recv(c, mem_ctx, reply_addr); } @@ -215,3 +227,27 @@ void make_nbt_name_server(struct nbt_name *nbt, const char *name) { make_nbt_name(nbt, name, NBT_NAME_SERVER); } + +struct resolve_context *lp_resolve_context(struct loadparm_context *lp_ctx) +{ + const char **methods = lp_name_resolve_order(lp_ctx); + int i; + struct resolve_context *ret = resolve_context_init(lp_ctx); + + if (ret == NULL) + return NULL; + + for (i = 0; methods != NULL && methods[i] != NULL; i++) { + if (!strcmp(methods[i], "wins")) { + resolve_context_add_wins_method(ret, lp_wins_server_list(lp_ctx)); + } else if (!strcmp(methods[i], "bcast")) { + resolve_context_add_bcast_method(ret); + } else if (!strcmp(methods[i], "host")) { + resolve_context_add_host_method(ret); + } else { + DEBUG(0, ("Unknown resolve method '%s'", methods[i])); + } + } + + return ret; +} diff --git a/source4/libcli/resolve/resolve.h b/source4/libcli/resolve/resolve.h index 72db3839a2..73cb78c124 100644 --- a/source4/libcli/resolve/resolve.h +++ b/source4/libcli/resolve/resolve.h @@ -23,6 +23,8 @@ #define __RESOLVE_H__ #include "libcli/nbt/libnbt.h" +typedef struct composite_context *(*resolve_name_send_fn)(TALLOC_CTX *mem_ctx, struct event_context *, void *privdata, struct nbt_name *); +typedef NTSTATUS (*resolve_name_recv_fn)(struct composite_context *, TALLOC_CTX *, const char **); #include "libcli/resolve/proto.h" #endif /* __RESOLVE_H__ */ diff --git a/source4/libcli/resolve/testsuite.c b/source4/libcli/resolve/testsuite.c index b87b59b81a..73a8c841bb 100644 --- a/source4/libcli/resolve/testsuite.c +++ b/source4/libcli/resolve/testsuite.c @@ -44,7 +44,7 @@ static bool test_async_resolve(struct torture_context *tctx) host, timelimit); while (timeval_elapsed(&tv) < timelimit) { const char *s; - struct composite_context *c = resolve_name_host_send(mem_ctx, ev, &n); + struct composite_context *c = resolve_name_host_send(mem_ctx, ev, NULL, &n); torture_assert(tctx, c != NULL, "resolve_name_host_send"); torture_assert_ntstatus_ok(tctx, resolve_name_host_recv(c, mem_ctx, &s), "async resolve failed"); diff --git a/source4/libcli/resolve/wins.c b/source4/libcli/resolve/wins.c index 2cbcd5f483..73b9413eb4 100644 --- a/source4/libcli/resolve/wins.c +++ b/source4/libcli/resolve/wins.c @@ -24,17 +24,22 @@ #include "libcli/resolve/resolve.h" #include "param/param.h" -/* +struct resolve_wins_data { + const char **address_list; +}; + +/** wins name resolution method - async send */ struct composite_context *resolve_name_wins_send( TALLOC_CTX *mem_ctx, struct event_context *event_ctx, + void *userdata, struct nbt_name *name) { - const char **address_list = lp_wins_server_list(global_loadparm); - if (address_list == NULL) return NULL; - return resolve_name_nbtlist_send(mem_ctx, event_ctx, name, address_list, false, true); + struct resolve_wins_data *wins_data = talloc_get_type(userdata, struct resolve_wins_data); + if (wins_data->address_list == NULL) return NULL; + return resolve_name_nbtlist_send(mem_ctx, event_ctx, name, wins_data->address_list, false, true); } /* @@ -51,9 +56,20 @@ NTSTATUS resolve_name_wins_recv(struct composite_context *c, */ NTSTATUS resolve_name_wins(struct nbt_name *name, TALLOC_CTX *mem_ctx, + const char **address_list, const char **reply_addr) { - struct composite_context *c = resolve_name_wins_send(mem_ctx, NULL, name); + struct composite_context *c; + struct resolve_wins_data *wins_data = talloc(mem_ctx, struct resolve_wins_data); + wins_data->address_list = address_list; + c = resolve_name_wins_send(mem_ctx, NULL, wins_data, name); return resolve_name_wins_recv(c, mem_ctx, reply_addr); } +bool resolve_context_add_wins_method(struct resolve_context *ctx, const char **address_list) +{ + struct resolve_wins_data *wins_data = talloc(ctx, struct resolve_wins_data); + wins_data->address_list = str_list_copy(wins_data, address_list); + return resolve_context_add_method(ctx, resolve_name_wins_send, resolve_name_wins_recv, + wins_data); +} diff --git a/source4/libcli/smb2/connect.c b/source4/libcli/smb2/connect.c index 39bb992d11..8b75e125b0 100644 --- a/source4/libcli/smb2/connect.c +++ b/source4/libcli/smb2/connect.c @@ -163,7 +163,7 @@ static void continue_resolve(struct composite_context *creq) struct composite_context *smb2_connect_send(TALLOC_CTX *mem_ctx, const char *host, const char *share, - const char **name_resolve_order, + struct resolve_context *resolve_ctx, struct cli_credentials *credentials, struct event_context *ev) { @@ -188,7 +188,7 @@ struct composite_context *smb2_connect_send(TALLOC_CTX *mem_ctx, ZERO_STRUCT(name); name.name = host; - creq = resolve_name_send(&name, c->event_ctx, name_resolve_order); + creq = resolve_name_send(resolve_ctx, &name, c->event_ctx); composite_continue(c, creq, continue_resolve, c); return c; } @@ -215,13 +215,13 @@ NTSTATUS smb2_connect_recv(struct composite_context *c, TALLOC_CTX *mem_ctx, */ NTSTATUS smb2_connect(TALLOC_CTX *mem_ctx, const char *host, const char *share, - const char **name_resolve_order, + struct resolve_context *resolve_ctx, struct cli_credentials *credentials, struct smb2_tree **tree, struct event_context *ev) { struct composite_context *c = smb2_connect_send(mem_ctx, host, share, - name_resolve_order, + resolve_ctx, credentials, ev); return smb2_connect_recv(c, mem_ctx, tree); } diff --git a/source4/libcli/smb2/smb2_calls.h b/source4/libcli/smb2/smb2_calls.h index 318a634ac4..6a551da4ae 100644 --- a/source4/libcli/smb2/smb2_calls.h +++ b/source4/libcli/smb2/smb2_calls.h @@ -95,4 +95,5 @@ struct smb2_setinfo { struct cli_credentials; struct event_context; +struct resolve_context; #include "libcli/smb2/smb2_proto.h" diff --git a/source4/libcli/smb_composite/connect.c b/source4/libcli/smb_composite/connect.c index 9579cd20b5..1a8262c76a 100644 --- a/source4/libcli/smb_composite/connect.c +++ b/source4/libcli/smb_composite/connect.c @@ -463,8 +463,7 @@ struct composite_context *smb_composite_connect_send(struct smb_composite_connec state->stage = CONNECT_RESOLVE; make_nbt_name_server(&name, io->in.dest_host); - state->creq = resolve_name_send(&name, c->event_ctx, - lp_name_resolve_order(global_loadparm)); + state->creq = resolve_name_send(lp_resolve_context(global_loadparm), &name, c->event_ctx); if (state->creq == NULL) goto failed; state->creq->async.private_data = c; diff --git a/source4/libcli/wrepl/winsrepl.c b/source4/libcli/wrepl/winsrepl.c index 9f7bd91ec9..00346c45a4 100644 --- a/source4/libcli/wrepl/winsrepl.c +++ b/source4/libcli/wrepl/winsrepl.c @@ -30,6 +30,7 @@ #include "system/network.h" #include "lib/socket/netif.h" #include "param/param.h" +#include "libcli/resolve/resolve.h" static struct wrepl_request *wrepl_request_finished(struct wrepl_request *req, NTSTATUS status); @@ -343,7 +344,7 @@ struct composite_context *wrepl_connect_send(struct wrepl_socket *wrepl_socket, if (composite_nomem(peer, result)) return result; state->creq = socket_connect_send(wrepl_socket->sock, us, peer, - 0, lp_name_resolve_order(global_loadparm), + 0, lp_resolve_context(global_loadparm), wrepl_socket->event.ctx); composite_continue(result, state->creq, wrepl_connect_handler, state); return result; |