2 Unix SMB/CIFS implementation.
4 Copyright (C) Andrew Tridgell 1992-2000
5 Copyright (C) Jeremy Allison 1992-2000
6 Copyright (C) Volker Lendecke 2005
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 12 aug 96: Erik.Devriendt@te6.siemens.be
25 added support for shared memory implementation of share mode locking
27 May 1997. Jeremy Allison (jallison@whistle.com). Modified share mode
28 locking to deal with multiple share modes per open file.
30 September 1997. Jeremy Allison (jallison@whistle.com). Added oplock
33 rewrtten completely to use new tdb code. Tridge, Dec '99
35 Added POSIX locking support. Jeremy Allison (jeremy@valinux.com), Apr. 2000.
42 #define DBGC_CLASS DBGC_LOCKING
44 /* the locking database handle */
45 static TDB_CONTEXT *tdb;
47 /****************************************************************************
49 ****************************************************************************/
51 static const char *lock_type_name(enum brl_type lock_type)
53 return (lock_type == READ_LOCK) ? "READ" : "WRITE";
56 /****************************************************************************
57 Utility function called to see if a file region is locked.
58 ****************************************************************************/
60 BOOL is_locked(files_struct *fsp,connection_struct *conn,
61 SMB_BIG_UINT count,SMB_BIG_UINT offset,
62 enum brl_type lock_type)
64 int snum = SNUM(conn);
65 int strict_locking = lp_strict_locking(snum);
71 if (!lp_locking(snum) || !strict_locking)
74 if (strict_locking == Auto) {
75 if (EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type) && (lock_type == READ_LOCK || lock_type == WRITE_LOCK)) {
76 DEBUG(10,("is_locked: optimisation - exclusive oplock on file %s\n", fsp->fsp_name ));
78 } else if ((fsp->oplock_type == LEVEL_II_OPLOCK) &&
79 (lock_type == READ_LOCK)) {
80 DEBUG(10,("is_locked: optimisation - level II oplock on file %s\n", fsp->fsp_name ));
83 ret = !brl_locktest(fsp->dev, fsp->inode, fsp->fnum,
84 global_smbpid, procid_self(), conn->cnum,
85 offset, count, lock_type);
88 ret = !brl_locktest(fsp->dev, fsp->inode, fsp->fnum,
89 global_smbpid, procid_self(), conn->cnum,
90 offset, count, lock_type);
93 DEBUG(10,("is_locked: brl start=%.0f len=%.0f %s for file %s\n",
94 (double)offset, (double)count, ret ? "locked" : "unlocked",
98 * There is no lock held by an SMB daemon, check to
99 * see if there is a POSIX lock from a UNIX or NFS process.
102 if(!ret && lp_posix_locking(snum)) {
103 ret = is_posix_locked(fsp, offset, count, lock_type);
105 DEBUG(10,("is_locked: posix start=%.0f len=%.0f %s for file %s\n",
106 (double)offset, (double)count, ret ? "locked" : "unlocked",
113 /****************************************************************************
114 Utility function called by locking requests.
115 ****************************************************************************/
117 static NTSTATUS do_lock(files_struct *fsp,connection_struct *conn, uint16 lock_pid,
118 SMB_BIG_UINT count,SMB_BIG_UINT offset,enum brl_type lock_type, BOOL *my_lock_ctx)
120 NTSTATUS status = NT_STATUS_LOCK_NOT_GRANTED;
122 if (!lp_locking(SNUM(conn)))
125 /* NOTE! 0 byte long ranges ARE allowed and should be stored */
127 DEBUG(10,("do_lock: lock type %s start=%.0f len=%.0f requested for file %s\n",
128 lock_type_name(lock_type), (double)offset, (double)count, fsp->fsp_name ));
130 if (OPEN_FSP(fsp) && fsp->can_lock && (fsp->conn == conn)) {
131 status = brl_lock(fsp->dev, fsp->inode, fsp->fnum,
132 lock_pid, procid_self(), conn->cnum,
134 lock_type, my_lock_ctx);
136 if (NT_STATUS_IS_OK(status) && lp_posix_locking(SNUM(conn))) {
139 * Try and get a POSIX lock on this range.
140 * Note that this is ok if it is a read lock
141 * overlapping on a different fd. JRA.
144 if (!set_posix_lock(fsp, offset, count, lock_type)) {
145 if (errno == EACCES || errno == EAGAIN)
146 status = NT_STATUS_FILE_LOCK_CONFLICT;
148 status = map_nt_error_from_unix(errno);
151 * We failed to map - we must now remove the brl
154 (void)brl_unlock(fsp->dev, fsp->inode, fsp->fnum,
155 lock_pid, procid_self(), conn->cnum,
156 offset, count, False,
165 /****************************************************************************
166 Utility function called by locking requests. This is *DISGUSTING*. It also
167 appears to be "What Windows Does" (tm). Andrew, ever wonder why Windows 2000
168 is so slow on the locking tests...... ? This is the reason. Much though I hate
169 it, we need this. JRA.
170 ****************************************************************************/
172 NTSTATUS do_lock_spin(files_struct *fsp,connection_struct *conn, uint16 lock_pid,
173 SMB_BIG_UINT count,SMB_BIG_UINT offset,enum brl_type lock_type, BOOL *my_lock_ctx)
175 int j, maxj = lp_lock_spin_count();
176 int sleeptime = lp_lock_sleep_time();
177 NTSTATUS status, ret;
182 ret = NT_STATUS_OK; /* to keep dumb compilers happy */
184 for (j = 0; j < maxj; j++) {
185 status = do_lock(fsp, conn, lock_pid, count, offset, lock_type, my_lock_ctx);
186 if (!NT_STATUS_EQUAL(status, NT_STATUS_LOCK_NOT_GRANTED) &&
187 !NT_STATUS_EQUAL(status, NT_STATUS_FILE_LOCK_CONFLICT)) {
190 /* if we do fail then return the first error code we got */
193 /* Don't spin if we blocked ourselves. */
198 sys_usleep(sleeptime);
203 /* Struct passed to brl_unlock. */
204 struct posix_unlock_data_struct {
210 /****************************************************************************
211 Function passed to brl_unlock to allow POSIX unlock to be done first.
212 ****************************************************************************/
214 static void posix_unlock(void *pre_data)
216 struct posix_unlock_data_struct *pdata = (struct posix_unlock_data_struct *)pre_data;
218 if (lp_posix_locking(SNUM(pdata->fsp->conn)))
219 release_posix_lock(pdata->fsp, pdata->offset, pdata->count);
222 /****************************************************************************
223 Utility function called by unlocking requests.
224 ****************************************************************************/
226 NTSTATUS do_unlock(files_struct *fsp,connection_struct *conn, uint16 lock_pid,
227 SMB_BIG_UINT count,SMB_BIG_UINT offset)
230 struct posix_unlock_data_struct posix_data;
232 if (!lp_locking(SNUM(conn)))
235 if (!OPEN_FSP(fsp) || !fsp->can_lock || (fsp->conn != conn)) {
236 return NT_STATUS_INVALID_HANDLE;
239 DEBUG(10,("do_unlock: unlock start=%.0f len=%.0f requested for file %s\n",
240 (double)offset, (double)count, fsp->fsp_name ));
243 * Remove the existing lock record from the tdb lockdb
244 * before looking at POSIX locks. If this record doesn't
245 * match then don't bother looking to remove POSIX locks.
248 posix_data.fsp = fsp;
249 posix_data.offset = offset;
250 posix_data.count = count;
252 ok = brl_unlock(fsp->dev, fsp->inode, fsp->fnum,
253 lock_pid, procid_self(), conn->cnum, offset, count,
254 False, posix_unlock, (void *)&posix_data);
257 DEBUG(10,("do_unlock: returning ERRlock.\n" ));
258 return NT_STATUS_RANGE_NOT_LOCKED;
263 /****************************************************************************
264 Remove any locks on this fd. Called from file_close().
265 ****************************************************************************/
267 void locking_close_file(files_struct *fsp)
269 struct process_id pid = procid_self();
271 if (!lp_locking(SNUM(fsp->conn)))
275 * Just release all the brl locks, no need to release individually.
278 brl_close(fsp->dev, fsp->inode, pid, fsp->conn->cnum, fsp->fnum);
280 if(lp_posix_locking(SNUM(fsp->conn))) {
283 * Release all the POSIX locks.
285 posix_locking_close_file(fsp);
290 /****************************************************************************
291 Initialise the locking functions.
292 ****************************************************************************/
294 static int open_read_only;
296 BOOL locking_init(int read_only)
303 tdb = tdb_open_log(lock_path("locking.tdb"),
304 lp_open_files_db_hash_size(),
305 TDB_DEFAULT|(read_only?0x0:TDB_CLEAR_IF_FIRST),
306 read_only?O_RDONLY:O_RDWR|O_CREAT,
310 DEBUG(0,("ERROR: Failed to initialise locking database\n"));
314 if (!posix_locking_init(read_only))
317 open_read_only = read_only;
322 /*******************************************************************
323 Deinitialize the share_mode management.
324 ******************************************************************/
326 BOOL locking_end(void)
330 brl_shutdown(open_read_only);
332 if (tdb_close(tdb) != 0)
339 /*******************************************************************
340 Form a static locking key for a dev/inode pair.
341 ******************************************************************/
343 /* key and data records in the tdb locking database */
349 /*******************************************************************
350 Form a static locking key for a dev/inode pair.
351 ******************************************************************/
353 static TDB_DATA locking_key(SMB_DEV_T dev, SMB_INO_T inode)
355 static struct locking_key key;
358 memset(&key, '\0', sizeof(key));
361 kbuf.dptr = (char *)&key;
362 kbuf.dsize = sizeof(key);
366 /*******************************************************************
367 Print out a share mode.
368 ********************************************************************/
370 char *share_mode_str(int num, struct share_mode_entry *e)
372 static pstring share_str;
374 slprintf(share_str, sizeof(share_str)-1, "share_mode_entry[%d]: %s "
375 "pid = %s, share_access = 0x%x, private_options = 0x%x, "
376 "access_mask = 0x%x, mid = 0x%x, type= 0x%x, file_id = %lu, "
377 "dev = 0x%x, inode = %.0f",
379 e->op_type == UNUSED_SHARE_MODE_ENTRY ? "UNUSED" : "",
380 procid_str_static(&e->pid),
381 e->share_access, e->private_options,
382 e->access_mask, e->op_mid, e->op_type, e->share_file_id,
383 (unsigned int)e->dev, (double)e->inode );
388 /*******************************************************************
389 Print out a share mode table.
390 ********************************************************************/
392 static void print_share_mode_table(struct locking_data *data)
394 int num_share_modes = data->u.s.num_share_mode_entries;
395 struct share_mode_entry *shares =
396 (struct share_mode_entry *)(data + 1);
399 for (i = 0; i < num_share_modes; i++) {
400 struct share_mode_entry entry;
402 memcpy(&entry, &shares[i], sizeof(struct share_mode_entry));
403 DEBUG(10,("print_share_mode_table: %s\n",
404 share_mode_str(i, &entry)));
408 /*******************************************************************
409 Get all share mode entries for a dev/inode pair.
410 ********************************************************************/
412 static BOOL parse_share_modes(TDB_DATA dbuf, struct share_mode_lock *lck)
414 struct locking_data *data;
417 if (dbuf.dsize < sizeof(struct locking_data)) {
418 smb_panic("PANIC: parse_share_modes: buffer too short.\n");
421 data = (struct locking_data *)dbuf.dptr;
423 lck->delete_on_close = data->u.s.delete_on_close;
424 lck->initial_delete_on_close = data->u.s.initial_delete_on_close;
425 lck->num_share_modes = data->u.s.num_share_mode_entries;
427 DEBUG(10, ("parse_share_modes: delete_on_close: %d, "
428 "initial_delete_on_close: %d, "
429 "num_share_modes: %d\n",
430 lck->delete_on_close,
431 lck->initial_delete_on_close,
432 lck->num_share_modes));
434 if ((lck->num_share_modes < 0) || (lck->num_share_modes > 1000000)) {
435 DEBUG(0, ("invalid number of share modes: %d\n",
436 lck->num_share_modes));
437 smb_panic("PANIC: invalid number of share modes");
440 lck->share_modes = NULL;
442 if (lck->num_share_modes != 0) {
444 if (dbuf.dsize < (sizeof(struct locking_data) +
445 (lck->num_share_modes *
446 sizeof(struct share_mode_entry)))) {
447 smb_panic("PANIC: parse_share_modes: buffer too short.\n");
450 lck->share_modes = talloc_memdup(lck, dbuf.dptr+sizeof(*data),
451 lck->num_share_modes *
452 sizeof(struct share_mode_entry));
454 if (lck->share_modes == NULL) {
455 smb_panic("talloc failed\n");
459 /* Get any delete token. */
460 if (data->u.s.delete_token_size) {
461 char *p = dbuf.dptr + sizeof(*data) +
462 (lck->num_share_modes *
463 sizeof(struct share_mode_entry));
465 if ((data->u.s.delete_token_size < sizeof(uid_t) + sizeof(gid_t)) ||
466 ((data->u.s.delete_token_size - sizeof(uid_t)) % sizeof(gid_t)) != 0) {
467 DEBUG(0, ("parse_share_modes: invalid token size %d\n",
468 data->u.s.delete_token_size));
469 smb_panic("parse_share_modes: invalid token size\n");
472 lck->delete_token = TALLOC_P(lck, UNIX_USER_TOKEN);
473 if (!lck->delete_token) {
474 smb_panic("talloc failed\n");
477 /* Copy out the uid and gid. */
478 memcpy(&lck->delete_token->uid, p, sizeof(uid_t));
480 memcpy(&lck->delete_token->gid, p, sizeof(gid_t));
483 /* Any supplementary groups ? */
484 lck->delete_token->ngroups = (data->u.s.delete_token_size > (sizeof(uid_t) + sizeof(gid_t))) ?
485 ((data->u.s.delete_token_size -
486 (sizeof(uid_t) + sizeof(gid_t)))/sizeof(gid_t)) : 0;
488 if (lck->delete_token->ngroups) {
489 /* Make this a talloc child of lck->delete_token. */
490 lck->delete_token->groups = TALLOC_ARRAY(lck->delete_token, gid_t,
491 lck->delete_token->ngroups);
492 if (!lck->delete_token) {
493 smb_panic("talloc failed\n");
496 for (i = 0; i < lck->delete_token->ngroups; i++) {
497 memcpy(&lck->delete_token->groups[i], p, sizeof(gid_t));
503 lck->delete_token = NULL;
506 /* Save off the associated service path and filename. */
507 lck->servicepath = talloc_strdup(lck, dbuf.dptr + sizeof(*data) +
508 (lck->num_share_modes *
509 sizeof(struct share_mode_entry)) +
510 data->u.s.delete_token_size );
512 lck->filename = talloc_strdup(lck, dbuf.dptr + sizeof(*data) +
513 (lck->num_share_modes *
514 sizeof(struct share_mode_entry)) +
515 data->u.s.delete_token_size +
516 strlen(lck->servicepath) + 1 );
519 * Ensure that each entry has a real process attached.
522 for (i = 0; i < lck->num_share_modes; i++) {
523 struct share_mode_entry *entry_p = &lck->share_modes[i];
524 DEBUG(10,("parse_share_modes: %s\n",
525 share_mode_str(i, entry_p) ));
526 if (!process_exists(entry_p->pid)) {
527 DEBUG(10,("parse_share_modes: deleted %s\n",
528 share_mode_str(i, entry_p) ));
529 entry_p->op_type = UNUSED_SHARE_MODE_ENTRY;
530 lck->modified = True;
537 static TDB_DATA unparse_share_modes(struct share_mode_lock *lck)
542 struct locking_data *data;
545 uint32 delete_token_size;
550 for (i=0; i<lck->num_share_modes; i++) {
551 if (!is_unused_share_mode_entry(&lck->share_modes[i])) {
556 if (num_valid == 0) {
560 sp_len = strlen(lck->servicepath);
561 delete_token_size = (lck->delete_token ?
562 (sizeof(uid_t) + sizeof(gid_t) + (lck->delete_token->ngroups*sizeof(gid_t))) : 0);
564 result.dsize = sizeof(*data) +
565 lck->num_share_modes * sizeof(struct share_mode_entry) +
568 strlen(lck->filename) + 1;
569 result.dptr = talloc_size(lck, result.dsize);
571 if (result.dptr == NULL) {
572 smb_panic("talloc failed\n");
575 data = (struct locking_data *)result.dptr;
577 data->u.s.num_share_mode_entries = lck->num_share_modes;
578 data->u.s.delete_on_close = lck->delete_on_close;
579 data->u.s.initial_delete_on_close = lck->initial_delete_on_close;
580 data->u.s.delete_token_size = delete_token_size;
581 DEBUG(10, ("unparse_share_modes: del: %d, initial del %d, tok = %u, num: %d\n",
582 data->u.s.delete_on_close,
583 data->u.s.initial_delete_on_close,
584 (unsigned int)data->u.s.delete_token_size,
585 data->u.s.num_share_mode_entries));
586 memcpy(result.dptr + sizeof(*data), lck->share_modes,
587 sizeof(struct share_mode_entry)*lck->num_share_modes);
588 offset = sizeof(*data) +
589 sizeof(struct share_mode_entry)*lck->num_share_modes;
591 /* Store any delete on close token. */
592 if (lck->delete_token) {
593 char *p = result.dptr + offset;
595 memcpy(p, &lck->delete_token->uid, sizeof(uid_t));
598 memcpy(p, &lck->delete_token->gid, sizeof(gid_t));
600 for (i = 0; i < lck->delete_token->ngroups; i++) {
601 memcpy(p, &lck->delete_token->groups[i], sizeof(gid_t));
604 offset = p - result.dptr;
607 safe_strcpy(result.dptr + offset, lck->servicepath,
608 result.dsize - offset - 1);
609 offset += sp_len + 1;
610 safe_strcpy(result.dptr + offset, lck->filename,
611 result.dsize - offset - 1);
613 if (DEBUGLEVEL >= 10) {
614 print_share_mode_table(data);
620 static int share_mode_lock_destructor(void *p)
622 struct share_mode_lock *lck =
623 talloc_get_type_abort(p, struct share_mode_lock);
624 TDB_DATA key = locking_key(lck->dev, lck->ino);
627 if (!lck->modified) {
631 data = unparse_share_modes(lck);
633 if (data.dptr == NULL) {
635 /* There has been an entry before, delete it */
636 if (tdb_delete(tdb, key) == -1) {
637 smb_panic("Could not delete share entry\n");
643 if (tdb_store(tdb, key, data, TDB_REPLACE) == -1) {
644 smb_panic("Could not store share mode entry\n");
648 tdb_chainunlock(tdb, key);
653 struct share_mode_lock *get_share_mode_lock(TALLOC_CTX *mem_ctx,
654 SMB_DEV_T dev, SMB_INO_T ino,
655 const char *servicepath,
658 struct share_mode_lock *lck;
659 TDB_DATA key = locking_key(dev, ino);
662 lck = TALLOC_P(mem_ctx, struct share_mode_lock);
664 DEBUG(0, ("talloc failed\n"));
668 /* Ensure we set every field here as the destructor must be
669 valid even if parse_share_modes fails. */
671 lck->servicepath = NULL;
672 lck->filename = NULL;
675 lck->num_share_modes = 0;
676 lck->share_modes = NULL;
677 lck->delete_token = NULL;
678 lck->delete_on_close = False;
679 lck->initial_delete_on_close = False;
681 lck->modified = False;
683 if (tdb_chainlock(tdb, key) != 0) {
684 DEBUG(3, ("Could not lock share entry\n"));
689 /* We must set the destructor immediately after the chainlock
690 ensure the lock is cleaned up on any of the error return
693 talloc_set_destructor(lck, share_mode_lock_destructor);
695 data = tdb_fetch(tdb, key);
696 lck->fresh = (data.dptr == NULL);
700 if (fname == NULL || servicepath == NULL) {
704 lck->filename = talloc_strdup(lck, fname);
705 lck->servicepath = talloc_strdup(lck, servicepath);
706 if (lck->filename == NULL || lck->servicepath == NULL) {
707 DEBUG(0, ("talloc failed\n"));
712 if (!parse_share_modes(data, lck)) {
713 DEBUG(0, ("Could not parse share modes\n"));
715 SAFE_FREE(data.dptr);
720 SAFE_FREE(data.dptr);
725 /*******************************************************************
726 Sets the service name and filename for rename.
727 At this point we emit "file renamed" messages to all
728 process id's that have this file open.
729 Based on an initial code idea from SATOH Fumiyasu <fumiya@samba.gr.jp>
730 ********************************************************************/
732 BOOL rename_share_filename(struct share_mode_lock *lck,
733 const char *servicepath,
746 DEBUG(10, ("rename_share_filename: servicepath %s newname %s\n",
747 servicepath, newname));
750 * rename_internal_fsp() and rename_internals() add './' to
751 * head of newname if newname does not contain a '/'.
753 while (newname[0] && newname[1] && newname[0] == '.' && newname[1] == '/') {
757 lck->servicepath = talloc_strdup(lck, servicepath);
758 lck->filename = talloc_strdup(lck, newname);
759 if (lck->filename == NULL || lck->servicepath == NULL) {
760 DEBUG(0, ("rename_share_filename: talloc failed\n"));
763 lck->modified = True;
765 sp_len = strlen(lck->servicepath);
766 fn_len = strlen(lck->filename);
768 msg_len = MSG_FILE_RENAMED_MIN_SIZE + sp_len + 1 + fn_len + 1;
770 /* Set up the name changed message. */
771 frm = TALLOC(lck, msg_len);
776 SDEV_T_VAL(frm,0,lck->dev);
777 SINO_T_VAL(frm,8,lck->ino);
779 DEBUG(10,("rename_share_filename: msg_len = %d\n", msg_len ));
781 safe_strcpy(&frm[16], lck->servicepath, sp_len);
782 safe_strcpy(&frm[16 + sp_len + 1], lck->filename, fn_len);
784 /* Send the messages. */
785 for (i=0; i<lck->num_share_modes; i++) {
786 struct share_mode_entry *se = &lck->share_modes[i];
787 if (!is_valid_share_mode_entry(se)) {
790 /* But not to ourselves... */
791 if (procid_is_me(&se->pid)) {
795 DEBUG(10,("rename_share_filename: sending rename message to pid %u "
796 "dev %x, inode %.0f sharepath %s newname %s\n",
797 (unsigned int)procid_to_pid(&se->pid),
798 (unsigned int)lck->dev, (double)lck->ino,
799 lck->servicepath, lck->filename ));
802 message_send_pid(se->pid, MSG_SMB_FILE_RENAME,
810 BOOL get_delete_on_close_flag(SMB_DEV_T dev, SMB_INO_T inode)
813 struct share_mode_lock *lck = get_share_mode_lock(NULL, dev, inode, NULL, NULL);
817 result = lck->delete_on_close;
822 BOOL is_valid_share_mode_entry(const struct share_mode_entry *e)
826 num_props += ((e->op_type == NO_OPLOCK) ? 1 : 0);
827 num_props += (EXCLUSIVE_OPLOCK_TYPE(e->op_type) ? 1 : 0);
828 num_props += (LEVEL_II_OPLOCK_TYPE(e->op_type) ? 1 : 0);
830 SMB_ASSERT(num_props <= 1);
831 return (num_props != 0);
834 BOOL is_deferred_open_entry(const struct share_mode_entry *e)
836 return (e->op_type == DEFERRED_OPEN_ENTRY);
839 BOOL is_unused_share_mode_entry(const struct share_mode_entry *e)
841 return (e->op_type == UNUSED_SHARE_MODE_ENTRY);
844 /*******************************************************************
845 Fill a share mode entry.
846 ********************************************************************/
848 static void fill_share_mode_entry(struct share_mode_entry *e,
850 uint16 mid, uint16 op_type)
853 e->pid = procid_self();
854 e->share_access = fsp->share_access;
855 e->private_options = fsp->fh->private_options;
856 e->access_mask = fsp->access_mask;
858 e->op_type = op_type;
859 e->time.tv_sec = fsp->open_time.tv_sec;
860 e->time.tv_usec = fsp->open_time.tv_usec;
861 e->share_file_id = fsp->file_id;
863 e->inode = fsp->inode;
866 static void fill_deferred_open_entry(struct share_mode_entry *e,
867 const struct timeval request_time,
868 SMB_DEV_T dev, SMB_INO_T ino, uint16 mid)
871 e->pid = procid_self();
873 e->op_type = DEFERRED_OPEN_ENTRY;
874 e->time.tv_sec = request_time.tv_sec;
875 e->time.tv_usec = request_time.tv_usec;
880 static void add_share_mode_entry(struct share_mode_lock *lck,
881 const struct share_mode_entry *entry)
885 for (i=0; i<lck->num_share_modes; i++) {
886 struct share_mode_entry *e = &lck->share_modes[i];
887 if (is_unused_share_mode_entry(e)) {
893 if (i == lck->num_share_modes) {
894 /* No unused entry found */
895 ADD_TO_ARRAY(lck, struct share_mode_entry, *entry,
896 &lck->share_modes, &lck->num_share_modes);
898 lck->modified = True;
901 void set_share_mode(struct share_mode_lock *lck, files_struct *fsp,
902 uint16 mid, uint16 op_type)
904 struct share_mode_entry entry;
905 fill_share_mode_entry(&entry, fsp, mid, op_type);
906 add_share_mode_entry(lck, &entry);
909 void add_deferred_open(struct share_mode_lock *lck, uint16 mid,
910 struct timeval request_time,
911 SMB_DEV_T dev, SMB_INO_T ino)
913 struct share_mode_entry entry;
914 fill_deferred_open_entry(&entry, request_time, dev, ino, mid);
915 add_share_mode_entry(lck, &entry);
918 /*******************************************************************
919 Check if two share mode entries are identical, ignoring oplock
920 and mid info and desired_access.
921 ********************************************************************/
923 static BOOL share_modes_identical(struct share_mode_entry *e1,
924 struct share_mode_entry *e2)
926 #if 1 /* JRA PARANOIA TEST - REMOVE LATER */
927 if (procid_equal(&e1->pid, &e2->pid) &&
928 e1->share_file_id == e2->share_file_id &&
929 e1->dev == e2->dev &&
930 e1->inode == e2->inode &&
931 (e1->share_access) != (e2->share_access)) {
932 DEBUG(0,("PANIC: share_modes_identical: share_mode "
933 "mismatch (e1 = 0x%x, e2 = 0x%x). Logic error.\n",
934 (unsigned int)e1->share_access,
935 (unsigned int)e2->share_access ));
936 smb_panic("PANIC: share_modes_identical logic error.\n");
940 return (procid_equal(&e1->pid, &e2->pid) &&
941 (e1->share_access) == (e2->share_access) &&
942 e1->dev == e2->dev &&
943 e1->inode == e2->inode &&
944 e1->share_file_id == e2->share_file_id );
947 static BOOL deferred_open_identical(struct share_mode_entry *e1,
948 struct share_mode_entry *e2)
950 return (procid_equal(&e1->pid, &e2->pid) &&
951 (e1->op_mid == e2->op_mid) &&
952 (e1->dev == e2->dev) &&
953 (e1->inode == e2->inode));
956 static struct share_mode_entry *find_share_mode_entry(struct share_mode_lock *lck,
957 struct share_mode_entry *entry)
961 for (i=0; i<lck->num_share_modes; i++) {
962 struct share_mode_entry *e = &lck->share_modes[i];
963 if (is_valid_share_mode_entry(entry) &&
964 is_valid_share_mode_entry(e) &&
965 share_modes_identical(e, entry)) {
968 if (is_deferred_open_entry(entry) &&
969 is_deferred_open_entry(e) &&
970 deferred_open_identical(e, entry)) {
977 /*******************************************************************
978 Del the share mode of a file for this process. Return the number of
980 ********************************************************************/
982 BOOL del_share_mode(struct share_mode_lock *lck, files_struct *fsp)
984 struct share_mode_entry entry, *e;
986 fill_share_mode_entry(&entry, fsp, 0, NO_OPLOCK);
988 e = find_share_mode_entry(lck, &entry);
993 e->op_type = UNUSED_SHARE_MODE_ENTRY;
994 lck->modified = True;
998 void del_deferred_open_entry(struct share_mode_lock *lck, uint16 mid)
1000 struct share_mode_entry entry, *e;
1002 fill_deferred_open_entry(&entry, timeval_zero(),
1003 lck->dev, lck->ino, mid);
1005 e = find_share_mode_entry(lck, &entry);
1010 e->op_type = UNUSED_SHARE_MODE_ENTRY;
1011 lck->modified = True;
1014 /*******************************************************************
1015 Remove an oplock mid and mode entry from a share mode.
1016 ********************************************************************/
1018 BOOL remove_share_oplock(struct share_mode_lock *lck, files_struct *fsp)
1020 struct share_mode_entry entry, *e;
1022 fill_share_mode_entry(&entry, fsp, 0, NO_OPLOCK);
1024 e = find_share_mode_entry(lck, &entry);
1030 e->op_type = NO_OPLOCK;
1031 lck->modified = True;
1035 /*******************************************************************
1036 Downgrade a oplock type from exclusive to level II.
1037 ********************************************************************/
1039 BOOL downgrade_share_oplock(struct share_mode_lock *lck, files_struct *fsp)
1041 struct share_mode_entry entry, *e;
1043 fill_share_mode_entry(&entry, fsp, 0, NO_OPLOCK);
1045 e = find_share_mode_entry(lck, &entry);
1050 e->op_type = LEVEL_II_OPLOCK;
1051 lck->modified = True;
1055 /****************************************************************************
1056 Deal with the internal needs of setting the delete on close flag. Note that
1057 as the tdb locking is recursive, it is safe to call this from within
1058 open_file_shared. JRA.
1059 ****************************************************************************/
1061 NTSTATUS can_set_delete_on_close(files_struct *fsp, BOOL delete_on_close,
1064 if (!delete_on_close) {
1065 return NT_STATUS_OK;
1069 * Only allow delete on close for writable files.
1072 if ((dosmode & aRONLY) &&
1073 !lp_delete_readonly(SNUM(fsp->conn))) {
1074 DEBUG(10,("can_set_delete_on_close: file %s delete on close "
1075 "flag set but file attribute is readonly.\n",
1077 return NT_STATUS_CANNOT_DELETE;
1081 * Only allow delete on close for writable shares.
1084 if (!CAN_WRITE(fsp->conn)) {
1085 DEBUG(10,("can_set_delete_on_close: file %s delete on "
1086 "close flag set but write access denied on share.\n",
1088 return NT_STATUS_ACCESS_DENIED;
1092 * Only allow delete on close for files/directories opened with delete
1096 if (!(fsp->access_mask & DELETE_ACCESS)) {
1097 DEBUG(10,("can_set_delete_on_close: file %s delete on "
1098 "close flag set but delete access denied.\n",
1100 return NT_STATUS_ACCESS_DENIED;
1103 return NT_STATUS_OK;
1106 /*************************************************************************
1107 Return a talloced copy of a UNIX_USER_TOKEN. NULL on fail.
1108 (Should this be in locking.c.... ?).
1109 *************************************************************************/
1111 static UNIX_USER_TOKEN *copy_unix_token(TALLOC_CTX *ctx, UNIX_USER_TOKEN *tok)
1113 UNIX_USER_TOKEN *cpy;
1119 cpy = TALLOC_P(ctx, UNIX_USER_TOKEN);
1124 cpy->uid = tok->uid;
1125 cpy->gid = tok->gid;
1126 cpy->ngroups = tok->ngroups;
1128 /* Make this a talloc child of cpy. */
1129 cpy->groups = TALLOC_ARRAY(cpy, gid_t, tok->ngroups);
1133 memcpy(cpy->groups, tok->groups, tok->ngroups * sizeof(gid_t));
1138 /****************************************************************************
1139 Replace the delete on close token.
1140 ****************************************************************************/
1142 void set_delete_on_close_token(struct share_mode_lock *lck, UNIX_USER_TOKEN *tok)
1144 /* Ensure there's no token. */
1145 if (lck->delete_token) {
1146 TALLOC_FREE(lck->delete_token); /* Also deletes groups... */
1147 lck->delete_token = NULL;
1150 /* Copy the new token (can be NULL). */
1151 lck->delete_token = copy_unix_token(lck, tok);
1152 lck->modified = True;
1155 /****************************************************************************
1156 Sets the delete on close flag over all share modes on this file.
1157 Modify the share mode entry for all files open
1158 on this device and inode to tell other smbds we have
1159 changed the delete on close flag. This will be noticed
1160 in the close code, the last closer will delete the file
1162 Note that setting this to any value clears the initial_delete_on_close flag.
1163 If delete_on_close is True this makes a copy of any UNIX_USER_TOKEN into the
1165 ****************************************************************************/
1167 BOOL set_delete_on_close(files_struct *fsp, BOOL delete_on_close, UNIX_USER_TOKEN *tok)
1169 struct share_mode_lock *lck;
1171 DEBUG(10,("set_delete_on_close: %s delete on close flag for "
1172 "fnum = %d, file %s\n",
1173 delete_on_close ? "Adding" : "Removing", fsp->fnum,
1180 lck = get_share_mode_lock(NULL, fsp->dev, fsp->inode, NULL, NULL);
1185 if (lck->delete_on_close != delete_on_close) {
1186 set_delete_on_close_token(lck, tok);
1187 lck->delete_on_close = delete_on_close;
1188 if (delete_on_close) {
1189 SMB_ASSERT(lck->delete_token != NULL);
1191 lck->modified = True;
1194 if (lck->initial_delete_on_close) {
1195 lck->initial_delete_on_close = False;
1196 lck->modified = True;
1203 static int traverse_fn(TDB_CONTEXT *the_tdb, TDB_DATA kbuf, TDB_DATA dbuf,
1206 struct locking_data *data;
1207 struct share_mode_entry *shares;
1208 const char *sharepath;
1211 void (*traverse_callback)(struct share_mode_entry *, const char *, const char *) = state;
1213 /* Ensure this is a locking_key record. */
1214 if (kbuf.dsize != sizeof(struct locking_key))
1217 data = (struct locking_data *)dbuf.dptr;
1218 shares = (struct share_mode_entry *)(dbuf.dptr + sizeof(*data));
1219 sharepath = dbuf.dptr + sizeof(*data) +
1220 data->u.s.num_share_mode_entries*sizeof(*shares) +
1221 data->u.s.delete_token_size;
1222 fname = dbuf.dptr + sizeof(*data) +
1223 data->u.s.num_share_mode_entries*sizeof(*shares) +
1224 data->u.s.delete_token_size +
1225 strlen(sharepath) + 1;
1227 for (i=0;i<data->u.s.num_share_mode_entries;i++) {
1228 traverse_callback(&shares[i], sharepath, fname);
1233 /*******************************************************************
1234 Call the specified function on each entry under management by the
1236 ********************************************************************/
1238 int share_mode_forall(void (*fn)(const struct share_mode_entry *, const char *, const char *))
1242 return tdb_traverse(tdb, traverse_fn, fn);