summaryrefslogtreecommitdiff
path: root/source3/rpc_server/srv_pipe_hnd.c
diff options
context:
space:
mode:
Diffstat (limited to 'source3/rpc_server/srv_pipe_hnd.c')
-rw-r--r--source3/rpc_server/srv_pipe_hnd.c89
1 files changed, 61 insertions, 28 deletions
diff --git a/source3/rpc_server/srv_pipe_hnd.c b/source3/rpc_server/srv_pipe_hnd.c
index a371e48bfd..7ab2b3aec6 100644
--- a/source3/rpc_server/srv_pipe_hnd.c
+++ b/source3/rpc_server/srv_pipe_hnd.c
@@ -81,8 +81,10 @@ void init_rpc_pipe_hnd(void)
Pipes[i].rhdr.offset = 0;
Pipes[i].rdata.offset = 0;
- Pipes[i].max_rdata_len = 0;
- Pipes[i].hdr_offsets = 0;
+ Pipes[i].file_offset = 0;
+ Pipes[i].hdr_offsets = 0;
+ Pipes[i].frag_len_left = 0;
+ Pipes[i].next_frag_start = 0;
}
return;
@@ -110,8 +112,10 @@ int open_rpc_pipe_hnd(char *pipe_name, int cnum, uint16 vuid)
Pipes[i].rhdr.offset = 0;
Pipes[i].rdata.offset = 0;
- Pipes[i].max_rdata_len = 0;
- Pipes[i].hdr_offsets = 0;
+ Pipes[i].file_offset = 0;
+ Pipes[i].hdr_offsets = 0;
+ Pipes[i].frag_len_left = 0;
+ Pipes[i].next_frag_start = 0;
fstrcpy(Pipes[i].name, pipe_name);
@@ -134,7 +138,7 @@ int open_rpc_pipe_hnd(char *pipe_name, int cnum, uint16 vuid)
headers are interspersed with the data at regular intervals. by the time
this function is called, the start of the data could possibly have been
- read by an SMBtrans (max_rdata_len != 0).
+ read by an SMBtrans (file_offset != 0).
calling create_rpc_request() here is a fudge. the data should already
have been prepared into arrays of headers + data stream sections.
@@ -142,13 +146,14 @@ int open_rpc_pipe_hnd(char *pipe_name, int cnum, uint16 vuid)
****************************************************************************/
int read_pipe(uint16 pnum, char *data, uint32 pos, int n)
{
- int data_pos = pos;
+ int data_hdr_pos;
+ int data_pos;
pipes_struct *p = &Pipes[pnum - PIPE_HANDLE_OFFSET];
DEBUG(6,("read_pipe: %x", pnum));
if (VALID_PNUM(pnum - PIPE_HANDLE_OFFSET))
{
- DEBUG(6,("name: %s cnum: %d open: %s data_pos: %lx len: %lx",
+ DEBUG(6,("name: %s cnum: %d open: %s data_pos: %d len: %d",
p->name,
p->cnum,
BOOLSTR(p->open),
@@ -160,7 +165,6 @@ int read_pipe(uint16 pnum, char *data, uint32 pos, int n)
int num = 0;
int len = 0;
uint32 hdr_num = 0;
- uint32 rpc_frag_pos = 0;
DEBUG(6,("OK\n"));
@@ -170,29 +174,38 @@ int read_pipe(uint16 pnum, char *data, uint32 pos, int n)
return 0;
}
- DEBUG(6,("read_pipe: p: %p max_rdata_len: %d data_pos: %d num: %d\n",
- p, p->max_rdata_len, data_pos, num));
+ DEBUG(6,("read_pipe: p: %p file_offset: %d file_pos: %d\n",
+ p, p->file_offset, n));
+ DEBUG(6,("read_pipe: frag_len_left: %d next_frag_start: %d\n",
+ p->frag_len_left, p->next_frag_start));
/* the read request starts from where the SMBtrans2 left off. */
- data_pos += p->max_rdata_len;
-
- rpc_frag_pos = data_pos % p->hdr.frag_len;
-
- /* headers accumulate an offset */
- data_pos -= p->hdr_offsets;
+ data_pos = p->file_offset - p->hdr_offsets;
+ data_hdr_pos = p->file_offset;
len = mem_buf_len(p->rhdr.data);
num = len - (int)data_pos;
+ DEBUG(6,("read_pipe: len: %d num: %d n: %d\n", len, num, n));
+
if (num > n) num = n;
+ if (num <= 0)
+ {
+ DEBUG(5,("read_pipe: 0 or -ve data length\n"));
+ return 0;
+ }
if (!IS_BITS_SET_ALL(p->hdr.flags, RPC_FLG_LAST))
{
- DEBUG(5,("read_pipe: hdr_offsets: %d rpc_frag_pos: %d frag_len: %d\n",
- p->hdr_offsets, rpc_frag_pos, p->hdr.frag_len));
+ /* intermediate fragment - possibility of another header */
+
+ DEBUG(5,("read_pipe: frag_len: %d data_pos: %d data_hdr_pos: %d\n",
+ p->hdr.frag_len, data_pos, data_hdr_pos));
- if (rpc_frag_pos == 0)
+ if (data_hdr_pos == p->next_frag_start)
{
+ DEBUG(6,("read_pipe: next fragment header\n"));
+
/* this is subtracted from the total data bytes, later */
hdr_num = 0x18;
@@ -200,24 +213,44 @@ int read_pipe(uint16 pnum, char *data, uint32 pos, int n)
create_rpc_reply(p, data_pos, p->rdata.offset);
mem_buf_copy(data, p->rhdr.data, 0, 0x18);
- /* make room in data stream for header */
- p->hdr_offsets += 0x18;
data += 0x18;
+ p->frag_len_left = p->hdr.frag_len;
+ p->next_frag_start += p->hdr.frag_len;
+ p->hdr_offsets += 0x18;
- DEBUG(6,("read_pipe: hdr_offsets: %d\n", p->hdr_offsets));
+ /*DEBUG(6,("read_pipe: hdr_offsets: %d\n", p->hdr_offsets));*/
}
}
- if (num > 0)
+ if (num < hdr_num)
{
- DEBUG(6,("read_pipe: adjusted data_pos: %d num: %d\n",
- data_pos, num - hdr_num));
- mem_buf_copy(data, p->rhdr.data, data_pos, num - hdr_num);
+ DEBUG(5,("read_pipe: warning - data read only part of a header\n"));
+ }
+
+ DEBUG(6,("read_pipe: adjusted data_pos: %d num-hdr_num: %d\n",
+ data_pos, num - hdr_num));
+ mem_buf_copy(data, p->rhdr.data, data_pos, num - hdr_num);
+
+ data_pos += num;
+ data_hdr_pos += num;
+
+ if (hdr_num == 0x18 && num == 0x18)
+ {
+ DEBUG(6,("read_pipe: just header read\n"));
- return num;
+ /* advance to the next fragment */
+ p->frag_len_left -= 0x18;
}
+ else if (data_hdr_pos == p->next_frag_start)
+ {
+ DEBUG(6,("read_pipe: next fragment expected\n"));
+
+ /* advance to the next fragment */
+ }
+
+ p->file_offset += num;
- return 0;
+ return num;
}
else