1
0
mirror of https://github.com/samba-team/samba.git synced 2025-11-29 16:23:52 +03:00

r4640: first stage in the server side support for multiple context_ids on one pipe

this stage does the following:

 - simplifies the dcerpc_handle handling, and all the callers of it

 - split out the context_id depenent state into a linked list of established contexts

 - fixed some talloc handling in several rpc servers that i noticed while doing the above
(This used to be commit fde042b3fc)
This commit is contained in:
Andrew Tridgell
2005-01-10 12:15:26 +00:00
committed by Gerald (Jerry) Carter
parent 3136462ea9
commit 577218b2ad
15 changed files with 217 additions and 256 deletions

View File

@@ -69,10 +69,10 @@ static NTSTATUS $name\__op_bind(struct dcesrv_call_state *dce_call, const struct
#endif
}
static void $name\__op_unbind(struct dcesrv_connection *dce_conn, const struct dcesrv_interface *iface)
static void $name\__op_unbind(struct dcesrv_connection_context *context, const struct dcesrv_interface *iface)
{
#ifdef DCESRV_INTERFACE_$uname\_UNBIND
DCESRV_INTERFACE_$uname\_UNBIND(dce_conn,iface);
DCESRV_INTERFACE_$uname\_UNBIND(context, iface);
#else
return;
#endif

View File

@@ -97,6 +97,7 @@ struct pvfs_file_handle;
struct dcesrv_context;
struct dcesrv_interface;
struct dcesrv_connection;
struct dcesrv_connection_context;
struct dcesrv_endpoint;
struct dcesrv_call_state;
struct dcesrv_auth;

View File

@@ -43,12 +43,19 @@
invalid handle or retval if the handle is of the
wrong type */
#define DCESRV_PULL_HANDLE_RETVAL(h, inhandle, t, retval) do { \
(h) = dcesrv_handle_fetch(dce_call->conn, (inhandle), DCESRV_HANDLE_ANY); \
(h) = dcesrv_handle_fetch(dce_call->context, (inhandle), DCESRV_HANDLE_ANY); \
DCESRV_CHECK_HANDLE(h); \
if ((t) != DCESRV_HANDLE_ANY && (h)->wire_handle.handle_type != (t)) { \
return retval; \
} \
} while (0)
/* this checks for a valid policy handle and gives a dcerpc fault
if its the wrong type of handle */
#define DCESRV_PULL_HANDLE_FAULT(h, inhandle, t) do { \
(h) = dcesrv_handle_fetch(dce_call->context, (inhandle), t); \
DCESRV_CHECK_HANDLE(h); \
} while (0)
#define DCESRV_PULL_HANDLE(h, inhandle, t) DCESRV_PULL_HANDLE_RETVAL(h, inhandle, t, NT_STATUS_INVALID_HANDLE)
#define DCESRV_PULL_HANDLE_WERR(h, inhandle, t) DCESRV_PULL_HANDLE_RETVAL(h, inhandle, t, WERR_BADFID)

View File

