1
0
mirror of https://github.com/samba-team/samba.git synced 2024-12-23 17:34:34 +03:00

s3-dceprc: Improve dcerpc_guess_sizes() interface

Make it possible to pass in the NDR padding size so that theoretically
client and server code can decide to use a different alignment.

Pass in the header length as a parameter so that this function can be used for
different type of packets.

Make sure padding size will not make the fragment exceed the maximum length.

Calculate padding taking in account the header length.
This commit is contained in:
Simo Sorce 2010-07-30 13:12:35 -04:00
parent 3469fbc5e4
commit 4c64e4d4af
3 changed files with 30 additions and 20 deletions

View File

@ -140,7 +140,8 @@ NTSTATUS dcerpc_pull_dcerpc_auth(TALLOC_CTX *mem_ctx,
struct dcerpc_auth *r,
bool bigendian);
NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
size_t data_left, size_t max_xmit_frag,
size_t header_len, size_t data_left,
size_t max_xmit_frag, size_t pad_alignment,
size_t *data_to_send, size_t *frag_len,
size_t *auth_len, size_t *pad_len);
NTSTATUS dcerpc_add_auth_footer(struct pipe_auth_data *auth,

View File

@ -246,20 +246,23 @@ NTSTATUS dcerpc_pull_dcerpc_auth(TALLOC_CTX *mem_ctx,
* auth token and pad lengths.
*
* @param auth The pipe_auth_data structure for this pipe.
* @param header_len The length of the packet header
* @param data_left The data left in the send buffer
* @param data_to_send The max data we will send in the pdu
* @param frag_len The total length of the fragment
* @param auth_len The length of the auth trailer
* @param pad_len The padding to be applied
* @param max_xmit_frag The max fragment size.
* @param pad_alignment The NDR padding size.
* @param data_to_send [out] The max data we will send in the pdu
* @param frag_len [out] The total length of the fragment
* @param auth_len [out] The length of the auth trailer
* @param pad_len [out] The padding to be applied
*
* @return A NT Error status code.
*/
NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
size_t data_left, size_t max_xmit_frag,
size_t header_len, size_t data_left,
size_t max_xmit_frag, size_t pad_alignment,
size_t *data_to_send, size_t *frag_len,
size_t *auth_len, size_t *pad_len)
{
size_t data_space;
size_t max_len;
size_t mod_len;
struct gse_context *gse_ctx;
@ -273,11 +276,11 @@ NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
case DCERPC_AUTH_LEVEL_NONE:
case DCERPC_AUTH_LEVEL_CONNECT:
case DCERPC_AUTH_LEVEL_PACKET:
data_space = max_xmit_frag - DCERPC_REQUEST_LENGTH;
*data_to_send = MIN(data_space, data_left);
max_len = max_xmit_frag - header_len;
*data_to_send = MIN(max_len, data_left);
*pad_len = 0;
*auth_len = 0;
*frag_len = DCERPC_REQUEST_LENGTH + *data_to_send;
*frag_len = header_len + *data_to_send;
return NT_STATUS_OK;
case DCERPC_AUTH_LEVEL_PRIVACY:
@ -294,9 +297,7 @@ NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
/* Sign/seal case, calculate auth and pad lengths */
max_len = max_xmit_frag
- DCERPC_REQUEST_LENGTH
- DCERPC_AUTH_TRAILER_LENGTH;
max_len = max_xmit_frag - header_len - DCERPC_AUTH_TRAILER_LENGTH;
/* Treat the same for all authenticated rpc requests. */
switch (auth->auth_type) {
@ -349,16 +350,22 @@ NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
return NT_STATUS_INVALID_PARAMETER;
}
data_space = max_len - *auth_len;
max_len -= *auth_len;
*data_to_send = MIN(data_space, data_left);
mod_len = *data_to_send % CLIENT_NDR_PADDING_SIZE;
*data_to_send = MIN(max_len, data_left);
mod_len = (header_len + *data_to_send) % pad_alignment;
if (mod_len) {
*pad_len = CLIENT_NDR_PADDING_SIZE - mod_len;
*pad_len = pad_alignment - mod_len;
} else {
*pad_len = 0;
}
*frag_len = DCERPC_REQUEST_LENGTH + *data_to_send + *pad_len
if (*data_to_send + *pad_len > max_len) {
*data_to_send -= pad_alignment;
}
*frag_len = header_len + *data_to_send + *pad_len
+ DCERPC_AUTH_TRAILER_LENGTH + *auth_len;
return NT_STATUS_OK;

View File

@ -1286,8 +1286,10 @@ static NTSTATUS prepare_next_frag(struct rpc_api_pipe_req_state *state,
data_left = state->req_data->length - state->req_data_sent;
status = dcerpc_guess_sizes(state->cli->auth, data_left,
status = dcerpc_guess_sizes(state->cli->auth,
DCERPC_REQUEST_LENGTH, data_left,
state->cli->max_xmit_frag,
CLIENT_NDR_PADDING_SIZE,
&data_sent_thistime,
&frag_len, &auth_len, &pad_len);
if (!NT_STATUS_IS_OK(status)) {