diff options
author | Jeremy Allison <jra@samba.org> | 2000-04-27 22:23:04 +0000 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2000-04-27 22:23:04 +0000 |
commit | 36db78fedad935aaa689d52d7f58e075f1f71812 (patch) | |
tree | 24811c595378d882fd0737203667cfe468d199c5 | |
parent | 3d3c50326ba7f32ebb2fc683a3410dc0d1f18cdc (diff) | |
download | samba-36db78fedad935aaa689d52d7f58e075f1f71812.tar.gz samba-36db78fedad935aaa689d52d7f58e075f1f71812.tar.bz2 samba-36db78fedad935aaa689d52d7f58e075f1f71812.zip |
Fixed subtle unlocking bug when a file is closed. We need to store the
smbpid used when a file was opened in the files_struct. Else we use
the wrong global_smbpid when we are closing the file and trying to
remove the brl locks - this causes the brl locks to be left when the
file is closed as the samba_context check fails.
Jeremy.
(This used to be commit 2746e5602e493e5b022764b4b839eb4d2f14363b)
-rw-r--r-- | source3/include/smb.h | 1 | ||||
-rw-r--r-- | source3/locking/brlock.c | 37 | ||||
-rw-r--r-- | source3/locking/locking.c | 11 | ||||
-rw-r--r-- | source3/smbd/open.c | 4 | ||||
-rw-r--r-- | source3/smbd/process.c | 2 | ||||
-rw-r--r-- | source3/utils/torture.c | 2 |
6 files changed, 39 insertions, 18 deletions
diff --git a/source3/include/smb.h b/source3/include/smb.h index 6a3964e0f3..e4415e7d22 100644 --- a/source3/include/smb.h +++ b/source3/include/smb.h @@ -482,6 +482,7 @@ typedef struct files_struct SMB_OFF_T size; mode_t mode; uint16 vuid; + int smbpid; write_bmpx_struct *wbmpx_ptr; write_cache *wcp; struct timeval open_time; diff --git a/source3/locking/brlock.c b/source3/locking/brlock.c index 68daa7e0bb..ed1f73df5e 100644 --- a/source3/locking/brlock.c +++ b/source3/locking/brlock.c @@ -210,6 +210,9 @@ struct unlock_list *brl_unlock_list(TALLOC_CTX *ctx, struct unlock_list *ulhead, * Quit if the list is deleted. */ + DEBUG(10,("brl_unlock_list: curr: start=%.0f,size=%.0f\n", + (double)ulhead->start, (double)ulhead->size )); + for (i=0; i<num_locks && ulhead; i++) { struct lock_struct *lock = &locks[i]; @@ -227,9 +230,8 @@ struct unlock_list *brl_unlock_list(TALLOC_CTX *ctx, struct unlock_list *ulhead, for (ul_curr = ulhead; ul_curr;) { - DEBUG(10,("brl_unlock_list: curr: start=%.0f,size=%.0f \ -lock: start=%.0f,size=%.0f\n", (double)ul_curr->start, (double)ul_curr->size, - (double)lock->start, (double)lock->size )); + DEBUG(10,("brl_unlock_list: lock: start=%.0f,size=%.0f:", + (double)lock->start, (double)lock->size )); if ( (ul_curr->start >= (lock->start + lock->size)) || (lock->start > (ul_curr->start + ul_curr->size))) { @@ -248,7 +250,7 @@ OR.... +---------+ **********************************************/ - DEBUG(10,("brl_unlock_list: no overlap case.\n" )); + DEBUG(10,("no overlap case.\n" )); ul_curr = ul_curr->next; @@ -270,7 +272,7 @@ OR.... /* Save the next pointer */ struct unlock_list *ul_next = ul_curr->next; - DEBUG(10,("brl_unlock_list: delete case.\n" )); + DEBUG(10,("delete case.\n" )); DLIST_REMOVE(ulhead, ul_curr); if(ulhead == NULL) @@ -302,7 +304,7 @@ BECOMES.... ul_curr->size = (ul_curr->start + ul_curr->size) - (lock->start + lock->size); ul_curr->start = lock->start + lock->size; - DEBUG(10,("brl_unlock_list: truncate high case: start=%.0f,size=%.0f\n", + DEBUG(10,("truncate high case: start=%.0f,size=%.0f\n", (double)ul_curr->start, (double)ul_curr->size )); ul_curr = ul_curr->next; @@ -329,7 +331,7 @@ BECOMES.... ul_curr->size = lock->start - ul_curr->start; - DEBUG(10,("brl_unlock_list: truncate low case: start=%.0f,size=%.0f\n", + DEBUG(10,("truncate low case: start=%.0f,size=%.0f\n", (double)ul_curr->start, (double)ul_curr->size )); ul_curr = ul_curr->next; @@ -372,7 +374,7 @@ BECOMES..... /* Truncate the ul_curr. */ ul_curr->size = lock->start - ul_curr->start; - DEBUG(10,("brl_unlock_list: split case: curr: start=%.0f,size=%.0f \ + DEBUG(10,("split case: curr: start=%.0f,size=%.0f \ new: start=%.0f,size=%.0f\n", (double)ul_curr->start, (double)ul_curr->size, (double)ul_new->start, (double)ul_new->size )); @@ -385,7 +387,7 @@ new: start=%.0f,size=%.0f\n", (double)ul_curr->start, (double)ul_curr->size, * case by forcing an abort.... Remove in production. */ - smb_panic("brl_unlock_list: logic flaw in cases...\n"); + smb_panic("logic flaw in cases...\n"); } } /* end for ( ul_curr = ulhead; ul_curr;) */ } /* end for (i=0; i<num_locks && ul_head; i++) */ @@ -422,7 +424,10 @@ BOOL brl_unlock(SMB_DEV_T dev, SMB_INO_T ino, int fnum, tdb_lockchain(tdb, kbuf); dbuf = tdb_fetch(tdb, kbuf); - if (!dbuf.dptr) goto fail; + if (!dbuf.dptr) { + DEBUG(0,("brl_unlock: tdb_fetch failed !\n")); + goto fail; + } context.smbpid = smbpid; context.pid = pid; @@ -435,6 +440,18 @@ BOOL brl_unlock(SMB_DEV_T dev, SMB_INO_T ino, int fnum, struct lock_struct *lock = &locks[i]; +#if 0 + /* JRATEST - DEBUGGING INFO */ + if(!brl_same_context(&lock->context, &context)) { + DEBUG(10,("brl_unlock: Not same context. l_smbpid = %u, l_pid = %u, l_tid = %u: \ +smbpid = %u, pid = %u, tid = %u\n", + lock->context.smbpid, lock->context.pid, lock->context.tid, + context.smbpid, context.pid, context.tid )); + + } + /* JRATEST */ +#endif + if (brl_same_context(&lock->context, &context) && lock->fnum == fnum && lock->start == start && diff --git a/source3/locking/locking.c b/source3/locking/locking.c index 9d407bf16b..b6b34138e3 100644 --- a/source3/locking/locking.c +++ b/source3/locking/locking.c @@ -41,8 +41,6 @@ extern int DEBUGLEVEL; /* the locking database handle */ static TDB_CONTEXT *tdb; -int global_smbpid; - /* * Doubly linked list to hold pending closes needed for * POSIX locks. This may be changed to use a hash table (as @@ -569,7 +567,7 @@ BOOL is_locked(files_struct *fsp,connection_struct *conn, return(False); ret = !brl_locktest(fsp->dev, fsp->inode, - global_smbpid, getpid(), conn->cnum, + fsp->smbpid, getpid(), conn->cnum, offset, count, lock_type); /* @@ -607,7 +605,7 @@ BOOL do_lock(files_struct *fsp,connection_struct *conn, if (OPEN_FSP(fsp) && fsp->can_lock && (fsp->conn == conn)) { ok = brl_lock(fsp->dev, fsp->inode, fsp->fnum, - global_smbpid, getpid(), conn->cnum, + fsp->smbpid, getpid(), conn->cnum, offset, count, lock_type); @@ -627,7 +625,7 @@ BOOL do_lock(files_struct *fsp,connection_struct *conn, * lock entry. */ (void)brl_unlock(fsp->dev, fsp->inode, fsp->fnum, - global_smbpid, getpid(), conn->cnum, + fsp->smbpid, getpid(), conn->cnum, offset, count); } } @@ -676,9 +674,10 @@ BOOL do_unlock(files_struct *fsp,connection_struct *conn, pid = getpid(); ok = brl_unlock(fsp->dev, fsp->inode, fsp->fnum, - global_smbpid, pid, conn->cnum, offset, count); + fsp->smbpid, pid, conn->cnum, offset, count); if (!ok) { + DEBUG(10,("do_unlock: returning ERRlock.\n" )); *eclass = ERRDOS; *ecode = ERRlock; return False; diff --git a/source3/smbd/open.c b/source3/smbd/open.c index 737b9b5ef3..92bba76619 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -26,6 +26,7 @@ extern int DEBUGLEVEL; extern pstring sesssetup_user; extern uint16 global_oplock_port; extern BOOL global_client_failed_oplock_break; +extern int global_smbpid; /**************************************************************************** fd support routines - attempt to do a dos_open. @@ -164,6 +165,7 @@ static BOOL open_file(files_struct *fsp,connection_struct *conn, fsp->dev = sbuf.st_dev; GetTimeOfDay(&fsp->open_time); fsp->vuid = current_user.vuid; + fsp->smbpid = global_smbpid; fsp->size = 0; fsp->pos = -1; fsp->can_lock = True; @@ -797,6 +799,7 @@ files_struct *open_file_stat(connection_struct *conn, fsp->mode = 0; GetTimeOfDay(&fsp->open_time); fsp->vuid = current_user.vuid; + fsp->smbpid = global_smbpid; fsp->size = 0; fsp->pos = -1; fsp->can_lock = False; @@ -920,6 +923,7 @@ files_struct *open_directory(connection_struct *conn, fsp->mode = 0; GetTimeOfDay(&fsp->open_time); fsp->vuid = current_user.vuid; + fsp->smbpid = global_smbpid; fsp->size = 0; fsp->pos = -1; fsp->can_lock = True; diff --git a/source3/smbd/process.c b/source3/smbd/process.c index f378550282..77e6fc2aa7 100644 --- a/source3/smbd/process.c +++ b/source3/smbd/process.c @@ -28,6 +28,7 @@ struct timeval smb_last_time; static char *InBuffer = NULL; char *OutBuffer = NULL; char *last_inbuf = NULL; +int global_smbpid; /* * Size of data we can send to client. Set @@ -418,7 +419,6 @@ static int switch_message(int type,char *inbuf,char *outbuf,int size,int bufsize static int num_smb_messages = sizeof(smb_messages) / sizeof(struct smb_message_struct); int match; - extern int global_smbpid; if (pid == (pid_t)-1) pid = getpid(); diff --git a/source3/utils/torture.c b/source3/utils/torture.c index deeb304804..1a9e757977 100644 --- a/source3/utils/torture.c +++ b/source3/utils/torture.c @@ -930,7 +930,7 @@ static void run_locktest4(int dummy) fail: cli_close(&cli1, fnum1); - cli_close(&cli1, fnum2); + cli_close(&cli2, fnum2); cli_unlink(&cli1, fname); close_connection(&cli1); close_connection(&cli2); |