@@ -63,6 +63,19 @@ static struct dcesrv_endpoint *find_endpoint(struct dcesrv_context *dce_ctx,
return NULL;
}
/*
find a registered context_id from a bind or alter_context
*/
static struct dcesrv_connection_context *dcesrv_find_context(struct dcesrv_connection *conn,
uint32_t context_id)
{
struct dcesrv_connection_context *c;
for (c=conn->contexts;c;c=c->next) {
if (c->context_id == context_id) return c;
}
return NULL;
}
/*
see if a uuid and if_version match to an interface
*/
@@ -264,14 +277,18 @@ NTSTATUS dcesrv_fetch_session_key(struct dcesrv_connection *p,
static int dcesrv_endpoint_destructor(void *ptr)
{
struct dcesrv_connection *p = ptr;
if (p->iface) {
p->iface->unbind(p, p->iface);
while (p->contexts) {
struct dcesrv_connection_context *c = p->contexts;
DLIST_REMOVE(p->contexts, c);
if (c->iface) {
c->iface->unbind(c, c->iface);
}
talloc_free(c);
}
/* destroy any handles */
while (p->handles) {
dcesrv_handle_destroy(p, p->handles);
}
return 0;
}
@@ -291,11 +308,9 @@ NTSTATUS dcesrv_endpoint_connect(struct dcesrv_context *dce_ctx,
(*p)->dce_ctx = dce_ctx;
(*p)->endpoint = ep;
(*p)->iface = NULL;
(*p)->private = NULL;
(*p)->contexts = NULL;
(*p)->call_list = NULL;
(*p)->cli_max_recv_frag = 0;
(*p)->handles = NULL;
(*p)->partial_input = data_blob(NULL, 0);
(*p)->auth_state.auth_info = NULL;
(*p)->auth_state.gensec_security = NULL;
@@ -443,12 +458,21 @@ static NTSTATUS dcesrv_bind(struct dcesrv_call_state *call)
struct dcesrv_call_reply *rep;
NTSTATUS status;
uint32_t result=0, reason=0;
uint32_t context_id;
const struct dcesrv_interface *iface;
if (call->pkt.u.bind.num_contexts != 1 ||
call->pkt.u.bind.ctx_list[0].num_transfer_syntaxes < 1) {
return dcesrv_bind_nak(call, 0);
}
context_id = call->pkt.u.bind.ctx_list[0].context_id;
/* you can't bind twice on one context */
if (dcesrv_find_context(call->conn, context_id) != NULL) {
return dcesrv_bind_nak(call, 0);
}
if_version = call->pkt.u.bind.ctx_list[0].abstract_syntax.if_version;
uuid = GUID_string(call, &call->pkt.u.bind.ctx_list[0].abstract_syntax.uuid);
if (!uuid) {
@@ -465,14 +489,30 @@ static NTSTATUS dcesrv_bind(struct dcesrv_call_state *call)
return dcesrv_bind_nak(call, 0);
}
call->conn->iface = find_interface_by_uuid(call->conn->endpoint, uuid, if_version);
if (!call->conn->iface) {
iface = find_interface_by_uuid(call->conn->endpoint, uuid, if_version);
if (iface == NULL) {
DEBUG(2,("Request for unknown dcerpc interface %s/%d\n", uuid, if_version));
/* we don't know about that interface */
result = DCERPC_BIND_PROVIDER_REJECT;
reason = DCERPC_BIND_REASON_ASYNTAX;
}
if (iface) {
/* add this context to the list of available context_ids */
struct dcesrv_connection_context *context = talloc(call->conn,
struct dcesrv_connection_context);
if (context == NULL) {
return dcesrv_bind_nak(call, 0);
}
context->conn = call->conn;
context->iface = iface;
context->context_id = context_id;
context->private = NULL;
context->handles = NULL;
DLIST_ADD(call->conn->contexts, context);
call->context = context;
}
if (call->conn->cli_max_recv_frag == 0) {
call->conn->cli_max_recv_frag = call->pkt.u.bind.max_recv_frag;
}
@@ -492,10 +532,9 @@ static NTSTATUS dcesrv_bind(struct dcesrv_call_state *call)
pkt.u.bind_ack.max_xmit_frag = 0x2000;
pkt.u.bind_ack.max_recv_frag = 0x2000;
pkt.u.bind_ack.assoc_group_id = call->pkt.u.bind.assoc_group_id;
if (call->conn->iface) {
if (iface) {
/* FIXME: Use pipe name as specified by endpoint instead of interface name */
pkt.u.bind_ack.secondary_address = talloc_asprintf(call, "\\PIPE\\%s",
call->conn->iface->name);
pkt.u.bind_ack.secondary_address = talloc_asprintf(call, "\\PIPE\\%s", iface->name);
} else {
pkt.u.bind_ack.secondary_address = "";
}
@@ -514,15 +553,16 @@ static NTSTATUS dcesrv_bind(struct dcesrv_call_state *call)
return dcesrv_bind_nak(call, 0);
}
if (call->conn->iface) {
status = call->conn->iface->bind(call, call->conn->iface);
if (iface) {
status = iface->bind(call, iface);
if (!NT_STATUS_IS_OK(status)) {
DEBUG(2,("Request for dcerpc interface %s/%d rejected: %s\n", uuid, if_version, nt_errstr(status)));
DEBUG(2,("Request for dcerpc interface %s/%d rejected: %s\n",
uuid, if_version, nt_errstr(status)));
return dcesrv_bind_nak(call, 0);
}
}
rep = talloc_p(call, struct dcesrv_call_reply);
rep = talloc(call, struct dcesrv_call_reply);
if (!rep) {
return NT_STATUS_NO_MEMORY;
}
@@ -630,13 +670,17 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
NTSTATUS status;
DATA_BLOB stub;
uint32_t total_length;
struct dcesrv_connection_context *context;
call->fault_code = 0;
if (!call->conn->iface) {
context = dcesrv_find_context(call->conn, call->pkt.u.request.context_id);
if (context == NULL) {
return dcesrv_fault(call, DCERPC_FAULT_UNK_IF);
}
call->context = context;
pull = ndr_pull_init_blob(&call->pkt.u.request.stub_and_verifier, call);
if (!pull) {
return NT_STATUS_NO_MEMORY;
@@ -651,7 +695,7 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
}
/* unravel the NDR for the packet */
status = call->conn->iface->ndr_pull(call, call, pull, &r);
status = context->iface->ndr_pull(call, call, pull, &r);
if (!NT_STATUS_IS_OK(status)) {
return dcesrv_fault(call, call->fault_code);
}
@@ -663,7 +707,7 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
}
/* call the dispatch function */
status = call->conn->iface->dispatch(call, call, r);
status = context->iface->dispatch(call, call, r);
if (!NT_STATUS_IS_OK(status)) {
return dcesrv_fault(call, call->fault_code);
}
@@ -683,7 +727,7 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
push->flags |= LIBNDR_FLAG_BIGENDIAN;
}
status = call->conn->iface->ndr_push(call, call, push, r);
status = context->iface->ndr_push(call, call, push, r);
if (!NT_STATUS_IS_OK(status)) {
return dcesrv_fault(call, call->fault_code);
}
@@ -697,7 +741,7 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
struct dcesrv_call_reply *rep;
struct dcerpc_packet pkt;
rep = talloc_p(call, struct dcesrv_call_reply);
rep = talloc(call, struct dcesrv_call_reply);
if (!rep) {
return NT_STATUS_NO_MEMORY;
}
@@ -787,13 +831,14 @@ NTSTATUS dcesrv_input_process(struct dcesrv_connection *dce_conn)
struct dcesrv_call_state *call;
DATA_BLOB blob;
call = talloc_p(dce_conn, struct dcesrv_call_state);
call = talloc(dce_conn, struct dcesrv_call_state);
if (!call) {
talloc_free(dce_conn->partial_input.data);
return NT_STATUS_NO_MEMORY;
}
call->conn = dce_conn;
call->replies = NULL;
call->context = NULL;
blob = dce_conn->partial_input;
blob.length = dcerpc_get_frag_length(&blob);

View File

@@ -44,8 +44,7 @@ struct dcesrv_interface {
NTSTATUS (*bind)(struct dcesrv_call_state *, const struct dcesrv_interface *);
/* this function is called when the client disconnects the endpoint */
void (*unbind)(struct dcesrv_connection *, const struct dcesrv_interface *);
void (*unbind)(struct dcesrv_connection_context *, const struct dcesrv_interface *);
/* the ndr_pull function for the chosen interface.
*/
@@ -67,6 +66,7 @@ struct dcesrv_interface {
struct dcesrv_call_state {
struct dcesrv_call_state *next, *prev;
struct dcesrv_connection *conn;
struct dcesrv_connection_context *context;
struct dcerpc_packet pkt;
DATA_BLOB input;
@@ -85,9 +85,10 @@ struct dcesrv_call_state {
/* a dcerpc handle in internal format */
struct dcesrv_handle {
struct dcesrv_handle *next, *prev;
struct dcesrv_connection_context *context;
struct policy_handle wire_handle;
void *data;
void (*destroy)(struct dcesrv_connection *, struct dcesrv_handle *);
void (*destroy)(struct dcesrv_connection_context *, struct dcesrv_handle *);
};
/* hold the authentication state information */
@@ -98,6 +99,24 @@ struct dcesrv_auth {
NTSTATUS (*session_key)(struct dcesrv_connection *, DATA_BLOB *session_key);
};
struct dcesrv_connection_context {
struct dcesrv_connection_context *next, *prev;
uint32_t context_id;
/* the connection this is on */
struct dcesrv_connection *conn;
/* the ndr function table for the chosen interface */
const struct dcesrv_interface *iface;
/* private data for the interface implementation */
void *private;
/* current rpc handles - this is really the wrong scope for
them, but it will do for now */
struct dcesrv_handle *handles;
};
/* the state associated with a dcerpc server connection */
struct dcesrv_connection {
@@ -107,8 +126,8 @@ struct dcesrv_connection {
/* the endpoint that was opened */
const struct dcesrv_endpoint *endpoint;
/* the ndr function table for the chosen interface */
const struct dcesrv_interface *iface;
/* a list of established context_ids */
struct dcesrv_connection_context *contexts;
/* the state of the current calls */
struct dcesrv_call_state *call_list;
@@ -116,13 +135,6 @@ struct dcesrv_connection {
/* the maximum size the client wants to receive */
uint32_t cli_max_recv_frag;
/* private data for the interface implementation */
void *private;
/* current rpc handles - this is really the wrong scope for
them, but it will do for now */
struct dcesrv_handle *handles;
DATA_BLOB partial_input;
/* the current authentication state */

View File

@@ -26,14 +26,6 @@
#include "rpc_server/common/common.h"
#include "rpc_server/drsuapi/dcesrv_drsuapi.h"
/*
destroy a general handle.
*/
static void drsuapi_handle_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
{
talloc_free(h->data);
}
/*
drsuapi_DsBind
*/
@@ -57,14 +49,13 @@ static WERROR drsuapi_DsBind(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem
return WERR_FOOBAR;
}
handle = dcesrv_handle_new(dce_call->conn, DRSUAPI_BIND_HANDLE);
handle = dcesrv_handle_new(dce_call->context, DRSUAPI_BIND_HANDLE);
if (!handle) {
talloc_free(b_state);
return WERR_NOMEM;
}
handle->data = b_state;
handle->destroy = drsuapi_handle_destroy;
handle->data = talloc_steal(handle, b_state);
bind_info = talloc_p(mem_ctx, struct drsuapi_DsBindInfoCtr);
WERR_TALLOC_CHECK(bind_info);
@@ -96,10 +87,7 @@ static WERROR drsuapi_DsUnbind(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
DCESRV_PULL_HANDLE_WERR(h, r->in.bind_handle, DRSUAPI_BIND_HANDLE);
/* this causes the callback drsuapi_handle_destroy() to be called by
the handle destroy code which destroys the state associated
with the handle */
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
ZERO_STRUCTP(r->out.bind_handle);

View File

@@ -121,8 +121,7 @@ static error_status_t epm_Lookup(struct dcesrv_call_state *dce_call, TALLOC_CTX
uint32_t num_ents;
int i;
h = dcesrv_handle_fetch(dce_call->conn, r->in.entry_handle, HTYPE_LOOKUP);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.entry_handle, HTYPE_LOOKUP);
eps = h->data;
@@ -150,7 +149,7 @@ static error_status_t epm_Lookup(struct dcesrv_call_state *dce_call, TALLOC_CTX
if (num_ents == 0) {
r->out.entries = NULL;
ZERO_STRUCTP(r->out.entry_handle);
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
return EPMAPPER_STATUS_NO_MORE_ENTRIES;
}

View File

@@ -24,58 +24,62 @@
#include "dlinklist.h"
#include "rpc_server/dcerpc_server.h"
/*
destroy a rpc handle
*/
static int dcesrv_handle_destructor(void *ptr)
{
struct dcesrv_handle *h = ptr;
if (h->destroy) {
h->destroy(h->context, h);
}
DLIST_REMOVE(h->context->handles, h);
talloc_free(h);
return 0;
}
/*
allocate a new rpc handle
*/
struct dcesrv_handle *dcesrv_handle_new(struct dcesrv_connection *dce_conn,
struct dcesrv_handle *dcesrv_handle_new(struct dcesrv_connection_context *context,
uint8_t handle_type)
{
struct dcesrv_handle *h;
h = talloc_p(dce_conn, struct dcesrv_handle);
h = talloc_p(context, struct dcesrv_handle);
if (!h) {
return NULL;
}
h->data = NULL;
h->destroy = NULL;
h->context = context;
h->wire_handle.handle_type = handle_type;
h->wire_handle.uuid = GUID_random();
DLIST_ADD(dce_conn->handles, h);
DLIST_ADD(context->handles, h);
talloc_set_destructor(h, dcesrv_handle_destructor);
return h;
}
/*
destroy a rpc handle
*/
void dcesrv_handle_destroy(struct dcesrv_connection *dce_conn,
struct dcesrv_handle *h)
{
if (h->destroy) {
h->destroy(dce_conn, h);
}
DLIST_REMOVE(dce_conn->handles, h);
talloc_free(h);
}
/*
find an internal handle given a wire handle. If the wire handle is NULL then
allocate a new handle
*/
struct dcesrv_handle *dcesrv_handle_fetch(struct dcesrv_connection *dce_conn,
struct dcesrv_handle *dcesrv_handle_fetch(struct dcesrv_connection_context *context,
struct policy_handle *p,
uint8_t handle_type)
{
struct dcesrv_handle *h;
if (policy_handle_empty(p)) {
return dcesrv_handle_new(dce_conn, handle_type);
return dcesrv_handle_new(context, handle_type);
}
for (h=dce_conn->handles; h; h=h->next) {
for (h=context->handles; h; h=h->next) {
if (h->wire_handle.handle_type == p->handle_type &&
GUID_equal(&p->uuid, &h->wire_handle.uuid)) {
if (handle_type != DCESRV_HANDLE_ANY &&

View File

@@ -65,24 +65,6 @@ struct lsa_account_state {
};
/*
destroy an open policy. This closes the database connection
*/
static void lsa_Policy_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
{
struct lsa_policy_state *state = h->data;
talloc_free(state);
}
/*
destroy an open account.
*/
static void lsa_Account_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
{
struct lsa_account_state *astate = h->data;
talloc_free(astate);
}
/*
lsa_Close
*/
@@ -95,10 +77,7 @@ static NTSTATUS lsa_Close(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ct
DCESRV_PULL_HANDLE(h, r->in.handle, DCESRV_HANDLE_ANY);
/* this causes the callback samr_XXX_destroy() to be called by
the handle destroy code which destroys the state associated
with the handle */
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
ZERO_STRUCTP(r->out.handle);
@@ -278,13 +257,12 @@ static NTSTATUS lsa_OpenPolicy2(struct dcesrv_call_state *dce_call, TALLOC_CTX *
return status;
}
handle = dcesrv_handle_new(dce_call->conn, LSA_HANDLE_POLICY);
handle = dcesrv_handle_new(dce_call->context, LSA_HANDLE_POLICY);
if (!handle) {
return NT_STATUS_NO_MEMORY;
}
handle->data = talloc_reference(handle, state);
handle->destroy = lsa_Policy_destroy;
handle->data = talloc_steal(handle, state);
state->access_mask = r->in.access_mask;
state->handle = handle;
@@ -858,14 +836,13 @@ static NTSTATUS lsa_OpenAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *
astate->policy = talloc_reference(astate, state);
astate->access_mask = r->in.access_mask;
ah = dcesrv_handle_new(dce_call->conn, LSA_HANDLE_ACCOUNT);
ah = dcesrv_handle_new(dce_call->context, LSA_HANDLE_ACCOUNT);
if (!ah) {
talloc_free(astate);
return NT_STATUS_NO_MEMORY;
}
ah->data = astate;
ah->destroy = lsa_Account_destroy;
ah->data = talloc_steal(ah, astate);
*r->out.acct_handle = ah->wire_handle;

View File

@@ -73,7 +73,7 @@ static NTSTATUS netlogon_schannel_setup(struct dcesrv_call_state *dce_call)
return status;
}
dce_call->conn->private = state;
dce_call->context->private = state;
return NT_STATUS_OK;
}
@@ -83,7 +83,7 @@ static NTSTATUS netlogon_schannel_setup(struct dcesrv_call_state *dce_call)
*/
static NTSTATUS netlogon_bind(struct dcesrv_call_state *dce_call, const struct dcesrv_interface *di)
{
dce_call->conn->private = NULL;
dce_call->context->private = NULL;
/* if this is a schannel bind then we need to reconstruct the pipe state */
if (dce_call->conn->auth_state.auth_info &&
@@ -103,15 +103,11 @@ static NTSTATUS netlogon_bind(struct dcesrv_call_state *dce_call, const struct d
}
/* this function is called when the client disconnects the endpoint */
static void netlogon_unbind(struct dcesrv_connection *conn, const struct dcesrv_interface *di)
static void netlogon_unbind(struct dcesrv_connection_context *context, const struct dcesrv_interface *di)
{
struct server_pipe_state *pipe_state = conn->private;
if (pipe_state) {
struct server_pipe_state *pipe_state = context->private;
talloc_free(pipe_state);
}
conn->private = NULL;
context->private = NULL;
}
#define DCESRV_INTERFACE_NETLOGON_BIND netlogon_bind
@@ -120,7 +116,7 @@ static void netlogon_unbind(struct dcesrv_connection *conn, const struct dcesrv_
static NTSTATUS netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
struct netr_ServerReqChallenge *r)
{
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
ZERO_STRUCTP(r->out.credentials);
@@ -128,10 +124,10 @@ static NTSTATUS netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALL
if (pipe_state) {
talloc_free(pipe_state);
dce_call->conn->private = NULL;
dce_call->context->private = NULL;
}
pipe_state = talloc_p(dce_call->conn, struct server_pipe_state);
pipe_state = talloc_p(dce_call->context, struct server_pipe_state);
if (!pipe_state) {
return NT_STATUS_NO_MEMORY;
}
@@ -148,7 +144,7 @@ static NTSTATUS netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALL
*r->out.credentials = pipe_state->server_challenge;
dce_call->conn->private = pipe_state;
dce_call->context->private = pipe_state;
return NT_STATUS_OK;
}
@@ -156,7 +152,7 @@ static NTSTATUS netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALL
static NTSTATUS netr_ServerAuthenticate3(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
struct netr_ServerAuthenticate3 *r)
{
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
void *sam_ctx;
struct samr_Password *mach_pwd;
uint16_t acct_flags;
@@ -339,7 +335,7 @@ static NTSTATUS netr_creds_server_step_check(struct server_pipe_state *pipe_stat
static NTSTATUS netr_ServerPasswordSet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
struct netr_ServerPasswordSet *r)
{
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
void *sam_ctx;
int num_records;
@@ -468,7 +464,7 @@ static WERROR netr_LogonUasLogoff(struct dcesrv_call_state *dce_call, TALLOC_CTX
static NTSTATUS netr_LogonSamLogonEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
struct netr_LogonSamLogonEx *r)
{
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
struct auth_context *auth_context;
struct auth_usersupplied_info *user_info;
@@ -539,7 +535,7 @@ static NTSTATUS netr_LogonSamLogonEx(struct dcesrv_call_state *dce_call, TALLOC_
nt_status = auth_check_password(auth_context, mem_ctx, user_info, &server_info);
NT_STATUS_NOT_OK_RETURN(nt_status);
sam = talloc_p(mem_ctx, struct netr_SamBaseInfo);
sam = talloc_zero(mem_ctx, struct netr_SamBaseInfo);
NT_STATUS_HAVE_NO_MEMORY(sam);
sam->last_logon = server_info->last_logon;
@@ -660,7 +656,7 @@ static NTSTATUS netr_LogonSamLogonWithFlags(struct dcesrv_call_state *dce_call,
NTSTATUS nt_status;
struct netr_LogonSamLogonEx r2;
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
r->out.return_authenticator = talloc_p(mem_ctx, struct netr_Authenticator);
if (!r->out.return_authenticator) {
@@ -963,7 +959,7 @@ static NTSTATUS fill_domain_trust_info(TALLOC_CTX *mem_ctx, struct ldb_message *
static NTSTATUS netr_LogonGetDomainInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
struct netr_LogonGetDomainInfo *r)
{
struct server_pipe_state *pipe_state = dce_call->conn->private;
struct server_pipe_state *pipe_state = dce_call->context->private;
const char * const attrs[] = { "name", "dnsDomain", "objectSid",
"objectGUID", "flatName", "securityIdentifier",
NULL };

View File

@@ -50,14 +50,14 @@ static NTSTATUS remote_op_bind(struct dcesrv_call_state *dce_call, const struct
return status;
}
dce_call->conn->private = private;
dce_call->context->private = private;
return NT_STATUS_OK;
}
static void remote_op_unbind(struct dcesrv_connection *dce_conn, const struct dcesrv_interface *iface)
static void remote_op_unbind(struct dcesrv_connection_context *context, const struct dcesrv_interface *iface)
{
struct dcesrv_remote_private *private = dce_conn->private;
struct dcesrv_remote_private *private = context->private;
dcerpc_pipe_close(private->c_pipe);
@@ -67,7 +67,7 @@ static void remote_op_unbind(struct dcesrv_connection *dce_conn, const struct dc
static NTSTATUS remote_op_ndr_pull(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, struct ndr_pull *pull, void **r)
{
NTSTATUS status;
const struct dcerpc_interface_table *table = dce_call->conn->iface->private;
const struct dcerpc_interface_table *table = dce_call->context->iface->private;
uint16_t opnum = dce_call->pkt.u.request.opnum;
dce_call->fault_code = 0;
@@ -96,9 +96,9 @@ static NTSTATUS remote_op_ndr_pull(struct dcesrv_call_state *dce_call, TALLOC_CT
static NTSTATUS remote_op_dispatch(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, void *r)
{
struct dcesrv_remote_private *private = dce_call->conn->private;
struct dcesrv_remote_private *private = dce_call->context->private;
uint16_t opnum = dce_call->pkt.u.request.opnum;
const struct dcerpc_interface_table *table = dce_call->conn->iface->private;
const struct dcerpc_interface_table *table = dce_call->context->iface->private;
const struct dcerpc_interface_call *call;
const char *name;
@@ -129,7 +129,7 @@ static NTSTATUS remote_op_dispatch(struct dcesrv_call_state *dce_call, TALLOC_CT
static NTSTATUS remote_op_ndr_push(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, struct ndr_push *push, void *r)
{
NTSTATUS status;
const struct dcerpc_interface_table *table = dce_call->conn->iface->private;
const struct dcerpc_interface_table *table = dce_call->context->iface->private;
uint16_t opnum = dce_call->pkt.u.request.opnum;
/* unravel the NDR for the packet */

View File

@@ -30,14 +30,6 @@
#include "lib/ldb/include/ldb.h"
/*
destroy a general handle.
*/
static void samr_handle_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
{
talloc_free(h->data);
}
/*
This is a bad temporary hack until we have at least some kind of schema
support
@@ -72,14 +64,13 @@ static NTSTATUS samr_Connect(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem
return NT_STATUS_INVALID_SYSTEM_SERVICE;
}
handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_CONNECT);
handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_CONNECT);
if (!handle) {
talloc_free(c_state);
return NT_STATUS_NO_MEMORY;
}
handle->data = c_state;
handle->destroy = samr_handle_destroy;
handle->data = talloc_steal(handle, c_state);
c_state->access_mask = r->in.access_mask;
*r->out.connect_handle = handle->wire_handle;
@@ -100,10 +91,7 @@ static NTSTATUS samr_Close(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_c
DCESRV_PULL_HANDLE(h, r->in.handle, DCESRV_HANDLE_ANY);
/* this causes the parameters samr_XXX_destroy() to be called by
the handle destroy code which destroys the state associated
with the handle */
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
ZERO_STRUCTP(r->out.handle);
@@ -327,14 +315,14 @@ static NTSTATUS samr_OpenDomain(struct dcesrv_call_state *dce_call, TALLOC_CTX *
}
d_state->access_mask = r->in.access_mask;
h_domain = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_DOMAIN);
h_domain = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_DOMAIN);
if (!h_domain) {
talloc_free(d_state);
return NT_STATUS_NO_MEMORY;
}
h_domain->data = d_state;
h_domain->destroy = samr_handle_destroy;
h_domain->data = talloc_steal(h_domain, d_state);
*r->out.domain_handle = h_domain->wire_handle;
return NT_STATUS_OK;
@@ -579,13 +567,12 @@ static NTSTATUS samr_CreateDomainGroup(struct dcesrv_call_state *dce_call, TALLO
}
/* create the policy handle */
g_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_GROUP);
g_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_GROUP);
if (!g_handle) {
return NT_STATUS_NO_MEMORY;
}
g_handle->data = a_state;
g_handle->destroy = samr_handle_destroy;
g_handle->data = talloc_steal(g_handle, a_state);
*r->out.group_handle = g_handle->wire_handle;
*r->out.rid = rid;
@@ -862,16 +849,12 @@ static NTSTATUS samr_CreateUser2(struct dcesrv_call_state *dce_call, TALLOC_CTX
}
/* create the policy handle */
u_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_USER);
u_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_USER);
if (!u_handle) {
return NT_STATUS_NO_MEMORY;
}
u_handle->data = a_state;
u_handle->destroy = samr_handle_destroy;
/* the domain state is in use one more time */
u_handle->data = talloc_steal(u_handle, a_state);
*r->out.user_handle = u_handle->wire_handle;
*r->out.access_granted = 0xf07ff; /* TODO: fix access mask calculations */
@@ -1095,12 +1078,11 @@ static NTSTATUS samr_CreateDomAlias(struct dcesrv_call_state *dce_call, TALLOC_C
}
/* create the policy handle */
a_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_ALIAS);
a_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_ALIAS);
if (a_handle == NULL)
return NT_STATUS_NO_MEMORY;
a_handle->data = a_state;
a_handle->destroy = samr_handle_destroy;
a_handle->data = talloc_steal(a_handle, a_state);
*r->out.alias_handle = a_handle->wire_handle;
*r->out.rid = rid;
@@ -1518,13 +1500,12 @@ static NTSTATUS samr_OpenGroup(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
}
/* create the policy handle */
g_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_GROUP);
g_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_GROUP);
if (!g_handle) {
return NT_STATUS_NO_MEMORY;
}
g_handle->data = a_state;
g_handle->destroy = samr_handle_destroy;
g_handle->data = talloc_steal(g_handle, a_state);
*r->out.group_handle = g_handle->wire_handle;
@@ -1993,13 +1974,12 @@ static NTSTATUS samr_OpenAlias(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
}
/* create the policy handle */
g_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_ALIAS);
g_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_ALIAS);
if (!g_handle) {
return NT_STATUS_NO_MEMORY;
}
g_handle->data = a_state;
g_handle->destroy = samr_handle_destroy;
g_handle->data = talloc_steal(g_handle, a_state);
*r->out.alias_handle = g_handle->wire_handle;
@@ -2426,13 +2406,12 @@ static NTSTATUS samr_OpenUser(struct dcesrv_call_state *dce_call, TALLOC_CTX *me
}
/* create the policy handle */
u_handle = dcesrv_handle_new(dce_call->conn, SAMR_HANDLE_USER);
u_handle = dcesrv_handle_new(dce_call->context, SAMR_HANDLE_USER);
if (!u_handle) {
return NT_STATUS_NO_MEMORY;
}
u_handle->data = a_state;
u_handle->destroy = samr_handle_destroy;
u_handle->data = talloc_steal(u_handle, a_state);
*r->out.user_handle = u_handle->wire_handle;

View File

@@ -186,26 +186,6 @@ static WERROR spoolss_EnumPrinters(struct dcesrv_call_state *dce_call, TALLOC_CT
}
/*
destroy connection state
*/
static void spoolss_OpenPrinter_close(struct spoolss_openprinter_state *c_state)
{
c_state->reference_count--;
if (c_state->reference_count == 0) {
talloc_destroy(c_state->mem_ctx);
}
}
/*
destroy an open connection. This closes the database connection
*/
static void spoolss_OpenPrinter_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
{
struct spoolss_openprinter_state *c_state = h->data;
spoolss_OpenPrinter_close(c_state);
}
/*
spoolss_OpenPrinter
*/
@@ -498,10 +478,7 @@ static WERROR spoolss_ClosePrinter(struct dcesrv_call_state *dce_call, TALLOC_CT
DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
/* this causes the callback s_XXX_destroy() to be called by
the handle destroy code which destroys the state associated
with the handle */
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
ZERO_STRUCTP(r->out.handle);
@@ -905,34 +882,24 @@ static WERROR spoolss_OpenPrinterEx_server(struct dcesrv_call_state *dce_call,
{
struct spoolss_openprinter_state *state;
struct dcesrv_handle *handle;
TALLOC_CTX *op_mem_ctx;
/* Check printername is our name */
if (!strequal(r->in.printername + 2, lp_netbios_name()))
return WERR_INVALID_PRINTER_NAME;
op_mem_ctx = talloc_init("spoolss_OpenPrinter");
if (!op_mem_ctx) {
return WERR_OK;
}
state = talloc_p(op_mem_ctx, struct spoolss_openprinter_state);
if (!state) {
return WERR_OK;
}
state->mem_ctx = op_mem_ctx;
handle = dcesrv_handle_new(dce_call->conn, SPOOLSS_HANDLE_SERVER);
handle = dcesrv_handle_new(dce_call->context, SPOOLSS_HANDLE_SERVER);
if (!handle) {
talloc_destroy(state->mem_ctx);
return WERR_NOMEM;
}
handle->data = state;
handle->destroy = spoolss_OpenPrinter_destroy;
state = talloc_p(handle, struct spoolss_openprinter_state);
if (!state) {
return WERR_OK;
}
handle->data = state;
state->reference_count = 1;
state->access_mask = r->in.access_mask;
*r->out.handle = handle->wire_handle;

View File

@@ -32,8 +32,6 @@ enum spoolss_handle {
state asscoiated with a spoolss_OpenPrinter{,Ex}() operation
*/
struct spoolss_openprinter_state {
int reference_count;
void *openprinter_ctx;
TALLOC_CTX *mem_ctx;
uint32_t access_mask;
};

View File

@@ -33,7 +33,7 @@ static NTSTATUS dcerpc_winreg_bind(struct dcesrv_call_state *dce_call, const str
struct registry_context *ctx;
reg_open_local(&ctx);
dce_call->conn->private = ctx;
dce_call->context->private = ctx;
return NT_STATUS_OK;
}
@@ -42,11 +42,11 @@ static NTSTATUS dcerpc_winreg_bind(struct dcesrv_call_state *dce_call, const str
static WERROR winreg_openhive (struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, uint32_t hkey, struct policy_handle **outh)
{
struct registry_context *ctx = dce_call->conn->private;
struct registry_context *ctx = dce_call->context->private;
struct dcesrv_handle *h;
WERROR error;
h = dcesrv_handle_new(dce_call->conn, HTYPE_REGKEY);
h = dcesrv_handle_new(dce_call->context, HTYPE_REGKEY);
error = reg_get_predefined_key(ctx, hkey, (struct registry_key **)&h->data);
if (!W_ERROR_IS_OK(error)) {
@@ -81,10 +81,9 @@ static WERROR winreg_CloseKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *me
{
struct dcesrv_handle *h;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
dcesrv_handle_destroy(dce_call->conn, h);
talloc_free(h);
return WERR_OK;
}
@@ -99,20 +98,18 @@ static WERROR winreg_CreateKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
struct dcesrv_handle *h, *newh;
WERROR error;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
newh = dcesrv_handle_new(dce_call->conn, HTYPE_REGKEY);
newh = dcesrv_handle_new(dce_call->context, HTYPE_REGKEY);
error = reg_key_add_name(newh, (struct registry_key *)h->data, r->in.key.name,
r->in.access_mask,
r->in.sec_desc?r->in.sec_desc->sd:NULL,
(struct registry_key **)&newh->data);
if (W_ERROR_IS_OK(error)) {
r->out.handle = &newh->wire_handle;
} else {
dcesrv_handle_destroy(dce_call->conn, newh);
talloc_free(newh);
}
return error;
@@ -128,8 +125,7 @@ static WERROR winreg_DeleteKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
struct dcesrv_handle *h;
WERROR result;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
if (W_ERROR_IS_OK(result)) {
return reg_key_del((struct registry_key *)h->data, r->in.key.name);
@@ -148,8 +144,7 @@ static WERROR winreg_DeleteValue(struct dcesrv_call_state *dce_call, TALLOC_CTX
struct dcesrv_handle *h;
struct registry_key *key;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
key = h->data;
@@ -166,8 +161,7 @@ static WERROR winreg_EnumKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem
struct dcesrv_handle *h;
struct registry_key *key;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
r->out.result = reg_key_get_subkey_by_index(mem_ctx, (struct registry_key *)h->data, r->in.enum_index, &key);
@@ -194,8 +188,7 @@ static WERROR winreg_EnumValue(struct dcesrv_call_state *dce_call, TALLOC_CTX *m
struct registry_value *value;
WERROR result;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
key = h->data;
@@ -224,8 +217,7 @@ static WERROR winreg_FlushKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *me
{
struct dcesrv_handle *h;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
return reg_key_flush(h->data);
}
@@ -239,8 +231,7 @@ static WERROR winreg_GetKeySecurity(struct dcesrv_call_state *dce_call, TALLOC_C
{
struct dcesrv_handle *h;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
return WERR_NOT_SUPPORTED;
}
@@ -275,10 +266,9 @@ static WERROR winreg_OpenKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem
struct dcesrv_handle *h, *newh;
WERROR result;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
newh = dcesrv_handle_new(dce_call->conn, HTYPE_REGKEY);
newh = dcesrv_handle_new(dce_call->context, HTYPE_REGKEY);
result = reg_open_key(newh, (struct registry_key *)h->data,
r->in.keyname.name, (struct registry_key **)&newh->data);
@@ -286,7 +276,7 @@ static WERROR winreg_OpenKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem
if (W_ERROR_IS_OK(result)) {
r->out.handle = &newh->wire_handle;
} else {
dcesrv_handle_destroy(dce_call->conn, newh);
talloc_free(newh);
}
return result;
@@ -303,8 +293,8 @@ static WERROR winreg_QueryInfoKey(struct dcesrv_call_state *dce_call, TALLOC_CTX
struct registry_key *k;
WERROR ret;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
k = h->data;
ret = reg_key_num_subkeys(k, &r->out.num_subkeys);
@@ -349,8 +339,7 @@ static WERROR winreg_QueryValue(struct dcesrv_call_state *dce_call, TALLOC_CTX *
struct registry_value *val;
WERROR result;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
key = h->data;
@@ -425,8 +414,7 @@ static WERROR winreg_SetValue(struct dcesrv_call_state *dce_call, TALLOC_CTX *me
struct registry_key *key;
WERROR result;
h = dcesrv_handle_fetch(dce_call->conn, r->in.handle, HTYPE_REGKEY);
DCESRV_CHECK_HANDLE(h);
DCESRV_PULL_HANDLE_FAULT(h, r->in.handle, HTYPE_REGKEY);
key = h->data;