summaryrefslogtreecommitdiff
path: root/source/smbd/reply.c
diff options
context:
space:
mode:
Diffstat (limited to 'source/smbd/reply.c')
-rw-r--r--source/smbd/reply.c300
1 files changed, 67 insertions, 233 deletions
diff --git a/source/smbd/reply.c b/source/smbd/reply.c
index a8f674183c5..ffa80aac870 100644
--- a/source/smbd/reply.c
+++ b/source/smbd/reply.c
@@ -42,7 +42,6 @@ extern BOOL short_case_preserve;
extern pstring sesssetup_user;
extern fstring myworkgroup;
extern int Client;
-extern int global_oplock_break;
/* this macro should always be used to extract an fnum (smb_fid) from
a packet to ensure chaining works correctly */
@@ -66,18 +65,18 @@ static void overflow_attack(int len)
****************************************************************************/
int reply_special(char *inbuf,char *outbuf)
{
- int outsize = 4;
- int msg_type = CVAL(inbuf,0);
- int msg_flags = CVAL(inbuf,1);
- pstring name1,name2;
- extern fstring remote_machine;
- extern fstring local_machine;
- char *p;
-
- *name1 = *name2 = 0;
-
- smb_setlen(outbuf,0);
-
+ int outsize = 4;
+ int msg_type = CVAL(inbuf,0);
+ int msg_flags = CVAL(inbuf,1);
+ pstring name1,name2;
+ extern fstring remote_machine;
+ extern fstring local_machine;
+ char *p;
+
+ *name1 = *name2 = 0;
+
+ smb_setlen(outbuf,0);
+
switch (msg_type) {
case 0x81: /* session request */
CVAL(outbuf,0) = 0x82;
@@ -122,15 +121,15 @@ int reply_special(char *inbuf,char *outbuf)
DEBUG(0,("Unexpected session response\n"));
break;
- case 0x85: /* session keepalive */
- default:
- return(0);
- }
-
+ case 0x85: /* session keepalive */
+ default:
+ return(0);
+ }
+
DEBUG(5,("%s init msg_type=0x%x msg_flags=0x%x\n",
timestring(),msg_type,msg_flags));
-
- return(outsize);
+
+ return(outsize);
}
@@ -252,7 +251,7 @@ int reply_tcon_and_X(char *inbuf,char *outbuf,int length,int bufsize)
if ((SVAL(inbuf,smb_vwv2) & 0x1) != 0)
close_cnum(SVAL(inbuf,smb_tid),vuid);
- if (passlen > MAX_PASSWORD_LENGTH) {
+ if (passlen > MAX_PASS_LEN) {
overflow_attack(passlen);
}
@@ -388,7 +387,7 @@ int reply_sesssetup_and_X(char *inbuf,char *outbuf,int length,int bufsize)
if (Protocol < PROTOCOL_NT1) {
smb_apasslen = SVAL(inbuf,smb_vwv7);
- if (smb_apasslen > MAX_PASSWORD_LENGTH)
+ if (smb_apasslen > MAX_PASS_LEN)
{
overflow_attack(smb_apasslen);
}
@@ -423,12 +422,12 @@ int reply_sesssetup_and_X(char *inbuf,char *outbuf,int length,int bufsize)
if (passlen1 != 24 && passlen2 != 24)
doencrypt = False;
- if (passlen1 > MAX_PASSWORD_LENGTH) {
+ if (passlen1 > MAX_PASS_LEN) {
overflow_attack(passlen1);
}
- passlen1 = MIN(passlen1, MAX_PASSWORD_LENGTH);
- passlen2 = MIN(passlen2, MAX_PASSWORD_LENGTH);
+ passlen1 = MIN(passlen1, MAX_PASS_LEN);
+ passlen2 = MIN(passlen2, MAX_PASS_LEN);
if(doencrypt) {
/* Save the lanman2 password and the NT md4 password. */
@@ -599,7 +598,7 @@ int reply_sesssetup_and_X(char *inbuf,char *outbuf,int length,int bufsize)
if (!done_sesssetup)
max_send = MIN(max_send,smb_bufsize);
- DEBUG(6,("Client requested max send size of %d\n", max_send));
+ DEBUG(5,(" Client requested max send size of %d\n", max_send));
done_sesssetup = True;
@@ -640,15 +639,6 @@ int reply_chkpth(char *inbuf,char *outbuf)
unix_ERR_class = ERRDOS;
unix_ERR_code = ERRbadpath;
}
-
- /* Ugly - NT specific hack - but needed (JRA) */
- if((errno == ENOTDIR) && (Protocol >= PROTOCOL_NT1) &&
- (get_remote_arch() == RA_WINNT))
- {
- unix_ERR_class = ERRDOS;
- unix_ERR_code = ERRbaddirectory;
- }
-
return(UNIXERROR(ERRDOS,ERRbadpath));
}
@@ -1111,8 +1101,6 @@ int reply_open(char *inbuf,char *outbuf)
int rmode=0;
struct stat sbuf;
BOOL bad_path = False;
- files_struct *fsp;
- int oplock_request = CORE_OPLOCK_REQUEST(inbuf);
cnum = SVAL(inbuf,smb_tid);
@@ -1137,12 +1125,9 @@ int reply_open(char *inbuf,char *outbuf)
unixmode = unix_mode(cnum,aARCH);
- open_file_shared(fnum,cnum,fname,share_mode,3,unixmode,
- oplock_request,&rmode,NULL);
-
- fsp = &Files[fnum];
+ open_file_shared(fnum,cnum,fname,share_mode,3,unixmode,&rmode,NULL);
- if (!fsp->open)
+ if (!Files[fnum].open)
{
if((errno == ENOENT) && bad_path)
{
@@ -1152,8 +1137,8 @@ int reply_open(char *inbuf,char *outbuf)
return(UNIXERROR(ERRDOS,ERRnoaccess));
}
- if (fstat(fsp->fd_ptr->fd,&sbuf) != 0) {
- close_file(fnum);
+ if (fstat(Files[fnum].fd_ptr->fd,&sbuf) != 0) {
+ close_file(fnum, 0);
return(ERROR(ERRDOS,ERRnoaccess));
}
@@ -1163,7 +1148,7 @@ int reply_open(char *inbuf,char *outbuf)
if (fmode & aDIR) {
DEBUG(3,("attempt to open a directory %s\n",fname));
- close_file(fnum);
+ close_file(fnum, 0);
return(ERROR(ERRDOS,ERRnoaccess));
}
@@ -1174,12 +1159,10 @@ int reply_open(char *inbuf,char *outbuf)
SIVAL(outbuf,smb_vwv4,size);
SSVAL(outbuf,smb_vwv6,rmode);
- if (oplock_request && lp_fake_oplocks(SNUM(cnum))) {
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+ if (lp_fake_oplocks(SNUM(cnum))) {
+ CVAL(outbuf,smb_flg) |= (CVAL(inbuf,smb_flg) & (1<<5));
}
- if(fsp->granted_oplock)
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
return(outsize);
}
@@ -1194,7 +1177,7 @@ int reply_open_and_X(char *inbuf,char *outbuf,int length,int bufsize)
int fnum = -1;
int smb_mode = SVAL(inbuf,smb_vwv3);
int smb_attr = SVAL(inbuf,smb_vwv5);
- BOOL oplock_request = EXTENDED_OPLOCK_REQUEST(inbuf);
+ BOOL oplock_request = BITSETW(inbuf+smb_vwv2,1);
#if 0
int open_flags = SVAL(inbuf,smb_vwv2);
int smb_sattr = SVAL(inbuf,smb_vwv4);
@@ -1206,7 +1189,6 @@ int reply_open_and_X(char *inbuf,char *outbuf,int length,int bufsize)
struct stat sbuf;
int smb_action = 0;
BOOL bad_path = False;
- files_struct *fsp;
/* If it's an IPC, pass off the pipe handler. */
if (IS_IPC(cnum))
@@ -1234,11 +1216,9 @@ int reply_open_and_X(char *inbuf,char *outbuf,int length,int bufsize)
unixmode = unix_mode(cnum,smb_attr | aARCH);
open_file_shared(fnum,cnum,fname,smb_mode,smb_ofun,unixmode,
- oplock_request, &rmode,&smb_action);
+ &rmode,&smb_action);
- fsp = &Files[fnum];
-
- if (!fsp->open)
+ if (!Files[fnum].open)
{
if((errno == ENOENT) && bad_path)
{
@@ -1248,8 +1228,8 @@ int reply_open_and_X(char *inbuf,char *outbuf,int length,int bufsize)
return(UNIXERROR(ERRDOS,ERRnoaccess));
}
- if (fstat(fsp->fd_ptr->fd,&sbuf) != 0) {
- close_file(fnum);
+ if (fstat(Files[fnum].fd_ptr->fd,&sbuf) != 0) {
+ close_file(fnum, 0);
return(ERROR(ERRDOS,ERRnoaccess));
}
@@ -1257,18 +1237,12 @@ int reply_open_and_X(char *inbuf,char *outbuf,int length,int bufsize)
fmode = dos_mode(cnum,fname,&sbuf);
mtime = sbuf.st_mtime;
if (fmode & aDIR) {
- close_file(fnum);
+ close_file(fnum, 0);
return(ERROR(ERRDOS,ERRnoaccess));
}
if (oplock_request && lp_fake_oplocks(SNUM(cnum))) {
- smb_action |= EXTENDED_OPLOCK_GRANTED;
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
- }
-
- if(fsp->granted_oplock) {
- smb_action |= EXTENDED_OPLOCK_GRANTED;
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+ smb_action |= (1<<15);
}
set_message(outbuf,15,0,True);
@@ -1303,7 +1277,7 @@ int reply_ulogoffX(char *inbuf,char *outbuf,int length,int bufsize)
int i;
for (i=0;i<MAX_OPEN_FILES;i++)
if (Files[i].uid == vuser->uid && Files[i].open) {
- close_file(i);
+ close_file(i, 0);
}
}
@@ -1330,8 +1304,6 @@ int reply_mknew(char *inbuf,char *outbuf)
mode_t unixmode;
int ofun = 0;
BOOL bad_path = False;
- files_struct *fsp;
- int oplock_request = CORE_OPLOCK_REQUEST(inbuf);
com = SVAL(inbuf,smb_com);
cnum = SVAL(inbuf,smb_tid);
@@ -1373,12 +1345,9 @@ int reply_mknew(char *inbuf,char *outbuf)
}
/* Open file in dos compatibility share mode. */
- open_file_shared(fnum,cnum,fname,(DENY_FCB<<4)|0xF, ofun, unixmode,
- oplock_request, NULL, NULL);
+ open_file_shared(fnum,cnum,fname,(DENY_FCB<<4)|0xF, ofun, unixmode, NULL, NULL);
- fsp = &Files[fnum];
-
- if (!fsp->open)
+ if (!Files[fnum].open)
{
if((errno == ENOENT) && bad_path)
{
@@ -1391,13 +1360,10 @@ int reply_mknew(char *inbuf,char *outbuf)
outsize = set_message(outbuf,1,0,True);
SSVAL(outbuf,smb_vwv0,fnum);
- if (oplock_request && lp_fake_oplocks(SNUM(cnum))) {
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+ if (lp_fake_oplocks(SNUM(cnum))) {
+ CVAL(outbuf,smb_flg) |= (CVAL(inbuf,smb_flg) & (1<<5));
}
-
- if(fsp->granted_oplock)
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
-
+
DEBUG(2,("new file %s\n",fname));
DEBUG(3,("%s mknew %s fd=%d fnum=%d cnum=%d dmode=%d umode=%o\n",timestring(),fname,Files[fnum].fd_ptr->fd,fnum,cnum,createmode,unixmode));
@@ -1418,8 +1384,6 @@ int reply_ctemp(char *inbuf,char *outbuf)
int createmode;
mode_t unixmode;
BOOL bad_path = False;
- files_struct *fsp;
- int oplock_request = CORE_OPLOCK_REQUEST(inbuf);
cnum = SVAL(inbuf,smb_tid);
createmode = SVAL(inbuf,smb_vwv0);
@@ -1447,12 +1411,9 @@ int reply_ctemp(char *inbuf,char *outbuf)
/* Open file in dos compatibility share mode. */
/* We should fail if file exists. */
- open_file_shared(fnum,cnum,fname2,(DENY_FCB<<4)|0xF, 0x10, unixmode,
- oplock_request, NULL, NULL);
+ open_file_shared(fnum,cnum,fname2,(DENY_FCB<<4)|0xF, 0x10, unixmode, NULL, NULL);
- fsp = &Files[fnum];
-
- if (!fsp->open)
+ if (!Files[fnum].open)
{
if((errno == ENOENT) && bad_path)
{
@@ -1467,13 +1428,10 @@ int reply_ctemp(char *inbuf,char *outbuf)
CVAL(smb_buf(outbuf),0) = 4;
strcpy(smb_buf(outbuf) + 1,fname2);
- if (oplock_request && lp_fake_oplocks(SNUM(cnum))) {
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+ if (lp_fake_oplocks(SNUM(cnum))) {
+ CVAL(outbuf,smb_flg) |= (CVAL(inbuf,smb_flg) & (1<<5));
}
- if(fsp->granted_oplock)
- CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
-
DEBUG(2,("created temp file %s\n",fname2));
DEBUG(3,("%s ctemp %s fd=%d fnum=%d cnum=%d dmode=%d umode=%o\n",timestring(),fname2,Files[fnum].fd_ptr->fd,fnum,cnum,createmode,unixmode));
@@ -1621,22 +1579,6 @@ int reply_readbraw(char *inbuf, char *outbuf)
int fd;
char *fname;
-#ifdef USE_OPLOCKS
- /*
- * Special check if an oplock break has been issued
- * and the readraw request croses on the wire, we must
- * return a zero length response here.
- */
-
- if(global_oplock_break)
- {
- _smb_setlen(header,0);
- transfer_file(0,Client,0,header,4,0);
- DEBUG(5,("readbraw - oplock break finished\n"));
- return -1;
- }
-#endif
-
cnum = SVAL(inbuf,smb_tid);
fnum = GETFNUM(inbuf,smb_vwv0);
@@ -2248,7 +2190,7 @@ int reply_close(char *inbuf,char *outbuf)
/* try and set the date */
set_filetime(Files[fnum].name,mtime);
- close_file(fnum);
+ close_file(fnum, 1);
/* We have a cached error */
if(eclass || err)
@@ -2295,7 +2237,7 @@ int reply_writeclose(char *inbuf,char *outbuf)
set_filetime(Files[fnum].name,mtime);
- close_file(fnum);
+ close_file(fnum, 1);
DEBUG(3,("%s writeclose fnum=%d cnum=%d num=%d wrote=%d (numopen=%d)\n",
timestring(),fnum,cnum,numtowrite,nwritten,
@@ -2492,8 +2434,7 @@ int reply_printopen(char *inbuf,char *outbuf)
return(ERROR(ERRDOS,ERRnoaccess));
/* Open for exclusive use, write only. */
- open_file_shared(fnum,cnum,fname2,(DENY_ALL<<4)|1, 0x12, unix_mode(cnum,0),
- 0, NULL, NULL);
+ open_file_shared(fnum,cnum,fname2,(DENY_ALL<<4)|1, 0x12, unix_mode(cnum,0), NULL, NULL);
if (!Files[fnum].open)
return(UNIXERROR(ERRDOS,ERRnoaccess));
@@ -2527,7 +2468,7 @@ int reply_printclose(char *inbuf,char *outbuf)
if (!CAN_PRINT(cnum))
return(ERROR(ERRDOS,ERRnoaccess));
- close_file(fnum);
+ close_file(fnum, 1);
DEBUG(3,("%s printclose fd=%d fnum=%d cnum=%d\n",timestring(),Files[fnum].fd_ptr->fd,fnum,cnum));
@@ -2695,66 +2636,6 @@ int reply_mkdir(char *inbuf,char *outbuf)
return(outsize);
}
-/****************************************************************************
-Static function used by reply_rmdir to delete an entire directory
-tree recursively.
-****************************************************************************/
-static BOOL recursive_rmdir(char *directory)
-{
- char *dname = NULL;
- BOOL ret = False;
- void *dirptr = OpenDir(-1, directory, False);
-
- if(dirptr == NULL)
- return True;
-
- while((dname = ReadDirName(dirptr)))
- {
- pstring fullname;
- struct stat st;
-
- if((strcmp(dname, ".") == 0) || (strcmp(dname, "..")==0))
- continue;
-
- /* Construct the full name. */
- if(strlen(directory) + strlen(dname) + 1 >= sizeof(fullname))
- {
- errno = ENOMEM;
- ret = True;
- break;
- }
- strcpy(fullname, directory);
- strcat(fullname, "/");
- strcat(fullname, dname);
-
- if(sys_lstat(fullname, &st) != 0)
- {
- ret = True;
- break;
- }
-
- if(st.st_mode & S_IFDIR)
- {
- if(recursive_rmdir(fullname)!=0)
- {
- ret = True;
- break;
- }
- if(sys_rmdir(fullname) != 0)
- {
- ret = True;
- break;
- }
- }
- else if(sys_unlink(fullname) != 0)
- {
- ret = True;
- break;
- }
- }
- CloseDir(dirptr);
- return ret;
-}
/****************************************************************************
reply to a rmdir
@@ -2823,15 +2704,10 @@ int reply_rmdir(char *inbuf,char *outbuf)
if(sys_lstat(fullname, &st) != 0)
break;
if(st.st_mode & S_IFDIR)
- {
- if(lp_recursive_veto_delete(SNUM(cnum)))
{
- if(recursive_rmdir(fullname) != 0)
+ if(sys_rmdir(fullname) != 0)
break;
}
- if(sys_rmdir(fullname) != 0)
- break;
- }
else if(sys_unlink(fullname) != 0)
break;
}
@@ -3155,7 +3031,7 @@ static BOOL copy_file(char *src,char *dest1,int cnum,int ofun,
fnum1 = find_free_file();
if (fnum1<0) return(False);
open_file_shared(fnum1,cnum,src,(DENY_NONE<<4),
- 1,0,0,&Access,&action);
+ 1,0,&Access,&action);
if (!Files[fnum1].open) return(False);
@@ -3164,14 +3040,14 @@ static BOOL copy_file(char *src,char *dest1,int cnum,int ofun,
fnum2 = find_free_file();
if (fnum2<0) {
- close_file(fnum1);
+ close_file(fnum1, 0);
return(False);
}
open_file_shared(fnum2,cnum,dest,(DENY_NONE<<4)|1,
- ofun,st.st_mode,0,&Access,&action);
+ ofun,st.st_mode,&Access,&action);
if (!Files[fnum2].open) {
- close_file(fnum1);
+ close_file(fnum1, 0);
return(False);
}
@@ -3182,8 +3058,8 @@ static BOOL copy_file(char *src,char *dest1,int cnum,int ofun,
if (st.st_size)
ret = transfer_file(Files[fnum1].fd_ptr->fd,Files[fnum2].fd_ptr->fd,st.st_size,NULL,0,0);
- close_file(fnum1);
- close_file(fnum2);
+ close_file(fnum1, 0);
+ close_file(fnum2, 0);
return(ret == st.st_size);
}
@@ -3370,10 +3246,7 @@ int reply_setdir(char *inbuf,char *outbuf)
int reply_lockingX(char *inbuf,char *outbuf,int length,int bufsize)
{
int fnum = GETFNUM(inbuf,smb_vwv2);
- unsigned char locktype = CVAL(inbuf,smb_vwv3);
-#if 0
- unsigned char oplocklevel = CVAL(inbuf,smb_vwv3+1);
-#endif /* USE_OPLOCKS */
+ uint16 locktype = SVAL(inbuf,smb_vwv3);
uint16 num_ulocks = SVAL(inbuf,smb_vwv6);
uint16 num_locks = SVAL(inbuf,smb_vwv7);
uint32 count, offset;
@@ -3390,50 +3263,6 @@ int reply_lockingX(char *inbuf,char *outbuf,int length,int bufsize)
CHECK_ERROR(fnum);
data = smb_buf(inbuf);
-
-#ifdef USE_OPLOCKS
- /* Check if this is an oplock break on a file
- we have granted an oplock on.
- */
- if((locktype == LOCKING_ANDX_OPLOCK_RELEASE) &&
- (num_ulocks == 0) && (num_locks == 0) &&
- (CVAL(inbuf,smb_vwv0) == 0xFF))
- {
- share_lock_token token;
- files_struct *fsp = &Files[fnum];
- uint32 dev = fsp->fd_ptr->dev;
- uint32 inode = fsp->fd_ptr->inode;
-
- DEBUG(5,("reply_lockingX: oplock break reply from client for fnum = %d\n",
- fnum));
- /*
- * Make sure we have granted an oplock on this file.
- */
- if(!fsp->granted_oplock)
- {
- DEBUG(0,("reply_lockingX: Error : oplock break from client for fnum = %d and \
-no oplock granted on this file.\n", fnum));
- return ERROR(ERRDOS,ERRlock);
- }
-
- /* Remove the oplock flag from the sharemode. */
- lock_share_entry(fsp->cnum, dev, inode, &token);
- if(remove_share_oplock( fnum, token)==False)
- {
- DEBUG(0,("reply_lockingX: failed to remove share oplock for fnum %d, \
-dev = %x, inode = %x\n", fnum, dev, inode));
- unlock_share_entry(fsp->cnum, dev, inode, token);
- return -1;
- }
- unlock_share_entry(fsp->cnum, dev, inode, token);
-
- /* Clear the granted flag and return. */
-
- fsp->granted_oplock = False;
- return -1;
- }
-#endif /* USE_OPLOCKS */
-
/* Data now points at the beginning of the list
of smb_unlkrng structs */
for(i = 0; i < (int)num_ulocks; i++) {
@@ -3468,7 +3297,7 @@ dev = %x, inode = %x\n", fnum, dev, inode));
set_message(outbuf,2,0,True);
DEBUG(3,("%s lockingX fnum=%d cnum=%d type=%d num_locks=%d num_ulocks=%d\n",
- timestring(),fnum,cnum,(unsigned int)locktype,num_locks,num_ulocks));
+ timestring(),fnum,cnum,locktype,num_locks,num_ulocks));
chain_fnum = fnum;
@@ -3821,3 +3650,8 @@ int reply_getattrE(char *inbuf,char *outbuf)
return(outsize);
}
+
+
+
+
+