summaryrefslogtreecommitdiff
path: root/source4/librpc/rpc
diff options
context:
space:
mode:
Diffstat (limited to 'source4/librpc/rpc')
-rw-r--r--source4/librpc/rpc/dcerpc.h1
-rw-r--r--source4/librpc/rpc/dcerpc_auth.c11
-rw-r--r--source4/librpc/rpc/dcerpc_connect.c24
-rw-r--r--source4/librpc/rpc/dcerpc_schannel.c17
-rw-r--r--source4/librpc/rpc/dcerpc_util.c18
5 files changed, 37 insertions, 34 deletions
diff --git a/source4/librpc/rpc/dcerpc.h b/source4/librpc/rpc/dcerpc.h
index cbfe8478b2..df70580db3 100644
--- a/source4/librpc/rpc/dcerpc.h
+++ b/source4/librpc/rpc/dcerpc.h
@@ -100,6 +100,7 @@ struct dcerpc_pipe {
struct dcerpc_syntax_id transfer_syntax;
struct dcerpc_connection *conn;
+ struct dcerpc_binding *binding;
/* the last fault code from a DCERPC fault */
uint32_t last_fault_code;
diff --git a/source4/librpc/rpc/dcerpc_auth.c b/source4/librpc/rpc/dcerpc_auth.c
index bffa994abe..f0a7dc8ffe 100644
--- a/source4/librpc/rpc/dcerpc_auth.c
+++ b/source4/librpc/rpc/dcerpc_auth.c
@@ -168,7 +168,7 @@ struct composite_context *dcerpc_bind_auth_send(TALLOC_CTX *mem_ctx,
struct dcerpc_pipe *p,
const struct dcerpc_interface_table *table,
struct cli_credentials *credentials,
- uint8_t auth_type,
+ uint8_t auth_type, uint8_t auth_level,
const char *service)
{
struct composite_context *c, *creq;
@@ -233,8 +233,7 @@ struct composite_context *dcerpc_bind_auth_send(TALLOC_CTX *mem_ctx,
}
c->status = gensec_start_mech_by_authtype(sec->generic_state,
- auth_type,
- dcerpc_auth_level(p->conn));
+ auth_type, auth_level);
if (!NT_STATUS_IS_OK(c->status)) {
DEBUG(1, ("Failed to start GENSEC client mechanism %s: %s\n",
gensec_get_name_by_authtype(auth_type),
@@ -249,7 +248,7 @@ struct composite_context *dcerpc_bind_auth_send(TALLOC_CTX *mem_ctx,
}
sec->auth_info->auth_type = auth_type;
- sec->auth_info->auth_level = dcerpc_auth_level(p->conn);
+ sec->auth_info->auth_level = auth_level,
sec->auth_info->auth_pad_length = 0;
sec->auth_info->auth_reserved = 0;
sec->auth_info->auth_context_id = random();
@@ -323,11 +322,11 @@ NTSTATUS dcerpc_bind_auth_recv(struct composite_context *creq)
NTSTATUS dcerpc_bind_auth(struct dcerpc_pipe *p,
const struct dcerpc_interface_table *table,
struct cli_credentials *credentials,
- uint8_t auth_type,
+ uint8_t auth_type, uint8_t auth_level,
const char *service)
{
struct composite_context *creq;
creq = dcerpc_bind_auth_send(p, p, table, credentials,
- auth_type, service);
+ auth_type, auth_level, service);
return dcerpc_bind_auth_recv(creq);
}
diff --git a/source4/librpc/rpc/dcerpc_connect.c b/source4/librpc/rpc/dcerpc_connect.c
index 1c9ab8c0ed..67dfda6d7a 100644
--- a/source4/librpc/rpc/dcerpc_connect.c
+++ b/source4/librpc/rpc/dcerpc_connect.c
@@ -131,29 +131,19 @@ struct composite_context *dcerpc_pipe_connect_ncacn_np_smb_send(TALLOC_CTX *mem_
conn->in.called_name = strupper_talloc(mem_ctx, s->io.binding->host);
conn->in.service = "IPC$";
conn->in.service_type = NULL;
- conn->in.fallback_to_anonymous = False;
conn->in.workgroup = lp_workgroup();
/*
- * provide proper credentials - user supplied or anonymous in case this is
- * schannel connection
+ * provide proper credentials - user supplied, but allow a
+ * fallback to anonymous if this is an schannel connection
+ * (might be NT4 not allowing machine logins at session
+ * setup).
*/
+ s->conn.in.credentials = s->io.creds;
if (s->io.binding->flags & DCERPC_SCHANNEL) {
- struct cli_credentials *anon_creds;
-
- anon_creds = cli_credentials_init(mem_ctx);
- if (!anon_creds) {
- composite_error(c, NT_STATUS_NO_MEMORY);
- goto done;
- }
-
- cli_credentials_set_anonymous(anon_creds);
- cli_credentials_guess(anon_creds);
-
- s->conn.in.credentials = anon_creds;
-
+ conn->in.fallback_to_anonymous = True;
} else {
- s->conn.in.credentials = s->io.creds;
+ conn->in.fallback_to_anonymous = False;
}
/* send smb connect request */
diff --git a/source4/librpc/rpc/dcerpc_schannel.c b/source4/librpc/rpc/dcerpc_schannel.c
index 108b678188..64cf6748e8 100644
--- a/source4/librpc/rpc/dcerpc_schannel.c
+++ b/source4/librpc/rpc/dcerpc_schannel.c
@@ -55,16 +55,15 @@ static NTSTATUS dcerpc_schannel_key(TALLOC_CTX *tmp_ctx,
step 1 - establish a netlogon connection, with no authentication
*/
- /* Find the original binding string */
- status = dcerpc_parse_binding(tmp_ctx, p->conn->binding_string, &b);
- if (!NT_STATUS_IS_OK(status)) {
- DEBUG(0,("Failed to parse dcerpc binding '%s'\n", p->conn->binding_string));
- return status;
+ b = talloc(tmp_ctx, struct dcerpc_binding);
+ if (!b) {
+ return NT_STATUS_NO_MEMORY;
}
+ *b = *p->binding;
/* Make binding string for netlogon, not the other pipe */
status = dcerpc_epm_map_binding(tmp_ctx, b,
- &dcerpc_table_netlogon,
+ &dcerpc_table_netlogon,
p->conn->event_ctx);
if (!NT_STATUS_IS_OK(status)) {
DEBUG(0,("Failed to map DCERPC/TCP NCACN_NP pipe for '%s' - %s\n",
@@ -141,7 +140,8 @@ static NTSTATUS dcerpc_schannel_key(TALLOC_CTX *tmp_ctx,
NTSTATUS dcerpc_bind_auth_schannel(TALLOC_CTX *tmp_ctx,
struct dcerpc_pipe *p,
const struct dcerpc_interface_table *table,
- struct cli_credentials *credentials)
+ struct cli_credentials *credentials,
+ uint8_t auth_level)
{
NTSTATUS status;
@@ -156,7 +156,8 @@ NTSTATUS dcerpc_bind_auth_schannel(TALLOC_CTX *tmp_ctx,
return status;
}
- return dcerpc_bind_auth(p, table, credentials, DCERPC_AUTH_TYPE_SCHANNEL,
+ return dcerpc_bind_auth(p, table, credentials,
+ DCERPC_AUTH_TYPE_SCHANNEL, auth_level,
NULL);
}
diff --git a/source4/librpc/rpc/dcerpc_util.c b/source4/librpc/rpc/dcerpc_util.c
index 15a45ed3f0..6ef91b87b0 100644
--- a/source4/librpc/rpc/dcerpc_util.c
+++ b/source4/librpc/rpc/dcerpc_util.c
@@ -889,9 +889,10 @@ NTSTATUS dcerpc_pipe_auth(struct dcerpc_pipe *p,
/* If we don't already have netlogon credentials for
* the schannel bind, then we have to get these
* first */
- status = dcerpc_bind_auth_schannel(tmp_ctx, p, table, credentials);
+ status = dcerpc_bind_auth_schannel(tmp_ctx, p, table, credentials,
+ dcerpc_auth_level(p->conn));
} else if (!cli_credentials_is_anonymous(credentials) &&
- !(binding->transport == NCACN_NP &&
+ !(p->conn->transport.transport == NCACN_NP &&
!(binding->flags & DCERPC_SIGN) &&
!(binding->flags & DCERPC_SEAL))) {
@@ -925,7 +926,9 @@ NTSTATUS dcerpc_pipe_auth(struct dcerpc_pipe *p,
}
status = dcerpc_bind_auth(p, table,
- credentials, auth_type, table->authservices->names[0]);
+ credentials, auth_type,
+ dcerpc_auth_level(p->conn),
+ table->authservices->names[0]);
} else {
status = dcerpc_bind_auth_none(p, table);
}
@@ -1099,6 +1102,11 @@ NTSTATUS dcerpc_pipe_connect_b(TALLOC_CTX *parent_ctx,
return status;
}
+ p->binding = binding;
+ if (!talloc_reference(p, binding)) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
status = dcerpc_pipe_auth(p, binding, table, credentials);
if (!NT_STATUS_IS_OK(status)) {
talloc_free(p);
@@ -1195,6 +1203,10 @@ NTSTATUS dcerpc_secondary_connection(struct dcerpc_pipe *p, struct dcerpc_pipe *
}
(*p2)->conn->flags = p->conn->flags;
+ (*p2)->binding = b;
+ if (!talloc_reference(*p2, b)) {
+ return NT_STATUS_NO_MEMORY;
+ }
return NT_STATUS_OK;
}