From: Jeremy Allison Date: Tue, 8 Apr 2008 04:11:21 +0000 (-0700) Subject: Rewrite the wrap checks to deal with gcc 4.x optimisations. X-Git-Tag: samba-3.0.29~1165 X-Git-Url: http://git.samba.org/?a=commitdiff_plain;h=1261d7f713fedb312dfcfdd58c7d5b45e8185ba7;p=samba.git Rewrite the wrap checks to deal with gcc 4.x optimisations. Jeremy. --- diff --git a/source/smbd/ipc.c b/source/smbd/ipc.c index 6e5ff9f0359..f7b7c3132bd 100644 --- a/source/smbd/ipc.c +++ b/source/smbd/ipc.c @@ -434,6 +434,7 @@ int reply_trans(connection_struct *conn, char *inbuf,char *outbuf, unsigned int dscnt = SVAL(inbuf, smb_dscnt); unsigned int psoff = SVAL(inbuf, smb_psoff); unsigned int pscnt = SVAL(inbuf, smb_pscnt); + unsigned int av_size = size-4; struct trans_state *state; NTSTATUS result; @@ -489,11 +490,17 @@ int reply_trans(connection_struct *conn, char *inbuf,char *outbuf, } /* null-terminate the slack space */ memset(&state->data[state->total_data], 0, 100); - if ((dsoff+dscnt < dsoff) || (dsoff+dscnt < dscnt)) + + if (dscnt > state->total_data || + dsoff+dscnt < dsoff) { goto bad_param; - if ((smb_base(inbuf)+dsoff+dscnt > inbuf + size) || - (smb_base(inbuf)+dsoff+dscnt < smb_base(inbuf))) + } + + if (dsoff > av_size || + dscnt > av_size || + dsoff+dscnt > av_size) { goto bad_param; + } memcpy(state->data,smb_base(inbuf)+dsoff,dscnt); } @@ -512,11 +519,17 @@ int reply_trans(connection_struct *conn, char *inbuf,char *outbuf, } /* null-terminate the slack space */ memset(&state->param[state->total_param], 0, 100); - if ((psoff+pscnt < psoff) || (psoff+pscnt < pscnt)) + + if (pscnt > state->total_param || + psoff+pscnt < psoff) { goto bad_param; - if ((smb_base(inbuf)+psoff+pscnt > inbuf + size) || - (smb_base(inbuf)+psoff+pscnt < smb_base(inbuf))) + } + + if (psoff > av_size || + pscnt > av_size || + psoff+pscnt > av_size) { goto bad_param; + } memcpy(state->param,smb_base(inbuf)+psoff,pscnt); } @@ -600,6 +613,7 @@ int reply_transs(connection_struct *conn, char *inbuf,char *outbuf, { int outsize = 0; unsigned int pcnt,poff,dcnt,doff,pdisp,ddisp; + unsigned int av_size = size-4; struct trans_state *state; NTSTATUS result; @@ -643,34 +657,38 @@ int reply_transs(connection_struct *conn, char *inbuf,char *outbuf, goto bad_param; if (pcnt) { - if (pdisp+pcnt > state->total_param) - goto bad_param; - if ((pdisp+pcnt < pdisp) || (pdisp+pcnt < pcnt)) - goto bad_param; - if (pdisp > state->total_param) - goto bad_param; - if ((smb_base(inbuf) + poff + pcnt > inbuf + size) || - (smb_base(inbuf) + poff + pcnt < smb_base(inbuf))) + if (pdisp > state->total_param || + pcnt > state->total_param || + pdisp+pcnt > state->total_param || + pdisp+pcnt < pdisp) { goto bad_param; - if (state->param + pdisp < state->param) + } + + if (poff > av_size || + pcnt > av_size || + poff+pcnt > av_size || + poff+pcnt < poff) { goto bad_param; + } memcpy(state->param+pdisp,smb_base(inbuf)+poff, pcnt); } if (dcnt) { - if (ddisp+dcnt > state->total_data) - goto bad_param; - if ((ddisp+dcnt < ddisp) || (ddisp+dcnt < dcnt)) - goto bad_param; - if (ddisp > state->total_data) - goto bad_param; - if ((smb_base(inbuf) + doff + dcnt > inbuf + size) || - (smb_base(inbuf) + doff + dcnt < smb_base(inbuf))) - goto bad_param; - if (state->data + ddisp < state->data) + if (ddisp > state->total_data || + dcnt > state->total_data || + ddisp+dcnt > state->total_data || + ddisp+dcnt < ddisp) { + goto bad_param; + } + + if (ddisp > av_size || + dcnt > av_size || + ddisp+dcnt > av_size || + ddisp+dcnt < ddisp) { goto bad_param; + } memcpy(state->data+ddisp, smb_base(inbuf)+doff, dcnt); diff --git a/source/smbd/nttrans.c b/source/smbd/nttrans.c index 45563b4a4f6..b40ea9edca1 100644 --- a/source/smbd/nttrans.c +++ b/source/smbd/nttrans.c @@ -2978,7 +2978,8 @@ int reply_nttrans(connection_struct *conn, uint32 psoff = IVAL(inbuf,smb_nt_ParameterOffset); uint32 dscnt = IVAL(inbuf,smb_nt_DataCount); uint32 dsoff = IVAL(inbuf,smb_nt_DataOffset); - + uint32 av_size = size-4; + uint16 function_code = SVAL( inbuf, smb_nt_Function); NTSTATUS result; struct trans_state *state; @@ -3049,11 +3050,17 @@ int reply_nttrans(connection_struct *conn, END_PROFILE(SMBnttrans); return(ERROR_DOS(ERRDOS,ERRnomem)); } - if ((dsoff+dscnt < dsoff) || (dsoff+dscnt < dscnt)) + + if (dscnt > state->total_data || + dsoff+dscnt < dsoff) { goto bad_param; - if ((smb_base(inbuf)+dsoff+dscnt > inbuf + size) || - (smb_base(inbuf)+dsoff+dscnt < smb_base(inbuf))) + } + + if (dsoff > av_size || + dscnt > av_size || + dsoff+dscnt > av_size) { goto bad_param; + } memcpy(state->data,smb_base(inbuf)+dsoff,dscnt); } @@ -3069,11 +3076,17 @@ int reply_nttrans(connection_struct *conn, END_PROFILE(SMBnttrans); return(ERROR_DOS(ERRDOS,ERRnomem)); } - if ((psoff+pscnt < psoff) || (psoff+pscnt < pscnt)) + + if (pscnt > state->total_param || + psoff+pscnt < psoff) { goto bad_param; - if ((smb_base(inbuf)+psoff+pscnt > inbuf + size) || - (smb_base(inbuf)+psoff+pscnt < smb_base(inbuf))) + } + + if (psoff > av_size || + pscnt > av_size || + psoff+pscnt > av_size) { goto bad_param; + } memcpy(state->param,smb_base(inbuf)+psoff,pscnt); } @@ -3144,7 +3157,8 @@ int reply_nttranss(connection_struct *conn, char *inbuf,char *outbuf, int size,int bufsize) { int outsize = 0; - unsigned int pcnt,poff,dcnt,doff,pdisp,ddisp; + uint32_t pcnt,poff,dcnt,doff,pdisp,ddisp; + uint32_t av_size = size-4; struct trans_state *state; START_PROFILE(SMBnttranss); @@ -3188,34 +3202,38 @@ int reply_nttranss(connection_struct *conn, char *inbuf,char *outbuf, goto bad_param; if (pcnt) { - if (pdisp+pcnt > state->total_param) - goto bad_param; - if ((pdisp+pcnt < pdisp) || (pdisp+pcnt < pcnt)) + if (pdisp > state->total_param || + pcnt > state->total_param || + pdisp+pcnt > state->total_param || + pdisp+pcnt < pdisp) { goto bad_param; - if (pdisp > state->total_param) - goto bad_param; - if ((smb_base(inbuf) + poff + pcnt > inbuf + size) || - (smb_base(inbuf) + poff + pcnt < smb_base(inbuf))) - goto bad_param; - if (state->param + pdisp < state->param) + } + + if (poff > av_size || + pcnt > av_size || + poff+pcnt > av_size || + poff+pcnt < poff) { goto bad_param; + } memcpy(state->param+pdisp,smb_base(inbuf)+poff, pcnt); } if (dcnt) { - if (ddisp+dcnt > state->total_data) - goto bad_param; - if ((ddisp+dcnt < ddisp) || (ddisp+dcnt < dcnt)) + if (ddisp > state->total_data || + dcnt > state->total_data || + ddisp+dcnt > state->total_data || + ddisp+dcnt < ddisp) { goto bad_param; - if (ddisp > state->total_data) - goto bad_param; - if ((smb_base(inbuf) + doff + dcnt > inbuf + size) || - (smb_base(inbuf) + doff + dcnt < smb_base(inbuf))) - goto bad_param; - if (state->data + ddisp < state->data) + } + + if (ddisp > av_size || + dcnt > av_size || + ddisp+dcnt > av_size || + ddisp+dcnt < ddisp) { goto bad_param; + } memcpy(state->data+ddisp, smb_base(inbuf)+doff, dcnt); diff --git a/source/smbd/trans2.c b/source/smbd/trans2.c index a60f306c7b1..1401a5b4c60 100644 --- a/source/smbd/trans2.c +++ b/source/smbd/trans2.c @@ -6583,6 +6583,7 @@ int reply_trans2(connection_struct *conn, char *inbuf,char *outbuf, unsigned int psoff = SVAL(inbuf, smb_psoff); unsigned int pscnt = SVAL(inbuf, smb_pscnt); unsigned int tran_call = SVAL(inbuf, smb_setup0); + unsigned int av_size = size-4; struct trans_state *state; NTSTATUS result; @@ -6664,11 +6665,17 @@ int reply_trans2(connection_struct *conn, char *inbuf,char *outbuf, END_PROFILE(SMBtrans2); return(ERROR_DOS(ERRDOS,ERRnomem)); } - if ((dsoff+dscnt < dsoff) || (dsoff+dscnt < dscnt)) - goto bad_param; - if ((smb_base(inbuf)+dsoff+dscnt > inbuf + size) || - (smb_base(inbuf)+dsoff+dscnt < smb_base(inbuf))) + + if (dscnt > state->total_data || + dsoff+dscnt < dsoff) { goto bad_param; + } + + if (dsoff > av_size || + dscnt > av_size || + dsoff+dscnt > av_size) { + goto bad_param; + } memcpy(state->data,smb_base(inbuf)+dsoff,dscnt); } @@ -6685,11 +6692,17 @@ int reply_trans2(connection_struct *conn, char *inbuf,char *outbuf, END_PROFILE(SMBtrans2); return(ERROR_DOS(ERRDOS,ERRnomem)); } - if ((psoff+pscnt < psoff) || (psoff+pscnt < pscnt)) + + if (pscnt > state->total_param || + psoff+pscnt < psoff) { goto bad_param; - if ((smb_base(inbuf)+psoff+pscnt > inbuf + size) || - (smb_base(inbuf)+psoff+pscnt < smb_base(inbuf))) + } + + if (psoff > av_size || + pscnt > av_size || + psoff+pscnt > av_size) { goto bad_param; + } memcpy(state->param,smb_base(inbuf)+psoff,pscnt); } @@ -6738,6 +6751,7 @@ int reply_transs2(connection_struct *conn, { int outsize = 0; unsigned int pcnt,poff,dcnt,doff,pdisp,ddisp; + unsigned int av_size = size-4; struct trans_state *state; START_PROFILE(SMBtranss2); @@ -6780,34 +6794,38 @@ int reply_transs2(connection_struct *conn, goto bad_param; if (pcnt) { - if (pdisp+pcnt > state->total_param) - goto bad_param; - if ((pdisp+pcnt < pdisp) || (pdisp+pcnt < pcnt)) - goto bad_param; - if (pdisp > state->total_param) + if (pdisp > state->total_param || + pcnt > state->total_param || + pdisp+pcnt > state->total_param || + pdisp+pcnt < pdisp) { goto bad_param; - if ((smb_base(inbuf) + poff + pcnt > inbuf + size) || - (smb_base(inbuf) + poff + pcnt < smb_base(inbuf))) - goto bad_param; - if (state->param + pdisp < state->param) + } + + if (poff > av_size || + pcnt > av_size || + poff+pcnt > av_size || + poff+pcnt < poff) { goto bad_param; + } memcpy(state->param+pdisp,smb_base(inbuf)+poff, pcnt); } if (dcnt) { - if (ddisp+dcnt > state->total_data) - goto bad_param; - if ((ddisp+dcnt < ddisp) || (ddisp+dcnt < dcnt)) + if (ddisp > state->total_data || + dcnt > state->total_data || + ddisp+dcnt > state->total_data || + ddisp+dcnt < ddisp) { goto bad_param; - if (ddisp > state->total_data) - goto bad_param; - if ((smb_base(inbuf) + doff + dcnt > inbuf + size) || - (smb_base(inbuf) + doff + dcnt < smb_base(inbuf))) - goto bad_param; - if (state->data + ddisp < state->data) + } + + if (ddisp > av_size || + dcnt > av_size || + ddisp+dcnt > av_size || + ddisp+dcnt < ddisp) { goto bad_param; + } memcpy(state->data+ddisp, smb_base(inbuf)+doff, dcnt);