diff options
-rw-r--r-- | source/include/includes.h | 4 | ||||
-rw-r--r-- | source/include/proto.h | 4 | ||||
-rw-r--r-- | source/include/smb.h | 16 | ||||
-rw-r--r-- | source/locking/locking.c | 271 | ||||
-rw-r--r-- | source/smbd/server.c | 123 |
5 files changed, 230 insertions, 188 deletions
diff --git a/source/include/includes.h b/source/include/includes.h index e66ceb2d70c..2329553d234 100644 --- a/source/include/includes.h +++ b/source/include/includes.h @@ -1194,6 +1194,10 @@ it works and getting lots of bug reports */ #define QSORT_CAST (int (*)()) #endif +#ifndef INADDR_LOOPBACK +#define INADDR_LOOPBACK 0x7f000001 +#endif /* INADDR_LOOPBACK */ + /* this is a rough check to see if this machine has a lstat() call. it is not guaranteed to work */ #if !(defined(S_ISLNK) || defined(S_IFLNK)) diff --git a/source/include/proto.h b/source/include/proto.h index 9c6cccb3708..46a96a8bef7 100644 --- a/source/include/proto.h +++ b/source/include/proto.h @@ -299,13 +299,13 @@ BOOL unlock_share_entry(int cnum, uint32 dev, uint32 inode, share_lock_token tok int get_share_modes(int cnum, share_lock_token token, uint32 dev, uint32 inode, min_share_mode_entry **old_shares); void del_share_mode(share_lock_token token, int fnum); -BOOL set_share_mode(share_lock_token token, int fnum); +BOOL set_share_mode(share_lock_token token, int fnum, uint16 port); BOOL lock_share_entry(int cnum, uint32 dev, uint32 inode, share_lock_token *ptok); BOOL unlock_share_entry(int cnum, uint32 dev, uint32 inode, share_lock_token token); int get_share_modes(int cnum, share_lock_token token, uint32 dev, uint32 inode, min_share_mode_entry **old_shares); void del_share_mode(share_lock_token token, int fnum); -BOOL set_share_mode(share_lock_token token,int fnum); +BOOL set_share_mode(share_lock_token token,int fnum, uint16 port); /*The following definitions come from mangle.c */ diff --git a/source/include/smb.h b/source/include/smb.h index 05f73f7f45e..a67b3c02c96 100644 --- a/source/include/smb.h +++ b/source/include/smb.h @@ -433,9 +433,6 @@ struct interface struct in_addr ip; struct in_addr bcast; struct in_addr nmask; - char *name; - size_t mtu; /* may be useful in future... */ - short flags; }; /* share mode record pointed to in shared memory hash bucket */ @@ -455,6 +452,9 @@ typedef struct { smb_shm_offset_t next_share_mode_entry; int pid; +#ifdef USE_OPLOCKS + uint16 op_port; +#endif /* USE_OPLOCKS */ int share_mode; struct timeval time; } share_mode_entry; @@ -463,6 +463,9 @@ typedef struct typedef struct { int pid; +#ifdef USE_OPLOCKS + uint16 op_port; +#endif /* USE_OPLOCKS */ int share_mode; struct timeval time; } min_share_mode_entry; @@ -487,8 +490,13 @@ struct connect_record time_t start; }; - +#ifndef LOCKING_VERSION +#ifdef USE_OPLOCKS +#define LOCKING_VERSION 4 +#else /* USE_OPLOCKS */ #define LOCKING_VERSION 3 +#endif /* USE_OPLOCKS */ +#endif /* LOCKING_VERSION */ /* these are useful macros for checking validity of handles */ #define VALID_FNUM(fnum) (((fnum) >= 0) && ((fnum) < MAX_OPEN_FILES)) diff --git a/source/locking/locking.c b/source/locking/locking.c index 760d21a05d8..76046763940 100644 --- a/source/locking/locking.c +++ b/source/locking/locking.c @@ -46,7 +46,7 @@ BOOL is_locked(int fnum,int cnum,uint32 count,uint32 offset) return(False); return(fcntl_lock(Files[fnum].fd_ptr->fd,F_GETLK,offset,count, - (Files[fnum].can_write?F_WRLCK:F_RDLCK))); + (Files[fnum].can_write?F_WRLCK:F_RDLCK))); } @@ -68,7 +68,7 @@ BOOL do_lock(int fnum,int cnum,uint32 count,uint32 offset,int *eclass,uint32 *ec if (Files[fnum].can_lock && OPEN_FNUM(fnum) && (Files[fnum].cnum == cnum)) ok = fcntl_lock(Files[fnum].fd_ptr->fd,F_SETLK,offset,count, - (Files[fnum].can_write?F_WRLCK:F_RDLCK)); + (Files[fnum].can_write?F_WRLCK:F_RDLCK)); if (!ok) { *eclass = ERRDOS; @@ -182,37 +182,37 @@ int get_share_modes(int cnum, share_lock_token token, uint32 dev, uint32 inode, file_prev_p = file_scanner_p; while(file_scanner_p) { - if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) - { - found = True; - break; - } - else - { - file_prev_p = file_scanner_p ; - file_scanner_p = (share_mode_record *)smb_shm_offset2addr( - file_scanner_p->next_offset); - } + if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) + { + found = True; + break; + } + else + { + file_prev_p = file_scanner_p ; + file_scanner_p = (share_mode_record *)smb_shm_offset2addr( + file_scanner_p->next_offset); + } } if(!found) { - DEBUG(5,("get_share_modes (FAST_SHARE_MODES): no entry for \ + DEBUG(5,("get_share_modes (FAST_SHARE_MODES): no entry for \ file dev = %d, ino = %d in hash_bucket %d\n", dev, inode, hash_entry)); - return (0); + return (0); } if(file_scanner_p->locking_version != LOCKING_VERSION) { - DEBUG(0,("ERROR:get_share_modes (FAST_SHARE_MODES): Deleting old share mode \ + DEBUG(0,("ERROR:get_share_modes (FAST_SHARE_MODES): Deleting old share mode \ record due to old locking version %d for file dev = %d, inode = %d in hash \ bucket %d",file_scanner_p->locking_version, dev, inode, hash_entry)); - if(file_prev_p == file_scanner_p) - mode_array[hash_entry] = file_scanner_p->next_offset; - else - file_prev_p->next_offset = file_scanner_p->next_offset; - smb_shm_free(smb_shm_addr2offset(file_scanner_p)); - return (0); + if(file_prev_p == file_scanner_p) + mode_array[hash_entry] = file_scanner_p->next_offset; + else + file_prev_p->next_offset = file_scanner_p->next_offset; + smb_shm_free(smb_shm_addr2offset(file_scanner_p)); + return (0); } /* Allocate the old_shares array */ @@ -283,6 +283,9 @@ bucket (number of entries now = %d)\n", */ share_array[num_entries_copied].pid = entry_scanner_p->pid; share_array[num_entries_copied].share_mode = entry_scanner_p->share_mode; +#ifdef USE_OPLOCKS + share_array[num_entries_copied].op_port = entry_scanner_p->op_port; +#endif /* USE_OPLOCKS */ memcpy(&share_array[num_entries_copied].time, &entry_scanner_p->time, sizeof(struct timeval)); num_entries_copied++; @@ -361,17 +364,17 @@ void del_share_mode(share_lock_token token, int fnum) while(file_scanner_p) { - if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) - { - found = True; - break; - } - else - { - file_prev_p = file_scanner_p ; - file_scanner_p = (share_mode_record *) - smb_shm_offset2addr(file_scanner_p->next_offset); - } + if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) + { + found = True; + break; + } + else + { + file_prev_p = file_scanner_p ; + file_scanner_p = (share_mode_record *) + smb_shm_offset2addr(file_scanner_p->next_offset); + } } if(!found) @@ -383,20 +386,20 @@ inode %d in hash bucket %d\n", dev, inode, hash_entry)); if(file_scanner_p->locking_version != LOCKING_VERSION) { - DEBUG(0,("ERROR: del_share_modes (FAST_SHARE_MODES): Deleting old share mode \ + DEBUG(0,("ERROR: del_share_modes (FAST_SHARE_MODES): Deleting old share mode \ record due to old locking version %d for file dev %d, inode %d hash bucket %d\n", file_scanner_p->locking_version, dev, inode, hash_entry )); - if(file_prev_p == file_scanner_p) - mode_array[hash_entry] = file_scanner_p->next_offset; - else - file_prev_p->next_offset = file_scanner_p->next_offset; - smb_shm_free(smb_shm_addr2offset(file_scanner_p)); - return; + if(file_prev_p == file_scanner_p) + mode_array[hash_entry] = file_scanner_p->next_offset; + else + file_prev_p->next_offset = file_scanner_p->next_offset; + smb_shm_free(smb_shm_addr2offset(file_scanner_p)); + return; } found = False; entry_scanner_p = (share_mode_entry*)smb_shm_offset2addr( - file_scanner_p->share_mode_entries); + file_scanner_p->share_mode_entries); entry_prev_p = entry_scanner_p; while(entry_scanner_p) { @@ -441,15 +444,15 @@ for dev = %d, ino = %d, hashbucket %d\n", file_scanner_p->num_share_mode_entries /* If we deleted the last share mode entry then remove the share mode record. */ if(file_scanner_p->num_share_mode_entries == 0) - { + { DEBUG(2,("del_share_modes (FAST_SHARE_MODES): num entries = 0, deleting share_mode \ record dev = %d, inode = %d in hash bucket %d\n", dev, inode, hash_entry)); if(file_prev_p == file_scanner_p) - mode_array[hash_entry] = file_scanner_p->next_offset; + mode_array[hash_entry] = file_scanner_p->next_offset; else - file_prev_p->next_offset = file_scanner_p->next_offset; + file_prev_p->next_offset = file_scanner_p->next_offset; smb_shm_free(smb_shm_addr2offset(file_scanner_p)); - } + } } else { @@ -461,7 +464,7 @@ dev = %d, inode = %d in hash bucket %d\n", dev, inode, hash_entry)); /******************************************************************* set the share mode of a file. Return False on fail, True on success. ********************************************************************/ -BOOL set_share_mode(share_lock_token token, int fnum) +BOOL set_share_mode(share_lock_token token, int fnum, uint16 port) { files_struct *fs_p = &Files[fnum]; int32 dev, inode; @@ -493,17 +496,17 @@ BOOL set_share_mode(share_lock_token token, int fnum) while(file_scanner_p) { - if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) - { - found = True; - break; - } - else - { - file_prev_p = file_scanner_p ; - file_scanner_p = (share_mode_record *) - smb_shm_offset2addr(file_scanner_p->next_offset); - } + if( (file_scanner_p->st_dev == dev) && (file_scanner_p->st_ino == inode) ) + { + found = True; + break; + } + else + { + file_prev_p = file_scanner_p ; + file_scanner_p = (share_mode_record *) + smb_shm_offset2addr(file_scanner_p->next_offset); + } } if(!found) @@ -552,6 +555,9 @@ inode %d in hash bucket %d\n", fs_p->name, dev, inode, hash_entry)); new_entry_p->pid = getpid(); new_entry_p->share_mode = fs_p->share_mode; +#ifdef USE_OPLOCKS + new_entry_p->op_port = port; +#endif /* USE_OPLOCKS */ memcpy( (char *)&new_entry_p->time, (char *)&fs_p->open_time, sizeof(struct timeval)); /* Chain onto the share_mode_record */ @@ -751,9 +757,10 @@ for share file %s (%s)\n", fname, strerror(errno))); return -1; } - if (IVAL(buf,0) != LOCKING_VERSION) { + if (IVAL(buf,SMF_VERSION_OFFSET) != LOCKING_VERSION) { DEBUG(0,("ERROR: read_share_file: share file %s has incorrect \ -locking version (was %d, should be %d).\n",fname, IVAL(buf,0), LOCKING_VERSION)); +locking version (was %d, should be %d).\n",fname, + IVAL(buf,SMF_VERSION_OFFSET), LOCKING_VERSION)); if(buf) free(buf); delete_share_file(cnum, fname); @@ -762,13 +769,13 @@ locking version (was %d, should be %d).\n",fname, IVAL(buf,0), LOCKING_VERSION)) /* Sanity check for file contents */ size = sb.st_size; - size -= 10; /* Remove the header */ + size -= SMF_HEADER_LENGTH; /* Remove the header */ /* Remove the filename component. */ - size -= SVAL(buf, 8); + size -= SVAL(buf, SMF_FILENAME_LEN_OFFSET); - /* The remaining size must be a multiple of 16 - error if not. */ - if((size % 16) != 0) + /* The remaining size must be a multiple of SMF_ENTRY_LENGTH - error if not. */ + if((size % SMF_ENTRY_LENGTH) != 0) { DEBUG(0,("ERROR: read_share_file: share file %s is an incorrect length - \ deleting it.\n", fname)); @@ -813,7 +820,7 @@ int get_share_modes(int cnum, share_lock_token token, uint32 dev, uint32 inode, 4 - tv_usec 8 - share_mode 12 - pid - + 16 - oplock port (if oplocks in use) - 2 bytes. */ share_name(cnum, dev, inode, fname); @@ -828,7 +835,7 @@ int get_share_modes(int cnum, share_lock_token token, uint32 dev, uint32 inode, if(new_file == True) return 0; - num_entries = IVAL(buf,4); + num_entries = IVAL(buf,SMF_NUM_ENTRIES_OFFSET); DEBUG(5,("get_share_modes: share file %s has %d share mode entries.\n", fname, num_entries)); @@ -863,26 +870,29 @@ for share file %d\n", num_entries, fname)); } num_entries_copied = 0; - base = buf + 10 + SVAL(buf,8); + base = buf + SMF_HEADER_LENGTH + SVAL(buf,SMF_FILENAME_LEN_OFFSET); for( i = 0; i < num_entries; i++) { int pid; - char *p = base + (i*16); + char *p = base + (i*SMF_ENTRY_LENGTH); - pid = IVAL(p,12); + pid = IVAL(p,SME_PID_OFFSET); if(!process_exists(pid)) { DEBUG(0,("get_share_modes: process %d no longer exists and \ it left a share mode entry with mode 0x%X in share file %s\n", - pid, IVAL(p,8), fname)); + pid, IVAL(p,SME_SHAREMODE_OFFSET), fname)); continue; } - share_array[num_entries_copied].time.tv_sec = IVAL(p,0); - share_array[num_entries_copied].time.tv_usec = IVAL(p,4); - share_array[num_entries_copied].share_mode = IVAL(p,8); + share_array[num_entries_copied].time.tv_sec = IVAL(p,SME_SEC_OFFSET); + share_array[num_entries_copied].time.tv_usec = IVAL(p,SME_USEC_OFFSET); + share_array[num_entries_copied].share_mode = IVAL(p,SME_SHAREMODE_OFFSET); share_array[num_entries_copied].pid = pid; +#ifdef USE_OPLOCKS + share_array[num_entries_copied].op_port = SVAL(p,SME_PORT_OFFSET); +#endif /* USE_OPLOCKS */ num_entries_copied++; } @@ -918,18 +928,21 @@ position 0 for share mode file %s (%s)\n", fname, strerror(errno))); return 0; } - SIVAL(buf, 4, num_entries_copied); + SIVAL(buf, SMF_NUM_ENTRIES_OFFSET, num_entries_copied); for( i = 0; i < num_entries_copied; i++) { - char *p = base + (i*16); - - SIVAL(p,12,share_array[i].pid); - SIVAL(p,8,share_array[i].share_mode); - SIVAL(p,0,share_array[i].time.tv_sec); - SIVAL(p,4,share_array[i].time.tv_usec); + char *p = base + (i*SMF_ENTRY_LENGTH); + + SIVAL(p,SME_PID_OFFSET,share_array[i].pid); + SIVAL(p,SME_SHAREMODE_OFFSET,share_array[i].share_mode); + SIVAL(p,SME_SEC_OFFSET,share_array[i].time.tv_sec); + SIVAL(p,SME_USEC_OFFSET,share_array[i].time.tv_usec); +#ifdef USE_OPLOCKS + SIVAL(p,SME_PORT_OFFSET,share_array[i].op_port); +#endif /* USE_OPLOCKS */ } - newsize = (base - buf) + (16*num_entries_copied); + newsize = (base - buf) + (SMF_ENTRY_LENGTH*num_entries_copied); if(write(fd, buf, newsize) != newsize) { DEBUG(0,("ERROR: get_share_modes: failed to re-write share \ @@ -999,7 +1012,7 @@ void del_share_mode(share_lock_token token, int fnum) return; } - num_entries = IVAL(buf,4); + num_entries = IVAL(buf,SMF_NUM_ENTRIES_OFFSET); DEBUG(5,("del_share_mode: share file %s has %d share mode entries.\n", fname, num_entries)); @@ -1029,14 +1042,16 @@ for share file %d\n", num_entries, fname)); we have set - delete it. */ - base = buf + 10 + SVAL(buf,8); + base = buf + SMF_HEADER_LENGTH + SVAL(buf,SMF_FILENAME_LEN_OFFSET); for(i = 0; i < num_entries; i++) { - char *p = base + (i*16); + char *p = base + (i*SMF_ENTRY_LENGTH); - if((IVAL(p,0) != fs_p->open_time.tv_sec) || (IVAL(p,4) != fs_p->open_time.tv_usec) || - (IVAL(p,8) != fs_p->share_mode) || (IVAL(p,12) != pid)) + if((IVAL(p,SME_SEC_OFFSET) != fs_p->open_time.tv_sec) || + (IVAL(p,SME_USEC_OFFSET) != fs_p->open_time.tv_usec) || + (IVAL(p,SME_SHAREMODE_OFFSET) != fs_p->share_mode) || + (IVAL(p,SME_PID_OFFSET) != pid)) continue; DEBUG(5,("del_share_mode: deleting entry number %d (of %d) from the share file %s\n", @@ -1044,7 +1059,7 @@ for share file %d\n", num_entries, fname)); /* Remove this entry. */ if(i != num_entries - 1) - memcpy(p, p + 16, (num_entries - i - 1)*16); + memcpy(p, p + SMF_ENTRY_LENGTH, (num_entries - i - 1)*SMF_ENTRY_LENGTH); deleted = True; break; @@ -1059,7 +1074,7 @@ for share file %d\n", num_entries, fname)); } num_entries--; - SIVAL(buf,4, num_entries); + SIVAL(buf,SMF_NUM_ENTRIES_OFFSET, num_entries); if(num_entries == 0) { @@ -1074,23 +1089,23 @@ for share file %d\n", num_entries, fname)); /* Re-write the file - and truncate it at the correct point. */ if(lseek(fd, 0, SEEK_SET) != 0) - { - DEBUG(0,("ERROR: del_share_mode: lseek failed to reset to \ + { + DEBUG(0,("ERROR: del_share_mode: lseek failed to reset to \ position 0 for share mode file %s (%s)\n", fname, strerror(errno))); - if(buf) - free(buf); - return; - } + if(buf) + free(buf); + return; + } - newsize = (base - buf) + (16*num_entries); + newsize = (base - buf) + (SMF_ENTRY_LENGTH*num_entries); if(write(fd, buf, newsize) != newsize) - { - DEBUG(0,("ERROR: del_share_mode: failed to re-write share \ + { + DEBUG(0,("ERROR: del_share_mode: failed to re-write share \ mode file %s (%s)\n", fname, strerror(errno))); - if(buf) - free(buf); - return; - } + if(buf) + free(buf); + return; + } /* Now truncate the file at this point. */ if(ftruncate(fd, newsize) != 0) { @@ -1105,7 +1120,7 @@ mode file %s to size %d (%s)\n", fname, newsize, strerror(errno))); /******************************************************************* set the share mode of a file ********************************************************************/ -BOOL set_share_mode(share_lock_token token,int fnum) +BOOL set_share_mode(share_lock_token token,int fnum, uint16 port) { files_struct *fs_p = &Files[fnum]; pstring fname; @@ -1133,9 +1148,10 @@ BOOL set_share_mode(share_lock_token token,int fnum) int size = sb.st_size; /* Allocate space for the file plus one extra entry */ - if((buf = (char *)malloc(sb.st_size + 16)) == NULL) + if((buf = (char *)malloc(sb.st_size + SMF_ENTRY_LENGTH)) == NULL) { - DEBUG(0,("set_share_mode: malloc for file size %d fail !\n", sb.st_size + 16)); + DEBUG(0,("set_share_mode: malloc for file size %d fail !\n", + sb.st_size + SMF_ENTRY_LENGTH)); return False; } @@ -1157,20 +1173,21 @@ to 0 for share file %s (%s)\n", fname, strerror(errno))); return False; } - if (IVAL(buf,0) != LOCKING_VERSION) + if (IVAL(buf,SMF_VERSION_OFFSET) != LOCKING_VERSION) { DEBUG(0,("ERROR: set_share_mode: share file %s has incorrect \ -locking version (was %d, should be %d).\n",fname, IVAL(buf,0), LOCKING_VERSION)); +locking version (was %d, should be %d).\n",fname, IVAL(buf,SMF_VERSION_OFFSET), + LOCKING_VERSION)); if(buf) free(buf); delete_share_file(fs_p->cnum, fname); return False; } - size -= (10 + SVAL(buf, 8)); /* Remove the header */ + size -= (SMF_HEADER_LENGTH + SVAL(buf, SMF_FILENAME_LEN_OFFSET)); /* Remove the header */ - /* The remaining size must be a multiple of 16 - error if not. */ - if((size % 16) != 0) + /* The remaining size must be a multiple of SMF_ENTRY_LENGTH - error if not. */ + if((size % SMF_ENTRY_LENGTH) != 0) { DEBUG(0,("ERROR: set_share_mode: share file %s is an incorrect length - \ deleting it.\n", fname)); @@ -1184,28 +1201,32 @@ deleting it.\n", fname)); else { /* New file - just use a single_entry. */ - if((buf = (char *)malloc(10 + strlen(fs_p->name) + 1 + 16)) == NULL) + if((buf = (char *)malloc(SMF_HEADER_LENGTH + + strlen(fs_p->name) + 1 + SMF_ENTRY_LENGTH)) == NULL) { DEBUG(0,("ERROR: set_share_mode: malloc failed for single entry.\n")); return False; } - SIVAL(buf,0,LOCKING_VERSION); - SIVAL(buf,4,0); - SSVAL(buf,8,strlen(fs_p->name) + 1); - strcpy(buf + 10, fs_p->name); + SIVAL(buf,SMF_VERSION_OFFSET,LOCKING_VERSION); + SIVAL(buf,SMF_NUM_ENTRIES_OFFSET,0); + SSVAL(buf,SMF_FILENAME_LEN_OFFSET,strlen(fs_p->name) + 1); + strcpy(buf + SMF_HEADER_LENGTH, fs_p->name); } - num_entries = IVAL(buf,4); - header_size = 10 + SVAL(buf,8); - p = buf + header_size + (num_entries * 16); - SIVAL(p,0,fs_p->open_time.tv_sec); - SIVAL(p,4,fs_p->open_time.tv_usec); - SIVAL(p,8,fs_p->share_mode); - SIVAL(p,12,pid); + num_entries = IVAL(buf,SMF_NUM_ENTRIES_OFFSET); + header_size = SMF_HEADER_LENGTH + SVAL(buf,SMF_FILENAME_LEN_OFFSET); + p = buf + header_size + (num_entries * SMF_ENTRY_LENGTH); + SIVAL(p,SME_SEC_OFFSET,fs_p->open_time.tv_sec); + SIVAL(p,SME_USEC_OFFSET,fs_p->open_time.tv_usec); + SIVAL(p,SME_SHAREMODE_OFFSET,fs_p->share_mode); + SIVAL(p,SME_PID_OFFSET,pid); +#ifdef USE_OPLOCKS + SSVAL(p,SME_PORT_OFFSET,port); +#endif /* USE_OPLOCKS */ num_entries++; - SIVAL(buf,4,num_entries); + SIVAL(buf,SMF_NUM_ENTRIES_OFFSET,num_entries); if(lseek(fd, 0, SEEK_SET) != 0) { @@ -1216,7 +1237,8 @@ deleting it.\n", fname)); return False; } - if (write(fd,buf,header_size + (num_entries*16)) != (header_size + (num_entries*16))) + if (write(fd,buf,header_size + (num_entries*SMF_ENTRY_LENGTH)) != + (header_size + (num_entries*SMF_ENTRY_LENGTH))) { DEBUG(2,("ERROR: set_share_mode: Failed to write share file %s - \ deleting it (%s).\n",fname, strerror(errno))); @@ -1227,10 +1249,11 @@ deleting it (%s).\n",fname, strerror(errno))); } /* Now truncate the file at this point - just for safety. */ - if(ftruncate(fd, header_size + (16*num_entries))!= 0) + if(ftruncate(fd, header_size + (SMF_ENTRY_LENGTH*num_entries))!= 0) { DEBUG(0,("ERROR: set_share_mode: failed to ftruncate share \ -mode file %s to size %d (%s)\n", fname, header_size + (16*num_entries), strerror(errno))); +mode file %s to size %d (%s)\n", fname, header_size + (SMF_ENTRY_LENGTH*num_entries), + strerror(errno))); if(buf) free(buf); return False; diff --git a/source/smbd/server.c b/source/smbd/server.c index 110d31b3029..3b24ba5ce90 100644 --- a/source/smbd/server.c +++ b/source/smbd/server.c @@ -87,7 +87,7 @@ static int num_connections_open = 0; #ifdef USE_OPLOCKS /* Oplock ipc UDP socket. */ int oplock_sock = -1; -int oplock_port = -1; +uint16 oplock_port = 0; #endif /* USE_OPLOCKS */ extern fstring remote_machine; @@ -1720,7 +1720,7 @@ void open_file_shared(int fnum,int cnum,char *fname,int share_mode,int ofun, file (which expects the share_mode_entry to be there). */ if (lp_share_modes(SNUM(cnum))) - set_share_mode(token, fnum); + set_share_mode(token, fnum, 0); if ((flags2&O_TRUNC) && file_existed) truncate_unless_locked(fnum,cnum,token,&share_locked); @@ -2275,9 +2275,13 @@ static BOOL open_oplock_ipc() DEBUG(3,("open_oplock_ipc: opening loopback UDP socket.\n")); /* Open a lookback UDP socket on a random port. */ - oplock_sock = open_socket_in(SOCK_DGRAM, 0, 0,interpret_addr("127.0.0.1")); + oplock_sock = open_socket_in(SOCK_DGRAM, 0, 0, htonl(INADDR_LOOPBACK)); if (oplock_sock == -1) + { + DEBUG(0,("open_oplock_ipc: Failed to get local UDP socket for \ +address %x. Error was %s\n", INADDR_LOOPBACK, strerror(errno))); return(False); + } /* Find out the transient UDP port we have been allocated. */ if(getsockname(oplock_sock, (struct sockaddr *)&sock_name, &name_len)<0) @@ -2299,13 +2303,13 @@ static BOOL open_oplock_ipc() static BOOL process_local_message(int oplock_sock, char *buffer, int buf_size) { int32 msg_len; - int16 port; - struct in_addr from; + int16 from_port; + struct in_addr from_addr; char *msg_start; msg_len = IVAL(buffer,0); - port = SVAL(buffer,4); - memcpy((char *)&from, &buffer[6], sizeof(struct in_addr)); + from_port = SVAL(buffer,4); + memcpy((char *)&from_addr, &buffer[6], sizeof(struct in_addr)); msg_start = &buffer[6 + sizeof(struct in_addr)]; @@ -2318,6 +2322,13 @@ static BOOL process_local_message(int oplock_sock, char *buffer, int buf_size) } /* Validate message from address (must be localhost). */ + if(from_addr.s_addr != htonl(INADDR_LOOPBACK)) + { + DEBUG(0,("process_local_message: invalid from address \ +(was %x should be 127.0.0.1\n", from_addr.s_addr)); + return False; + } + return True; } #endif /* USE_OPLOCKS */ @@ -3994,14 +4005,57 @@ int construct_reply(char *inbuf,char *outbuf,int size,int bufsize) return(outsize); } +/**************************************************************************** + process an smb from the client - split out from the process() code so + it can be used by the oplock break code. +****************************************************************************/ + +static void process_smb(char *InBuffer, char *OutBuffer) +{ + extern int Client; + static int trans_num = 0; + + int msg_type = CVAL(InBuffer,0); + int32 len = smb_len(InBuffer); + int nread = len + 4; + + DEBUG(6,("got message type 0x%x of len 0x%x\n",msg_type,len)); + DEBUG(3,("%s Transaction %d of length %d\n",timestring(),trans_num,nread)); + +#ifdef WITH_VTP + if(trans_num == 1 && VT_Check(InBuffer)) + { + VT_Process(); + return; + } +#endif + + if (msg_type == 0) + show_msg(InBuffer); + + nread = construct_reply(InBuffer,OutBuffer,nread,max_send); + + if(nread > 0) + { + if (CVAL(OutBuffer,0) == 0) + show_msg(OutBuffer); + + if (nread != smb_len(OutBuffer) + 4) + { + DEBUG(0,("ERROR: Invalid message response size! %d %d\n", + nread, smb_len(OutBuffer))); + } + else + send_smb(Client,OutBuffer); + } + trans_num++; +} /**************************************************************************** process commands from the client ****************************************************************************/ static void process(void) { - static int trans_num = 0; - int nread; extern int Client; InBuffer = (char *)malloc(BUFFER_SIZE + SAFETY_MARGIN); @@ -4025,10 +4079,6 @@ static void process(void) while (True) { - int32 len; - int msg_type; - int msg_flags; - int type; int deadtime = lp_deadtime()*60; int counter; int last_keepalive=0; @@ -4048,7 +4098,7 @@ static void process(void) for (counter=SMBD_SELECT_LOOP; #ifdef USE_OPLOCKS !receive_message_or_smb(Client,oplock_sock, - InBuffer,SMBD_SELECT_LOOP*1000,&got_smb); + InBuffer,BUFFER_SIZE,SMBD_SELECT_LOOP*1000,&got_smb); #else /* USE_OPLOCKS */ !receive_smb(Client,InBuffer,SMBD_SELECT_LOOP*1000); #endif /* USE_OPLOCKS */ @@ -4136,54 +4186,11 @@ static void process(void) #ifdef USE_OPLOCKS if(got_smb) - { #endif /* USE_OPLOCKS */ - msg_type = CVAL(InBuffer,0); - msg_flags = CVAL(InBuffer,1); - type = CVAL(InBuffer,smb_com); - - len = smb_len(InBuffer); - - DEBUG(6,("got message type 0x%x of len 0x%x\n",msg_type,len)); - - nread = len + 4; - - DEBUG(3,("%s Transaction %d of length %d\n",timestring(),trans_num,nread)); - -#ifdef WITH_VTP - if(trans_num == 1 && VT_Check(InBuffer)) - { - VT_Process(); - return; - } -#endif - - - if (msg_type == 0) - show_msg(InBuffer); - - nread = construct_reply(InBuffer,OutBuffer,nread,max_send); - - if(nread > 0) - { - if (CVAL(OutBuffer,0) == 0) - show_msg(OutBuffer); - - if (nread != smb_len(OutBuffer) + 4) - { - DEBUG(0,("ERROR: Invalid message response size! %d %d\n", - nread, smb_len(OutBuffer))); - } - else - send_smb(Client,OutBuffer); - } - trans_num++; + process_smb(InBuffer, OutBuffer); #ifdef USE_OPLOCKS - } else - { process_local_message(oplock_sock, InBuffer, BUFFER_SIZE); - } #endif /* USE_OPLOCKS */ } } |