r10929: tagging release
[Samba.git] / release-3-0-20b / source / smbd / open.c
blob7c14156d659d50ee8bce92497a1f8304f9144487
1 /*
2 Unix SMB/CIFS implementation.
3 file opening and share modes
4 Copyright (C) Andrew Tridgell 1992-1998
5 Copyright (C) Jeremy Allison 2001-2004
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.
23 #include "includes.h"
25 extern struct current_user current_user;
26 extern userdom_struct current_user_info;
27 extern uint16 global_oplock_port;
28 extern uint16 global_smbpid;
29 extern BOOL global_client_failed_oplock_break;
31 struct dev_inode_bundle {
32 SMB_DEV_T dev;
33 SMB_INO_T inode;
36 /****************************************************************************
37 fd support routines - attempt to do a dos_open.
38 ****************************************************************************/
40 static int fd_open(struct connection_struct *conn,
41 const char *fname,
42 int flags,
43 mode_t mode)
45 int fd;
46 #ifdef O_NOFOLLOW
47 if (!lp_symlinks(SNUM(conn))) {
48 flags |= O_NOFOLLOW;
50 #endif
52 fd = SMB_VFS_OPEN(conn,fname,flags,mode);
54 DEBUG(10,("fd_open: name %s, flags = 0%o mode = 0%o, fd = %d. %s\n", fname,
55 flags, (int)mode, fd, (fd == -1) ? strerror(errno) : "" ));
57 return fd;
60 /****************************************************************************
61 Close the file associated with a fsp.
62 ****************************************************************************/
64 int fd_close(struct connection_struct *conn,
65 files_struct *fsp)
67 if (fsp->fh->fd == -1) {
68 return 0; /* What we used to call a stat open. */
70 if (fsp->fh->ref_count > 1) {
71 return 0; /* Shared handle. Only close last reference. */
73 return fd_close_posix(conn, fsp);
77 /****************************************************************************
78 Check a filename for the pipe string.
79 ****************************************************************************/
81 static void check_for_pipe(const char *fname)
83 /* special case of pipe opens */
84 char s[10];
85 StrnCpy(s,fname,sizeof(s)-1);
86 strlower_m(s);
87 if (strstr(s,"pipe/")) {
88 DEBUG(3,("Rejecting named pipe open for %s\n",fname));
89 set_saved_error_triple(ERRSRV, ERRaccess, NT_STATUS_ACCESS_DENIED);
93 /****************************************************************************
94 Change the ownership of a file to that of the parent directory.
95 Do this by fd if possible.
96 ****************************************************************************/
98 void change_owner_to_parent(connection_struct *conn,
99 files_struct *fsp,
100 const char *fname,
101 SMB_STRUCT_STAT *psbuf)
103 const char *parent_path = parent_dirname(fname);
104 SMB_STRUCT_STAT parent_st;
105 int ret;
107 ret = SMB_VFS_STAT(conn, parent_path, &parent_st);
108 if (ret == -1) {
109 DEBUG(0,("change_owner_to_parent: failed to stat parent "
110 "directory %s. Error was %s\n",
111 parent_path, strerror(errno) ));
112 return;
115 if (fsp && fsp->fh->fd != -1) {
116 become_root();
117 ret = SMB_VFS_FCHOWN(fsp, fsp->fh->fd, parent_st.st_uid, (gid_t)-1);
118 unbecome_root();
119 if (ret == -1) {
120 DEBUG(0,("change_owner_to_parent: failed to fchown "
121 "file %s to parent directory uid %u. Error "
122 "was %s\n", fname,
123 (unsigned int)parent_st.st_uid,
124 strerror(errno) ));
127 DEBUG(10,("change_owner_to_parent: changed new file %s to "
128 "parent directory uid %u.\n", fname,
129 (unsigned int)parent_st.st_uid ));
131 } else {
132 /* We've already done an lstat into psbuf, and we know it's a
133 directory. If we can cd into the directory and the dev/ino
134 are the same then we can safely chown without races as
135 we're locking the directory in place by being in it. This
136 should work on any UNIX (thanks tridge :-). JRA.
139 pstring saved_dir;
140 SMB_STRUCT_STAT sbuf;
142 if (!vfs_GetWd(conn,saved_dir)) {
143 DEBUG(0,("change_owner_to_parent: failed to get "
144 "current working directory\n"));
145 return;
148 /* Chdir into the new path. */
149 if (vfs_ChDir(conn, fname) == -1) {
150 DEBUG(0,("change_owner_to_parent: failed to change "
151 "current working directory to %s. Error "
152 "was %s\n", fname, strerror(errno) ));
153 goto out;
156 if (SMB_VFS_STAT(conn,".",&sbuf) == -1) {
157 DEBUG(0,("change_owner_to_parent: failed to stat "
158 "directory '.' (%s) Error was %s\n",
159 fname, strerror(errno)));
160 goto out;
163 /* Ensure we're pointing at the same place. */
164 if (sbuf.st_dev != psbuf->st_dev ||
165 sbuf.st_ino != psbuf->st_ino ||
166 sbuf.st_mode != psbuf->st_mode ) {
167 DEBUG(0,("change_owner_to_parent: "
168 "device/inode/mode on directory %s changed. "
169 "Refusing to chown !\n", fname ));
170 goto out;
173 become_root();
174 ret = SMB_VFS_CHOWN(conn, ".", parent_st.st_uid, (gid_t)-1);
175 unbecome_root();
176 if (ret == -1) {
177 DEBUG(10,("change_owner_to_parent: failed to chown "
178 "directory %s to parent directory uid %u. "
179 "Error was %s\n", fname,
180 (unsigned int)parent_st.st_uid, strerror(errno) ));
181 goto out;
184 DEBUG(10,("change_owner_to_parent: changed ownership of new "
185 "directory %s to parent directory uid %u.\n",
186 fname, (unsigned int)parent_st.st_uid ));
188 out:
190 vfs_ChDir(conn,saved_dir);
194 /****************************************************************************
195 Open a file.
196 ****************************************************************************/
198 static BOOL open_file(files_struct *fsp,
199 connection_struct *conn,
200 const char *fname,
201 SMB_STRUCT_STAT *psbuf,
202 int flags,
203 mode_t unx_mode,
204 uint32 access_mask)
206 int accmode = (flags & O_ACCMODE);
207 int local_flags = flags;
208 BOOL file_existed = VALID_STAT(*psbuf);
210 fsp->fh->fd = -1;
211 fsp->oplock_type = NO_OPLOCK;
212 errno = EPERM;
214 /* Check permissions */
217 * This code was changed after seeing a client open request
218 * containing the open mode of (DENY_WRITE/read-only) with
219 * the 'create if not exist' bit set. The previous code
220 * would fail to open the file read only on a read-only share
221 * as it was checking the flags parameter directly against O_RDONLY,
222 * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
223 * JRA.
226 if (!CAN_WRITE(conn)) {
227 /* It's a read-only share - fail if we wanted to write. */
228 if(accmode != O_RDONLY) {
229 DEBUG(3,("Permission denied opening %s\n",fname));
230 check_for_pipe(fname);
231 return False;
232 } else if(flags & O_CREAT) {
233 /* We don't want to write - but we must make sure that
234 O_CREAT doesn't create the file if we have write
235 access into the directory.
237 flags &= ~O_CREAT;
238 local_flags &= ~O_CREAT;
243 * This little piece of insanity is inspired by the
244 * fact that an NT client can open a file for O_RDONLY,
245 * but set the create disposition to FILE_EXISTS_TRUNCATE.
246 * If the client *can* write to the file, then it expects to
247 * truncate the file, even though it is opening for readonly.
248 * Quicken uses this stupid trick in backup file creation...
249 * Thanks *greatly* to "David W. Chapman Jr." <dwcjr@inethouston.net>
250 * for helping track this one down. It didn't bite us in 2.0.x
251 * as we always opened files read-write in that release. JRA.
254 if ((accmode == O_RDONLY) && ((flags & O_TRUNC) == O_TRUNC)) {
255 DEBUG(10,("open_file: truncate requested on read-only open "
256 "for file %s\n",fname ));
257 local_flags = (flags & ~O_ACCMODE)|O_RDWR;
260 if ((access_mask & (FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA|FILE_EXECUTE)) ||
261 (local_flags & O_CREAT) ||
262 ((local_flags & O_TRUNC) == O_TRUNC) ) {
265 * We can't actually truncate here as the file may be locked.
266 * open_file_shared will take care of the truncate later. JRA.
269 local_flags &= ~O_TRUNC;
271 #if defined(O_NONBLOCK) && defined(S_ISFIFO)
273 * We would block on opening a FIFO with no one else on the
274 * other end. Do what we used to do and add O_NONBLOCK to the
275 * open flags. JRA.
278 if (file_existed && S_ISFIFO(psbuf->st_mode)) {
279 local_flags |= O_NONBLOCK;
281 #endif
283 /* Don't create files with Microsoft wildcard characters. */
284 if ((local_flags & O_CREAT) && !file_existed &&
285 ms_has_wild(fname)) {
286 set_saved_error_triple(ERRDOS, ERRinvalidname,
287 NT_STATUS_OBJECT_NAME_INVALID);
288 return False;
291 /* Actually do the open */
292 fsp->fh->fd = fd_open(conn, fname, local_flags, unx_mode);
293 if (fsp->fh->fd == -1) {
294 DEBUG(3,("Error opening file %s (%s) (local_flags=%d) "
295 "(flags=%d)\n",
296 fname,strerror(errno),local_flags,flags));
297 check_for_pipe(fname);
298 return False;
301 /* Inherit the ACL if the file was created. */
302 if ((local_flags & O_CREAT) && !file_existed) {
303 inherit_access_acl(conn, fname, unx_mode);
306 } else {
307 fsp->fh->fd = -1; /* What we used to call a stat open. */
310 if (!file_existed) {
311 int ret;
313 if (fsp->fh->fd == -1) {
314 ret = SMB_VFS_STAT(conn, fname, psbuf);
315 } else {
316 ret = SMB_VFS_FSTAT(fsp,fsp->fh->fd,psbuf);
317 /* If we have an fd, this stat should succeed. */
318 if (ret == -1) {
319 DEBUG(0,("Error doing fstat on open file %s "
320 "(%s)\n", fname,strerror(errno) ));
324 /* For a non-io open, this stat failing means file not found. JRA */
325 if (ret == -1) {
326 fd_close(conn, fsp);
327 return False;
332 * POSIX allows read-only opens of directories. We don't
333 * want to do this (we use a different code path for this)
334 * so catch a directory open and return an EISDIR. JRA.
337 if(S_ISDIR(psbuf->st_mode)) {
338 fd_close(conn, fsp);
339 errno = EISDIR;
340 return False;
343 fsp->mode = psbuf->st_mode;
344 fsp->inode = psbuf->st_ino;
345 fsp->dev = psbuf->st_dev;
346 fsp->vuid = current_user.vuid;
347 fsp->file_pid = global_smbpid;
348 fsp->can_lock = True;
349 fsp->can_read = (access_mask & (FILE_READ_DATA)) ? True : False;
350 if (!CAN_WRITE(conn)) {
351 fsp->can_write = False;
352 } else {
353 fsp->can_write = (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ? True : False;
355 fsp->print_file = False;
356 fsp->modified = False;
357 fsp->oplock_type = NO_OPLOCK;
358 fsp->sent_oplock_break = NO_BREAK_SENT;
359 fsp->is_directory = False;
360 fsp->is_stat = False;
361 if (conn->aio_write_behind_list &&
362 is_in_path(fname, conn->aio_write_behind_list, conn->case_sensitive)) {
363 fsp->aio_write_behind = True;
366 string_set(&fsp->fsp_name,fname);
367 fsp->wcp = NULL; /* Write cache pointer. */
369 DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
370 *current_user_info.smb_name ? current_user_info.smb_name : conn->user,fsp->fsp_name,
371 BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
372 conn->num_files_open + 1));
374 errno = 0;
375 return True;
378 /*******************************************************************
379 Return True if the filename is one of the special executable types.
380 ********************************************************************/
382 static BOOL is_executable(const char *fname)
384 if ((fname = strrchr_m(fname,'.'))) {
385 if (strequal(fname,".com") ||
386 strequal(fname,".dll") ||
387 strequal(fname,".exe") ||
388 strequal(fname,".sym")) {
389 return True;
392 return False;
395 /****************************************************************************
396 Check if we can open a file with a share mode.
397 Returns True if conflict, False if not.
398 ****************************************************************************/
400 static BOOL share_conflict(share_mode_entry *entry,
401 uint32 access_mask,
402 uint32 share_access)
404 DEBUG(10,("share_conflict: entry->access_mask = 0x%x, "
405 "entry->share_access = 0x%x, "
406 "entry->private_options = 0x%x\n",
407 (unsigned int)entry->access_mask,
408 (unsigned int)entry->share_access,
409 (unsigned int)entry->private_options));
411 DEBUG(10,("share_conflict: access_mask = 0x%x, share_access = 0x%x\n",
412 (unsigned int)access_mask, (unsigned int)share_access));
414 if ((entry->access_mask & (FILE_WRITE_DATA|
415 FILE_APPEND_DATA|
416 FILE_READ_DATA|
417 FILE_EXECUTE|
418 DELETE_ACCESS)) == 0) {
419 DEBUG(10,("share_conflict: No conflict due to "
420 "entry->access_mask = 0x%x\n",
421 (unsigned int)entry->access_mask ));
422 return False;
425 if ((access_mask & (FILE_WRITE_DATA|
426 FILE_APPEND_DATA|
427 FILE_READ_DATA|
428 FILE_EXECUTE|
429 DELETE_ACCESS)) == 0) {
430 DEBUG(10,("share_conflict: No conflict due to "
431 "access_mask = 0x%x\n",
432 (unsigned int)access_mask ));
433 return False;
436 #if 1 /* JRA TEST - Superdebug. */
437 #define CHECK_MASK(num, am, right, sa, share) \
438 DEBUG(10,("share_conflict: [%d] am (0x%x) & right (0x%x) = 0x%x\n", \
439 (unsigned int)(num), (unsigned int)(am), \
440 (unsigned int)(right), (unsigned int)(am)&(right) )); \
441 DEBUG(10,("share_conflict: [%d] sa (0x%x) & share (0x%x) = 0x%x\n", \
442 (unsigned int)(num), (unsigned int)(sa), \
443 (unsigned int)(share), (unsigned int)(sa)&(share) )); \
444 if (((am) & (right)) && !((sa) & (share))) { \
445 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
446 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
447 (unsigned int)(share) )); \
448 set_saved_error_triple(ERRDOS, ERRbadshare, NT_STATUS_SHARING_VIOLATION); \
449 return True; \
451 #else
452 #define CHECK_MASK(num, am, right, sa, share) \
453 if (((am) & (right)) && !((sa) & (share))) { \
454 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
455 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
456 (unsigned int)(share) )); \
457 set_saved_error_triple(ERRDOS, ERRbadshare, NT_STATUS_SHARING_VIOLATION); \
458 return True; \
460 #endif
462 CHECK_MASK(1, entry->access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
463 share_access, FILE_SHARE_WRITE);
464 CHECK_MASK(2, access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
465 entry->share_access, FILE_SHARE_WRITE);
467 CHECK_MASK(3, entry->access_mask, FILE_READ_DATA | FILE_EXECUTE,
468 share_access, FILE_SHARE_READ);
469 CHECK_MASK(4, access_mask, FILE_READ_DATA | FILE_EXECUTE,
470 entry->share_access, FILE_SHARE_READ);
472 CHECK_MASK(5, entry->access_mask, DELETE_ACCESS,
473 share_access, FILE_SHARE_DELETE);
474 CHECK_MASK(6, access_mask, DELETE_ACCESS,
475 entry->share_access, FILE_SHARE_DELETE);
477 DEBUG(10,("share_conflict: No conflict.\n"));
478 return False;
481 #if defined(DEVELOPER)
482 static void validate_my_share_entries(int num,
483 share_mode_entry *share_entry)
485 files_struct *fsp;
487 if (share_entry->pid != sys_getpid()) {
488 return;
491 fsp = file_find_dif(share_entry->dev, share_entry->inode,
492 share_entry->share_file_id);
493 if (!fsp) {
494 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
495 share_mode_str(num, share_entry) ));
496 smb_panic("validate_my_share_entries: Cannot match a "
497 "share entry with an open file\n");
500 if (((uint16)fsp->oplock_type) != share_entry->op_type) {
501 pstring str;
502 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
503 share_mode_str(num, share_entry) ));
504 slprintf(str, sizeof(str)-1, "validate_my_share_entries: "
505 "file %s, oplock_type = 0x%x, op_type = 0x%x\n",
506 fsp->fsp_name, (unsigned int)fsp->oplock_type,
507 (unsigned int)share_entry->op_type );
508 smb_panic(str);
511 #endif
513 struct share_mode_entry_list {
514 struct share_mode_entry_list *next, *prev;
515 share_mode_entry entry;
518 static void free_broken_entry_list(struct share_mode_entry_list *broken_entry_list)
520 while (broken_entry_list) {
521 struct share_mode_entry_list *broken_entry = broken_entry_list;
522 DLIST_REMOVE(broken_entry_list, broken_entry);
523 SAFE_FREE(broken_entry);
527 static BOOL cause_oplock_break(int request, int existing, uint32 access_mask)
529 if ((access_mask == DELETE_ACCESS) &&
530 (request == NO_OPLOCK)) {
531 /* This is a delete request */
532 return (BATCH_OPLOCK_TYPE(existing) != 0);
535 if (EXCLUSIVE_OPLOCK_TYPE(existing) && (request != NO_OPLOCK)) {
536 return True;
539 if ((existing != NO_OPLOCK) && (request == NO_OPLOCK)) {
540 return True;
543 return False;
546 /****************************************************************************
547 Deal with open deny mode and oplock break processing.
548 Invarient: Share mode must be locked on entry and exit.
549 Returns -1 on error, or number of share modes on success (may be zero).
550 ****************************************************************************/
552 static int open_mode_check(connection_struct *conn,
553 const char *fname,
554 SMB_DEV_T dev,
555 SMB_INO_T inode,
556 uint32 access_mask,
557 uint32 share_access,
558 uint32 create_options,
559 int *p_oplock_request,
560 BOOL *p_all_current_opens_are_level_II)
562 int i;
563 int num_share_modes;
564 int oplock_contention_count = 0;
565 share_mode_entry *old_shares = NULL;
566 BOOL broke_oplock;
567 BOOL delete_on_close;
569 num_share_modes = get_share_modes(dev, inode, &old_shares, &delete_on_close);
571 if(num_share_modes == 0) {
572 SAFE_FREE(old_shares);
573 return 0;
576 if (access_mask &&
577 ((access_mask & ~(SYNCHRONIZE_ACCESS| FILE_READ_ATTRIBUTES|
578 FILE_WRITE_ATTRIBUTES))==0) &&
579 ((access_mask & (SYNCHRONIZE_ACCESS|FILE_READ_ATTRIBUTES|
580 FILE_WRITE_ATTRIBUTES)) != 0)) {
581 /* Stat open that doesn't trigger oplock breaks or share mode
582 * checks... ! JRA. */
583 SAFE_FREE(old_shares);
584 return num_share_modes;
587 /* A delete on close prohibits everything */
589 if (delete_on_close) {
590 SAFE_FREE(old_shares);
591 errno = EACCES;
592 return -1;
596 * Check if the share modes will give us access.
599 do {
600 struct share_mode_entry_list *broken_entry_list = NULL;
601 struct share_mode_entry_list *broken_entry = NULL;
603 broke_oplock = False;
604 *p_all_current_opens_are_level_II = True;
606 for(i = 0; i < num_share_modes; i++) {
607 share_mode_entry *share_entry = &old_shares[i];
608 BOOL opb_ret;
610 #if defined(DEVELOPER)
611 validate_my_share_entries(i, share_entry);
612 #endif
615 * By observation of NetBench, oplocks are broken
616 * *before* share modes are checked. This allows a
617 * file to be closed by the client if the share mode
618 * would deny access and the client has an oplock.
619 * Check if someone has an oplock on this file. If so
620 * we must break it before continuing.
623 if (!cause_oplock_break(*p_oplock_request,
624 share_entry->op_type,
625 access_mask)) {
626 if (!LEVEL_II_OPLOCK_TYPE(share_entry->op_type)) {
627 *p_all_current_opens_are_level_II = False;
629 continue;
632 /* This is an oplock break */
634 DEBUG(5,("open_mode_check: oplock_request = %d, "
635 "breaking oplock (%x) on file %s, "
636 "dev = %x, inode = %.0f\n",
637 *p_oplock_request, share_entry->op_type,
638 fname, (unsigned int)dev, (double)inode));
640 /* Ensure the reply for the open uses the correct
641 * sequence number. */
642 /* This isn't a real deferred packet as it's response
643 * will also increment the sequence.
645 srv_defer_sign_response(get_current_mid());
647 /* Oplock break - unlock to request it. */
648 unlock_share_entry(conn, dev, inode);
650 opb_ret = request_oplock_break(share_entry);
652 /* Now relock. */
653 lock_share_entry(conn, dev, inode);
655 if (!opb_ret) {
656 DEBUG(0,("open_mode_check: FAILED when breaking "
657 "oplock (%x) on file %s, dev = %x, "
658 "inode = %.0f\n",
659 old_shares[i].op_type, fname,
660 (unsigned int)dev, (double)inode));
661 SAFE_FREE(old_shares);
662 set_saved_error_triple(ERRDOS, ERRbadshare,
663 NT_STATUS_SHARING_VIOLATION);
664 return -1;
667 broken_entry = SMB_MALLOC_P(struct share_mode_entry_list);
668 if (!broken_entry) {
669 smb_panic("open_mode_check: malloc fail.\n");
671 broken_entry->entry = *share_entry;
672 DLIST_ADD(broken_entry_list, broken_entry);
673 broke_oplock = True;
675 } /* end for */
677 if (broke_oplock) {
678 /* Update the current open table. */
679 SAFE_FREE(old_shares);
680 num_share_modes = get_share_modes(dev, inode,
681 &old_shares,
682 &delete_on_close);
685 if (lp_share_modes(SNUM(conn))) {
686 /* Now we check the share modes, after any oplock breaks. */
687 for(i = 0; i < num_share_modes; i++) {
688 share_mode_entry *share_entry = &old_shares[i];
690 /* someone else has a share lock on it, check to see
691 * if we can too */
692 if (share_conflict(share_entry, access_mask,
693 share_access)) {
694 SAFE_FREE(old_shares);
695 free_broken_entry_list(broken_entry_list);
696 errno = EACCES;
697 return -1;
702 for(broken_entry = broken_entry_list; broken_entry;
703 broken_entry = broken_entry->next) {
704 oplock_contention_count++;
706 /* Paranoia check that this is no longer an exlusive entry. */
707 for(i = 0; i < num_share_modes; i++) {
708 share_mode_entry *share_entry = &old_shares[i];
710 if (!(share_modes_identical(&broken_entry->entry,
711 share_entry) &&
712 EXCLUSIVE_OPLOCK_TYPE(share_entry->op_type))) {
713 continue;
717 * This should not happen. The target left this oplock
718 * as exlusive.... The process *must* be dead....
721 DEBUG(0,("open_mode_check: exlusive oplock left by "
722 "process %d after break ! For file %s, "
723 "dev = %x, inode = %.0f. Deleting it to "
724 "continue...\n",
725 (int)broken_entry->entry.pid, fname,
726 (unsigned int)dev, (double)inode));
728 if (process_exists(broken_entry->entry.pid)) {
729 DEBUG(0,("open_mode_check: Existent process "
730 "%lu left active oplock.\n",
731 (unsigned long)broken_entry->entry.pid ));
734 if (del_share_entry(dev, inode, &broken_entry->entry,
735 NULL, &delete_on_close) == -1) {
736 free_broken_entry_list(broken_entry_list);
737 errno = EACCES;
738 set_saved_error_triple(ERRDOS, ERRbadshare,
739 NT_STATUS_SHARING_VIOLATION);
740 return -1;
744 * We must reload the share modes after deleting the
745 * other process's entry.
748 SAFE_FREE(old_shares);
749 num_share_modes = get_share_modes(dev, inode,
750 &old_shares,
751 &delete_on_close);
752 break;
753 } /* end for paranoia... */
754 } /* end for broken_entry */
755 free_broken_entry_list(broken_entry_list);
756 } while(broke_oplock);
759 * Refuse to grant an oplock in case the contention limit is
760 * reached when going through the lock list multiple times.
763 if(oplock_contention_count >= lp_oplock_contention_limit(SNUM(conn))) {
764 *p_oplock_request = 0;
765 DEBUG(4,("open_mode_check: oplock contention = %d. Not granting oplock.\n",
766 oplock_contention_count ));
769 SAFE_FREE(old_shares);
770 return num_share_modes;
773 /****************************************************************************
774 Delete the record for a handled deferred open entry.
775 ****************************************************************************/
777 static void delete_defered_open_entry_record(connection_struct *conn,
778 SMB_DEV_T dev,
779 SMB_INO_T inode)
781 uint16 mid = get_current_mid();
782 pid_t mypid = sys_getpid();
783 deferred_open_entry *de_array = NULL;
784 int num_de_entries, i;
786 if (!lp_defer_sharing_violations()) {
787 return;
790 num_de_entries = get_deferred_opens(conn, dev, inode, &de_array);
791 for (i = 0; i < num_de_entries; i++) {
792 deferred_open_entry *entry = &de_array[i];
793 if (entry->pid == mypid && entry->mid == mid && entry->dev == dev &&
794 entry->inode == inode) {
796 /* Remove the deferred open entry from the array. */
797 delete_deferred_open_entry(entry);
798 SAFE_FREE(de_array);
799 return;
802 SAFE_FREE(de_array);
805 /****************************************************************************
806 Handle the 1 second delay in returning a SHARING_VIOLATION error.
807 ****************************************************************************/
809 static void defer_open_sharing_error(connection_struct *conn,
810 struct timeval *ptv,
811 const char *fname,
812 SMB_DEV_T dev,
813 SMB_INO_T inode)
815 uint16 mid = get_current_mid();
816 pid_t mypid = sys_getpid();
817 deferred_open_entry *de_array = NULL;
818 int num_de_entries, i;
819 struct dev_inode_bundle dib;
821 if (!lp_defer_sharing_violations()) {
822 return;
825 dib.dev = dev;
826 dib.inode = inode;
828 num_de_entries = get_deferred_opens(conn, dev, inode, &de_array);
829 for (i = 0; i < num_de_entries; i++) {
830 deferred_open_entry *entry = &de_array[i];
831 if (entry->pid == mypid && entry->mid == mid) {
833 * Check if a 1 second timeout has expired.
835 if (usec_time_diff(ptv, &entry->time) >
836 SHARING_VIOLATION_USEC_WAIT) {
837 DEBUG(10,("defer_open_sharing_error: Deleting "
838 "deferred open entry for mid %u, "
839 "file %s\n",
840 (unsigned int)mid, fname ));
842 /* Expired, return a real error. */
843 /* Remove the deferred open entry from the array. */
845 delete_deferred_open_entry(entry);
846 SAFE_FREE(de_array);
847 return;
850 * If the timeout hasn't expired yet and we still have
851 * a sharing violation, just leave the entry in the
852 * deferred open array alone. We do need to reschedule
853 * this open call though (with the original created
854 * time).
856 DEBUG(10,("defer_open_sharing_error: time [%u.%06u] "
857 "updating deferred open entry for mid %u, file %s\n",
858 (unsigned int)entry->time.tv_sec,
859 (unsigned int)entry->time.tv_usec,
860 (unsigned int)mid, fname ));
862 push_sharing_violation_open_smb_message(&entry->time,
863 (char *)&dib,
864 sizeof(dib));
865 SAFE_FREE(de_array);
866 return;
870 DEBUG(10,("defer_open_sharing_error: time [%u.%06u] adding deferred "
871 "open entry for mid %u, file %s\n",
872 (unsigned int)ptv->tv_sec, (unsigned int)ptv->tv_usec,
873 (unsigned int)mid, fname ));
875 if (!push_sharing_violation_open_smb_message(ptv, (char *)&dib, sizeof(dib))) {
876 SAFE_FREE(de_array);
877 return;
879 if (!add_deferred_open(mid, ptv, dev, inode, global_oplock_port, fname)) {
880 remove_sharing_violation_open_smb_message(mid);
884 * Push the MID of this packet on the signing queue.
885 * We only do this once, the first time we push the packet
886 * onto the deferred open queue, as this has a side effect
887 * of incrementing the response sequence number.
890 srv_defer_sign_response(mid);
892 SAFE_FREE(de_array);
895 /****************************************************************************
896 Set a kernel flock on a file for NFS interoperability.
897 This requires a patch to Linux.
898 ****************************************************************************/
900 static void kernel_flock(files_struct *fsp, uint32 share_mode)
902 #if HAVE_KERNEL_SHARE_MODES
903 int kernel_mode = 0;
904 if (share_mode == FILE_SHARE_WRITE) {
905 kernel_mode = LOCK_MAND|LOCK_WRITE;
906 } else if (share_mode == FILE_SHARE_READ) {
907 kernel_mode = LOCK_MAND|LOCK_READ;
908 } else if (share_mode == FILE_SHARE_NONE) {
909 kernel_mode = LOCK_MAND;
911 if (kernel_mode) {
912 flock(fsp->fh->fd, kernel_mode);
914 #endif
918 /****************************************************************************
919 On overwrite open ensure that the attributes match.
920 ****************************************************************************/
922 static BOOL open_match_attributes(connection_struct *conn,
923 const char *path,
924 uint32 old_dos_attr,
925 uint32 new_dos_attr,
926 mode_t existing_unx_mode,
927 mode_t new_unx_mode,
928 mode_t *returned_unx_mode)
930 uint32 noarch_old_dos_attr, noarch_new_dos_attr;
932 noarch_old_dos_attr = (old_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
933 noarch_new_dos_attr = (new_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
935 if((noarch_old_dos_attr == 0 && noarch_new_dos_attr != 0) ||
936 (noarch_old_dos_attr != 0 && ((noarch_old_dos_attr & noarch_new_dos_attr) == noarch_old_dos_attr))) {
937 *returned_unx_mode = new_unx_mode;
938 } else {
939 *returned_unx_mode = (mode_t)0;
942 DEBUG(10,("open_match_attributes: file %s old_dos_attr = 0x%x, "
943 "existing_unx_mode = 0%o, new_dos_attr = 0x%x "
944 "returned_unx_mode = 0%o\n",
945 path,
946 (unsigned int)old_dos_attr,
947 (unsigned int)existing_unx_mode,
948 (unsigned int)new_dos_attr,
949 (unsigned int)*returned_unx_mode ));
951 /* If we're mapping SYSTEM and HIDDEN ensure they match. */
952 if (lp_map_system(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
953 if ((old_dos_attr & FILE_ATTRIBUTE_SYSTEM) &&
954 !(new_dos_attr & FILE_ATTRIBUTE_SYSTEM)) {
955 return False;
958 if (lp_map_hidden(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
959 if ((old_dos_attr & FILE_ATTRIBUTE_HIDDEN) &&
960 !(new_dos_attr & FILE_ATTRIBUTE_HIDDEN)) {
961 return False;
964 return True;
967 /****************************************************************************
968 Special FCB or DOS processing in the case of a sharing violation.
969 Try and find a duplicated file handle.
970 ****************************************************************************/
972 static files_struct *fcb_or_dos_open(connection_struct *conn,
973 const char *fname, SMB_DEV_T dev,
974 SMB_INO_T inode,
975 uint32 access_mask,
976 uint32 share_access,
977 uint32 create_options)
979 files_struct *fsp;
980 files_struct *dup_fsp;
982 DEBUG(5,("fcb_or_dos_open: attempting old open semantics for "
983 "file %s.\n", fname ));
985 for(fsp = file_find_di_first(dev, inode); fsp;
986 fsp = file_find_di_next(fsp)) {
988 DEBUG(10,("fcb_or_dos_open: checking file %s, fd = %d, "
989 "vuid = %u, file_pid = %u, private_options = 0x%x "
990 "access_mask = 0x%x\n", fsp->fsp_name,
991 fsp->fh->fd, (unsigned int)fsp->vuid,
992 (unsigned int)fsp->file_pid,
993 (unsigned int)fsp->fh->private_options,
994 (unsigned int)fsp->access_mask ));
996 if (fsp->fh->fd != -1 &&
997 fsp->vuid == current_user.vuid &&
998 fsp->file_pid == global_smbpid &&
999 (fsp->fh->private_options & (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS |
1000 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) &&
1001 (fsp->access_mask & FILE_WRITE_DATA) &&
1002 strequal(fsp->fsp_name, fname)) {
1003 DEBUG(10,("fcb_or_dos_open: file match\n"));
1004 break;
1008 if (!fsp) {
1009 return NULL;
1012 /* quite an insane set of semantics ... */
1013 if (is_executable(fname) &&
1014 (fsp->fh->private_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS)) {
1015 DEBUG(10,("fcb_or_dos_open: file fail due to is_executable.\n"));
1016 return NULL;
1019 /* We need to duplicate this fsp. */
1020 dup_fsp = dup_file_fsp(fsp, access_mask, share_access, create_options);
1021 if (!dup_fsp) {
1022 return NULL;
1025 return dup_fsp;
1028 /****************************************************************************
1029 Open a file with a share mode - old openX method - map into NTCreate.
1030 ****************************************************************************/
1032 BOOL map_open_params_to_ntcreate(const char *fname, int deny_mode, int open_func,
1033 uint32 *paccess_mask,
1034 uint32 *pshare_mode,
1035 uint32 *pcreate_disposition,
1036 uint32 *pcreate_options)
1038 uint32 access_mask;
1039 uint32 share_mode;
1040 uint32 create_disposition;
1041 uint32 create_options = 0;
1043 DEBUG(10,("map_open_params_to_ntcreate: fname = %s, deny_mode = 0x%x, "
1044 "open_func = 0x%x\n",
1045 fname, (unsigned int)deny_mode, (unsigned int)open_func ));
1047 /* Create the NT compatible access_mask. */
1048 switch (GET_OPENX_MODE(deny_mode)) {
1049 case DOS_OPEN_EXEC: /* Implies read-only - used to be FILE_READ_DATA */
1050 case DOS_OPEN_RDONLY:
1051 access_mask = FILE_GENERIC_READ;
1052 break;
1053 case DOS_OPEN_WRONLY:
1054 access_mask = FILE_GENERIC_WRITE;
1055 break;
1056 case DOS_OPEN_RDWR:
1057 case DOS_OPEN_FCB:
1058 access_mask = FILE_GENERIC_READ|FILE_GENERIC_WRITE;
1059 break;
1060 default:
1061 DEBUG(10,("map_open_params_to_ntcreate: bad open mode = 0x%x\n",
1062 (unsigned int)GET_OPENX_MODE(deny_mode)));
1063 return False;
1066 /* Create the NT compatible create_disposition. */
1067 switch (open_func) {
1068 case OPENX_FILE_EXISTS_FAIL|OPENX_FILE_CREATE_IF_NOT_EXIST:
1069 create_disposition = FILE_CREATE;
1070 break;
1072 case OPENX_FILE_EXISTS_OPEN:
1073 create_disposition = FILE_OPEN;
1074 break;
1076 case OPENX_FILE_EXISTS_OPEN|OPENX_FILE_CREATE_IF_NOT_EXIST:
1077 create_disposition = FILE_OPEN_IF;
1078 break;
1080 case OPENX_FILE_EXISTS_TRUNCATE:
1081 create_disposition = FILE_OVERWRITE;
1082 break;
1084 case OPENX_FILE_EXISTS_TRUNCATE|OPENX_FILE_CREATE_IF_NOT_EXIST:
1085 create_disposition = FILE_OVERWRITE_IF;
1086 break;
1088 default:
1089 /* From samba4 - to be confirmed. */
1090 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_EXEC) {
1091 create_disposition = FILE_CREATE;
1092 break;
1094 DEBUG(10,("map_open_params_to_ntcreate: bad "
1095 "open_func 0x%x\n", (unsigned int)open_func));
1096 return False;
1099 /* Create the NT compatible share modes. */
1100 switch (GET_DENY_MODE(deny_mode)) {
1101 case DENY_ALL:
1102 share_mode = FILE_SHARE_NONE;
1103 break;
1105 case DENY_WRITE:
1106 share_mode = FILE_SHARE_READ;
1107 break;
1109 case DENY_READ:
1110 share_mode = FILE_SHARE_WRITE;
1111 break;
1113 case DENY_NONE:
1114 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1115 break;
1117 case DENY_DOS:
1118 create_options |= NTCREATEX_OPTIONS_PRIVATE_DENY_DOS;
1119 if (is_executable(fname)) {
1120 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1121 } else {
1122 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_RDONLY) {
1123 share_mode = FILE_SHARE_READ;
1124 } else {
1125 share_mode = FILE_SHARE_NONE;
1128 break;
1130 case DENY_FCB:
1131 create_options |= NTCREATEX_OPTIONS_PRIVATE_DENY_FCB;
1132 share_mode = FILE_SHARE_NONE;
1133 break;
1135 default:
1136 DEBUG(10,("map_open_params_to_ntcreate: bad deny_mode 0x%x\n",
1137 (unsigned int)GET_DENY_MODE(deny_mode) ));
1138 return False;
1141 DEBUG(10,("map_open_params_to_ntcreate: file %s, access_mask = 0x%x, "
1142 "share_mode = 0x%x, create_disposition = 0x%x, "
1143 "create_options = 0x%x\n",
1144 fname,
1145 (unsigned int)access_mask,
1146 (unsigned int)share_mode,
1147 (unsigned int)create_disposition,
1148 (unsigned int)create_options ));
1150 if (paccess_mask) {
1151 *paccess_mask = access_mask;
1153 if (pshare_mode) {
1154 *pshare_mode = share_mode;
1156 if (pcreate_disposition) {
1157 *pcreate_disposition = create_disposition;
1159 if (pcreate_options) {
1160 *pcreate_options = create_options;
1163 return True;
1167 /* Map generic permissions to file object specific permissions */
1169 struct generic_mapping file_generic_mapping = {
1170 FILE_GENERIC_READ,
1171 FILE_GENERIC_WRITE,
1172 FILE_GENERIC_EXECUTE,
1173 FILE_GENERIC_ALL
1176 /****************************************************************************
1177 Open a file with a share mode.
1178 ****************************************************************************/
1180 files_struct *open_file_ntcreate(connection_struct *conn,
1181 const char *fname,
1182 SMB_STRUCT_STAT *psbuf,
1183 uint32 access_mask, /* access bits (FILE_READ_DATA etc.) */
1184 uint32 share_access, /* share constants (FILE_SHARE_READ etc). */
1185 uint32 create_disposition, /* FILE_OPEN_IF etc. */
1186 uint32 create_options, /* options such as delete on close. */
1187 uint32 new_dos_attributes, /* attributes used for new file. */
1188 int oplock_request, /* internal Samba oplock codes. */
1189 /* Information (FILE_EXISTS etc.) */
1190 int *pinfo)
1192 int flags=0;
1193 int flags2=0;
1194 BOOL file_existed = VALID_STAT(*psbuf);
1195 BOOL def_acl = False;
1196 BOOL internal_only_open = False;
1197 SMB_DEV_T dev = 0;
1198 SMB_INO_T inode = 0;
1199 int num_share_modes = 0;
1200 BOOL all_current_opens_are_level_II = False;
1201 BOOL fsp_open = False;
1202 files_struct *fsp = NULL;
1203 mode_t new_unx_mode = (mode_t)0;
1204 mode_t unx_mode = (mode_t)0;
1205 int info;
1206 uint32 existing_dos_attributes = 0;
1207 struct pending_message_list *pml = NULL;
1208 uint16 port = 0;
1209 uint16 mid = get_current_mid();
1211 if (conn->printer) {
1213 * Printers are handled completely differently.
1214 * Most of the passed parameters are ignored.
1217 if (pinfo) {
1218 *pinfo = FILE_WAS_CREATED;
1221 DEBUG(10, ("open_file_ntcreate: printer open fname=%s\n", fname));
1223 return print_fsp_open(conn, fname);
1226 /* We add aARCH to this as this mode is only used if the file is
1227 * created new. */
1228 unx_mode = unix_mode(conn, new_dos_attributes | aARCH,fname, True);
1230 DEBUG(10, ("open_file_ntcreate: fname=%s, dos_attrs=0x%x "
1231 "access_mask=0x%x share_access=0x%x "
1232 "create_disposition = 0x%x create_options=0x%x "
1233 "unix mode=0%o oplock_request=%d\n",
1234 fname, new_dos_attributes, access_mask, share_access,
1235 create_disposition, create_options, unx_mode,
1236 oplock_request));
1238 if (oplock_request == INTERNAL_OPEN_ONLY) {
1239 internal_only_open = True;
1240 oplock_request = 0;
1243 if ((pml = get_open_deferred_message(mid)) != NULL) {
1244 struct dev_inode_bundle dib;
1246 memcpy(&dib, pml->private_data.data, sizeof(dib));
1248 /* There could be a race condition where the dev/inode pair
1249 has changed since we deferred the message. If so, just
1250 remove the deferred open entry and return sharing
1251 violation. */
1253 /* If the timeout value is non-zero, we need to just return
1254 sharing violation. Don't retry the open as we were not
1255 notified of a close and we don't want to trigger another
1256 spurious oplock break. */
1258 if (!file_existed || dib.dev != psbuf->st_dev ||
1259 dib.inode != psbuf->st_ino || pml->msg_time.tv_sec ||
1260 pml->msg_time.tv_usec) {
1261 /* Ensure we don't reprocess this message. */
1262 remove_sharing_violation_open_smb_message(mid);
1264 /* Now remove the deferred open entry under lock. */
1265 lock_share_entry(conn, dib.dev, dib.inode);
1266 delete_defered_open_entry_record(conn, dib.dev,
1267 dib.inode);
1268 unlock_share_entry(conn, dib.dev, dib.inode);
1270 set_saved_error_triple(ERRDOS, ERRbadshare,
1271 NT_STATUS_SHARING_VIOLATION);
1272 return NULL;
1274 /* Ensure we don't reprocess this message. */
1275 remove_sharing_violation_open_smb_message(mid);
1278 if (!check_name(fname,conn)) {
1279 return NULL;
1282 new_dos_attributes &= SAMBA_ATTRIBUTES_MASK;
1283 if (file_existed) {
1284 existing_dos_attributes = dos_mode(conn, fname, psbuf);
1287 /* ignore any oplock requests if oplocks are disabled */
1288 if (!lp_oplocks(SNUM(conn)) || global_client_failed_oplock_break) {
1289 oplock_request = 0;
1292 /* this is for OS/2 long file names - say we don't support them */
1293 if (!lp_posix_pathnames() && strstr(fname,".+,;=[].")) {
1294 /* OS/2 Workplace shell fix may be main code stream in a later
1295 * release. */
1296 set_saved_error_triple(ERRDOS, ERRcannotopen,
1297 NT_STATUS_OBJECT_NAME_NOT_FOUND);
1298 DEBUG(5,("open_file_ntcreate: OS/2 long filenames are not "
1299 "supported.\n"));
1300 return NULL;
1303 switch( create_disposition ) {
1305 * Currently we're using FILE_SUPERSEDE as the same as
1306 * FILE_OVERWRITE_IF but they really are
1307 * different. FILE_SUPERSEDE deletes an existing file
1308 * (requiring delete access) then recreates it.
1310 case FILE_SUPERSEDE:
1311 /* If file exists replace/overwrite. If file doesn't
1312 * exist create. */
1313 flags2 |= (O_CREAT | O_TRUNC);
1314 break;
1316 case FILE_OVERWRITE_IF:
1317 /* If file exists replace/overwrite. If file doesn't
1318 * exist create. */
1319 flags2 |= (O_CREAT | O_TRUNC);
1320 break;
1322 case FILE_OPEN:
1323 /* If file exists open. If file doesn't exist error. */
1324 if (!file_existed) {
1325 DEBUG(5,("open_file_ntcreate: FILE_OPEN "
1326 "requested for file %s and file "
1327 "doesn't exist.\n", fname ));
1328 set_saved_error_triple(ERRDOS, ERRbadfile, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1329 errno = ENOENT;
1330 return NULL;
1332 break;
1334 case FILE_OVERWRITE:
1335 /* If file exists overwrite. If file doesn't exist
1336 * error. */
1337 if (!file_existed) {
1338 DEBUG(5,("open_file_ntcreate: FILE_OVERWRITE "
1339 "requested for file %s and file "
1340 "doesn't exist.\n", fname ));
1341 set_saved_error_triple(ERRDOS, ERRbadfile, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1342 errno = ENOENT;
1343 return NULL;
1345 flags2 |= O_TRUNC;
1346 break;
1348 case FILE_CREATE:
1349 /* If file exists error. If file doesn't exist
1350 * create. */
1351 if (file_existed) {
1352 DEBUG(5,("open_file_ntcreate: FILE_CREATE "
1353 "requested for file %s and file "
1354 "already exists.\n", fname ));
1355 if (S_ISDIR(psbuf->st_mode)) {
1356 errno = EISDIR;
1357 } else {
1358 errno = EEXIST;
1360 return NULL;
1362 flags2 |= (O_CREAT|O_EXCL);
1363 break;
1365 case FILE_OPEN_IF:
1366 /* If file exists open. If file doesn't exist
1367 * create. */
1368 flags2 |= O_CREAT;
1369 break;
1371 default:
1372 set_saved_error_triple(ERRDOS, ERRinvalidparam,
1373 NT_STATUS_INVALID_PARAMETER);
1374 return NULL;
1377 /* We only care about matching attributes on file exists and
1378 * overwrite. */
1380 if (file_existed && ((create_disposition == FILE_OVERWRITE) ||
1381 (create_disposition == FILE_OVERWRITE_IF))) {
1382 if (!open_match_attributes(conn, fname,
1383 existing_dos_attributes,
1384 new_dos_attributes, psbuf->st_mode,
1385 unx_mode, &new_unx_mode)) {
1386 DEBUG(5,("open_file_ntcreate: attributes missmatch "
1387 "for file %s (%x %x) (0%o, 0%o)\n",
1388 fname, existing_dos_attributes,
1389 new_dos_attributes,
1390 (unsigned int)psbuf->st_mode,
1391 (unsigned int)unx_mode ));
1392 errno = EACCES;
1393 return NULL;
1397 /* This is a nasty hack - must fix... JRA. */
1398 if (access_mask == MAXIMUM_ALLOWED_ACCESS) {
1399 access_mask = FILE_GENERIC_ALL;
1403 * Convert GENERIC bits to specific bits.
1406 se_map_generic(&access_mask, &file_generic_mapping);
1408 DEBUG(10, ("open_file_ntcreate: fname=%s, after mapping "
1409 "access_mask=0x%x\n", fname, access_mask ));
1412 * Note that we ignore the append flag as append does not
1413 * mean the same thing under DOS and Unix.
1416 if (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) {
1417 flags = O_RDWR;
1418 } else {
1419 flags = O_RDONLY;
1423 * Currently we only look at FILE_WRITE_THROUGH for create options.
1426 #if defined(O_SYNC)
1427 if (create_options & FILE_WRITE_THROUGH) {
1428 flags2 |= O_SYNC;
1430 #endif /* O_SYNC */
1432 if (!CAN_WRITE(conn)) {
1434 * We should really return a permission denied error if either
1435 * O_CREAT or O_TRUNC are set, but for compatibility with
1436 * older versions of Samba we just AND them out.
1438 flags2 &= ~(O_CREAT|O_TRUNC);
1442 * Ensure we can't write on a read-only share or file.
1445 if (flags != O_RDONLY && file_existed &&
1446 (!CAN_WRITE(conn) || IS_DOS_READONLY(existing_dos_attributes))) {
1447 DEBUG(5,("open_file_ntcreate: write access requested for "
1448 "file %s on read only %s\n",
1449 fname, !CAN_WRITE(conn) ? "share" : "file" ));
1450 set_saved_error_triple(ERRDOS, ERRnoaccess,
1451 NT_STATUS_ACCESS_DENIED);
1452 errno = EACCES;
1453 return NULL;
1456 fsp = file_new(conn);
1457 if(!fsp) {
1458 return NULL;
1461 if (file_existed) {
1463 dev = psbuf->st_dev;
1464 inode = psbuf->st_ino;
1466 lock_share_entry(conn, dev, inode);
1468 num_share_modes = open_mode_check(conn, fname, dev, inode,
1469 access_mask, share_access,
1470 create_options,
1471 &oplock_request,
1472 &all_current_opens_are_level_II);
1473 if(num_share_modes == -1) {
1475 if (!internal_only_open) {
1476 NTSTATUS status;
1477 get_saved_error_triple(NULL, NULL, &status);
1478 if (NT_STATUS_EQUAL(status,NT_STATUS_SHARING_VIOLATION)) {
1479 /* Check if this can be done with the
1480 * deny_dos and fcb calls. */
1481 if (create_options &
1482 (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
1483 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
1484 files_struct *fsp_dup;
1485 fsp_dup = fcb_or_dos_open(conn, fname, dev,
1486 inode, access_mask,
1487 share_access,
1488 create_options);
1490 if (fsp_dup) {
1491 unlock_share_entry(conn, dev, inode);
1492 file_free(fsp);
1493 if (pinfo) {
1494 *pinfo = FILE_WAS_OPENED;
1496 conn->num_files_open++;
1497 return fsp_dup;
1504 * This next line is a subtlety we need for
1505 * MS-Access. If a file open will fail due to share
1506 * permissions and also for security (access) reasons,
1507 * we need to return the access failed error, not the
1508 * share error. This means we must attempt to open the
1509 * file anyway in order to get the UNIX access error -
1510 * even if we're going to fail the open for share
1511 * reasons. This is bad, as we're burning another fd
1512 * if there are existing locks but there's nothing
1513 * else we can do. We also ensure we're not going to
1514 * create or tuncate the file as we only want an
1515 * access decision at this stage. JRA.
1517 errno = 0;
1518 fsp_open = open_file(fsp,conn,fname,psbuf,
1519 flags|(flags2&~(O_TRUNC|O_CREAT)),
1520 unx_mode,access_mask);
1522 DEBUG(4,("open_file_ntcreate : share_mode deny - "
1523 "calling open_file with flags=0x%X "
1524 "flags2=0x%X mode=0%o returned %d\n",
1525 flags, (flags2&~(O_TRUNC|O_CREAT)),
1526 (unsigned int)unx_mode, (int)fsp_open ));
1528 if (!fsp_open && errno) {
1529 /* Default error. */
1530 set_saved_error_triple(ERRDOS, ERRnoaccess,
1531 NT_STATUS_ACCESS_DENIED);
1535 * If we're returning a share violation, ensure we
1536 * cope with the braindead 1 second delay.
1539 if (!internal_only_open) {
1540 NTSTATUS status;
1541 get_saved_error_triple(NULL, NULL, &status);
1542 if (NT_STATUS_EQUAL(status,NT_STATUS_SHARING_VIOLATION)) {
1543 /* The fsp->open_time here represents
1544 * the current time of day. */
1545 defer_open_sharing_error(conn,
1546 &fsp->open_time,
1547 fname, dev, inode);
1551 unlock_share_entry(conn, dev, inode);
1552 if (fsp_open) {
1553 fd_close(conn, fsp);
1555 * We have detected a sharing violation here
1556 * so return the correct error code
1558 set_saved_error_triple(ERRDOS, ERRbadshare,
1559 NT_STATUS_SHARING_VIOLATION);
1561 file_free(fsp);
1562 return NULL;
1566 * We exit this block with the share entry *locked*.....
1571 * Ensure we pay attention to default ACLs on directories if required.
1574 if ((flags2 & O_CREAT) && lp_inherit_acls(SNUM(conn)) &&
1575 (def_acl = directory_has_default_acl(conn, parent_dirname(fname)))) {
1576 unx_mode = 0777;
1579 DEBUG(4,("calling open_file with flags=0x%X flags2=0x%X mode=0%o\n",
1580 (unsigned int)flags,(unsigned int)flags2,(unsigned int)unx_mode));
1583 * open_file strips any O_TRUNC flags itself.
1586 fsp_open = open_file(fsp,conn,fname,psbuf,flags|flags2,unx_mode,access_mask);
1588 if (!fsp_open) {
1589 if(file_existed) {
1590 unlock_share_entry(conn, dev, inode);
1592 file_free(fsp);
1593 return NULL;
1597 * Deal with the race condition where two smbd's detect the file
1598 * doesn't exist and do the create at the same time. One of them will
1599 * win and set a share mode, the other (ie. this one) should check if
1600 * the requested share mode for this create is allowed.
1603 if (!file_existed) {
1606 * Now the file exists and fsp is successfully opened,
1607 * fsp->dev and fsp->inode are valid and should replace the
1608 * dev=0,inode=0 from a non existent file. Spotted by
1609 * Nadav Danieli <nadavd@exanet.com>. JRA.
1612 dev = fsp->dev;
1613 inode = fsp->inode;
1615 lock_share_entry_fsp(fsp);
1617 num_share_modes = open_mode_check(conn, fname, dev, inode,
1618 access_mask, share_access,
1619 create_options,
1620 &oplock_request,
1621 &all_current_opens_are_level_II);
1623 if(num_share_modes == -1) {
1624 NTSTATUS status;
1625 get_saved_error_triple(NULL, NULL, &status);
1626 if (NT_STATUS_EQUAL(status,NT_STATUS_SHARING_VIOLATION)) {
1627 /* Check if this can be done with the deny_dos
1628 * and fcb calls. */
1629 if (create_options &
1630 (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
1631 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
1632 files_struct *fsp_dup;
1633 fsp_dup = fcb_or_dos_open(conn, fname, dev, inode,
1634 access_mask, share_access,
1635 create_options);
1636 if (fsp_dup) {
1637 unlock_share_entry(conn, dev, inode);
1638 fd_close(conn, fsp);
1639 file_free(fsp);
1640 if (pinfo) {
1641 *pinfo = FILE_WAS_OPENED;
1643 conn->num_files_open++;
1644 return fsp_dup;
1649 * If we're returning a share violation,
1650 * ensure we cope with the braindead 1 second
1651 * delay.
1654 /* The fsp->open_time here represents the
1655 * current time of day. */
1656 defer_open_sharing_error(conn, &fsp->open_time,
1657 fname, dev, inode);
1660 unlock_share_entry_fsp(fsp);
1661 fd_close(conn,fsp);
1662 file_free(fsp);
1664 * We have detected a sharing violation here, so
1665 * return the correct code.
1667 set_saved_error_triple(ERRDOS, ERRbadshare,
1668 NT_STATUS_SHARING_VIOLATION);
1669 return NULL;
1673 * If there are any share modes set then the file *did*
1674 * exist. Ensure we return the correct value for action.
1677 if (num_share_modes > 0) {
1678 file_existed = True;
1682 * We exit this block with the share entry *locked*.....
1686 /* note that we ignore failure for the following. It is
1687 basically a hack for NFS, and NFS will never set one of
1688 these only read them. Nobody but Samba can ever set a deny
1689 mode and we have already checked our more authoritative
1690 locking database for permission to set this deny mode. If
1691 the kernel refuses the operations then the kernel is wrong */
1693 kernel_flock(fsp, share_access);
1696 * At this point onwards, we can guarentee that the share entry
1697 * is locked, whether we created the file or not, and that the
1698 * deny mode is compatible with all current opens.
1702 * If requested, truncate the file.
1705 if (flags2&O_TRUNC) {
1707 * We are modifing the file after open - update the stat
1708 * struct..
1710 if ((SMB_VFS_FTRUNCATE(fsp,fsp->fh->fd,0) == -1) ||
1711 (SMB_VFS_FSTAT(fsp,fsp->fh->fd,psbuf)==-1)) {
1712 unlock_share_entry_fsp(fsp);
1713 fd_close(conn,fsp);
1714 file_free(fsp);
1715 return NULL;
1719 /* Record the options we were opened with. */
1720 fsp->share_access = share_access;
1721 fsp->fh->private_options = create_options;
1722 fsp->access_mask = access_mask;
1724 if (file_existed) {
1725 if (!(flags2 & O_TRUNC)) {
1726 info = FILE_WAS_OPENED;
1727 } else {
1728 info = FILE_WAS_OVERWRITTEN;
1730 } else {
1731 info = FILE_WAS_CREATED;
1732 /* Change the owner if required. */
1733 if (lp_inherit_owner(SNUM(conn))) {
1734 change_owner_to_parent(conn, fsp, fsp->fsp_name,
1735 psbuf);
1739 if (pinfo) {
1740 *pinfo = info;
1744 * Setup the oplock info in both the shared memory and
1745 * file structs.
1748 if(oplock_request && (num_share_modes == 0) &&
1749 !IS_VETO_OPLOCK_PATH(conn,fname) &&
1750 set_file_oplock(fsp, oplock_request) ) {
1751 port = global_oplock_port;
1752 } else if (oplock_request && all_current_opens_are_level_II) {
1753 port = global_oplock_port;
1754 oplock_request = LEVEL_II_OPLOCK;
1755 set_file_oplock(fsp, oplock_request);
1756 } else {
1757 port = 0;
1758 oplock_request = 0;
1761 set_share_mode(fsp, port, oplock_request);
1763 if (create_options & FILE_DELETE_ON_CLOSE) {
1764 uint32 dosattr= existing_dos_attributes;
1765 NTSTATUS result;
1767 if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED ||
1768 info == FILE_WAS_SUPERSEDED) {
1769 dosattr = new_dos_attributes;
1772 result = can_set_delete_on_close(fsp, True, dosattr);
1774 if (!NT_STATUS_IS_OK(result)) {
1775 uint8 u_e_c;
1776 uint32 u_e_code;
1777 BOOL dummy_del_on_close;
1778 /* Remember to delete the mode we just added. */
1779 del_share_mode(fsp, NULL, &dummy_del_on_close);
1780 unlock_share_entry_fsp(fsp);
1781 fd_close(conn,fsp);
1782 file_free(fsp);
1783 ntstatus_to_dos(result, &u_e_c, &u_e_code);
1784 set_saved_error_triple(u_e_c, u_e_code, result);
1785 return NULL;
1787 set_delete_on_close(fsp, True);
1790 if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED ||
1791 info == FILE_WAS_SUPERSEDED) {
1792 /* Files should be initially set as archive */
1793 if (lp_map_archive(SNUM(conn)) ||
1794 lp_store_dos_attributes(SNUM(conn))) {
1795 file_set_dosmode(conn, fname,
1796 new_dos_attributes | aARCH, NULL,
1797 True);
1802 * Take care of inherited ACLs on created files - if default ACL not
1803 * selected.
1806 if (!file_existed && !def_acl) {
1808 int saved_errno = errno; /* We might get ENOSYS in the next
1809 * call.. */
1811 if (SMB_VFS_FCHMOD_ACL(fsp, fsp->fh->fd, unx_mode) == -1
1812 && errno == ENOSYS) {
1813 errno = saved_errno; /* Ignore ENOSYS */
1816 } else if (new_unx_mode) {
1818 int ret = -1;
1820 /* Attributes need changing. File already existed. */
1823 int saved_errno = errno; /* We might get ENOSYS in the
1824 * next call.. */
1825 ret = SMB_VFS_FCHMOD_ACL(fsp, fsp->fh->fd,
1826 new_unx_mode);
1828 if (ret == -1 && errno == ENOSYS) {
1829 errno = saved_errno; /* Ignore ENOSYS */
1830 } else {
1831 DEBUG(5, ("open_file_shared: failed to reset "
1832 "attributes of file %s to 0%o\n",
1833 fname, (unsigned int)new_unx_mode));
1834 ret = 0; /* Don't do the fchmod below. */
1838 if ((ret == -1) &&
1839 (SMB_VFS_FCHMOD(fsp, fsp->fh->fd, new_unx_mode) == -1))
1840 DEBUG(5, ("open_file_shared: failed to reset "
1841 "attributes of file %s to 0%o\n",
1842 fname, (unsigned int)new_unx_mode));
1845 /* If this is a successful open, we must remove any deferred open
1846 * records. */
1847 delete_defered_open_entry_record(conn, fsp->dev, fsp->inode);
1848 unlock_share_entry_fsp(fsp);
1850 conn->num_files_open++;
1852 return fsp;
1855 /****************************************************************************
1856 Open a file for for write to ensure that we can fchmod it.
1857 ****************************************************************************/
1859 files_struct *open_file_fchmod(connection_struct *conn, const char *fname,
1860 SMB_STRUCT_STAT *psbuf)
1862 files_struct *fsp = NULL;
1863 BOOL fsp_open;
1865 if (!VALID_STAT(*psbuf)) {
1866 return NULL;
1869 fsp = file_new(conn);
1870 if(!fsp) {
1871 return NULL;
1874 /* note! we must use a non-zero desired access or we don't get
1875 a real file descriptor. Oh what a twisted web we weave. */
1876 fsp_open = open_file(fsp,conn,fname,psbuf,O_WRONLY,0,FILE_WRITE_DATA);
1879 * This is not a user visible file open.
1880 * Don't set a share mode and don't increment
1881 * the conn->num_files_open.
1884 if (!fsp_open) {
1885 file_free(fsp);
1886 return NULL;
1889 return fsp;
1892 /****************************************************************************
1893 Close the fchmod file fd - ensure no locks are lost.
1894 ****************************************************************************/
1896 int close_file_fchmod(files_struct *fsp)
1898 int ret = fd_close(fsp->conn, fsp);
1899 file_free(fsp);
1900 return ret;
1903 /****************************************************************************
1904 Open a directory from an NT SMB call.
1905 ****************************************************************************/
1907 files_struct *open_directory(connection_struct *conn,
1908 const char *fname,
1909 SMB_STRUCT_STAT *psbuf,
1910 uint32 access_mask,
1911 uint32 share_access,
1912 uint32 create_disposition,
1913 uint32 create_options,
1914 int *pinfo)
1916 files_struct *fsp = NULL;
1917 BOOL dir_existed = VALID_STAT(*psbuf) ? True : False;
1918 BOOL create_dir = False;
1919 int info = 0;
1921 DEBUG(5,("open_directory: opening directory %s, access_mask = 0x%x, "
1922 "share_access = 0x%x create_options = 0x%x, "
1923 "create_disposition = 0x%x\n",
1924 fname,
1925 (unsigned int)access_mask,
1926 (unsigned int)share_access,
1927 (unsigned int)create_options,
1928 (unsigned int)create_disposition));
1930 if (is_ntfs_stream_name(fname)) {
1931 DEBUG(0,("open_directory: %s is a stream name!\n", fname ));
1932 /* NB. Is the DOS error ERRbadpath or ERRbaddirectory ? */
1933 set_saved_error_triple(ERRDOS, ERRbadpath,
1934 NT_STATUS_NOT_A_DIRECTORY);
1935 return NULL;
1938 if (dir_existed && !S_ISDIR(psbuf->st_mode)) {
1939 DEBUG(0,("open_directory: %s is not a directory !\n", fname ));
1940 /* NB. Is the DOS error ERRbadpath or ERRbaddirectory ? */
1941 set_saved_error_triple(ERRDOS, ERRbadpath,
1942 NT_STATUS_NOT_A_DIRECTORY);
1943 return NULL;
1946 switch( create_disposition ) {
1947 case FILE_OPEN:
1948 /* If directory exists open. If directory doesn't
1949 * exist error. */
1950 if (!dir_existed) {
1951 DEBUG(5,("open_directory: FILE_OPEN requested "
1952 "for directory %s and it doesn't "
1953 "exist.\n", fname ));
1954 set_saved_error_triple(ERRDOS, ERRbadfile,
1955 NT_STATUS_OBJECT_NAME_NOT_FOUND);
1956 return NULL;
1958 info = FILE_WAS_OPENED;
1959 break;
1961 case FILE_CREATE:
1962 /* If directory exists error. If directory doesn't
1963 * exist create. */
1964 if (dir_existed) {
1965 DEBUG(5,("open_directory: FILE_CREATE "
1966 "requested for directory %s and it "
1967 "already exists.\n", fname ));
1968 set_saved_error_triple(ERRDOS, ERRfilexists,
1969 NT_STATUS_OBJECT_NAME_COLLISION);
1970 return NULL;
1972 create_dir = True;
1973 info = FILE_WAS_CREATED;
1974 break;
1976 case FILE_OPEN_IF:
1977 /* If directory exists open. If directory doesn't
1978 * exist create. */
1979 if (!dir_existed) {
1980 create_dir = True;
1981 info = FILE_WAS_CREATED;
1982 } else {
1983 info = FILE_WAS_OPENED;
1985 break;
1987 case FILE_SUPERSEDE:
1988 case FILE_OVERWRITE:
1989 case FILE_OVERWRITE_IF:
1990 default:
1991 DEBUG(5,("open_directory: invalid create_disposition "
1992 "0x%x for directory %s\n",
1993 (unsigned int)create_disposition, fname));
1994 file_free(fsp);
1995 set_saved_error_triple(ERRDOS, ERRinvalidparam,
1996 NT_STATUS_INVALID_PARAMETER);
1997 return NULL;
2000 if (create_dir) {
2002 * Try and create the directory.
2005 /* We know bad_path is false as it's caught earlier. */
2007 NTSTATUS status = mkdir_internal(conn, fname, False);
2009 if (!NT_STATUS_IS_OK(status)) {
2010 DEBUG(2,("open_directory: unable to create %s. "
2011 "Error was %s\n", fname, strerror(errno) ));
2012 /* Ensure we return the correct NT status to the
2013 * client. */
2014 set_saved_error_triple(0, 0, status);
2015 return NULL;
2018 /* Ensure we're checking for a symlink here.... */
2019 /* We don't want to get caught by a symlink racer. */
2021 if(SMB_VFS_LSTAT(conn,fname, psbuf) != 0) {
2022 return NULL;
2025 if(!S_ISDIR(psbuf->st_mode)) {
2026 DEBUG(0,("open_directory: %s is not a directory !\n",
2027 fname ));
2028 return NULL;
2032 fsp = file_new(conn);
2033 if(!fsp) {
2034 return NULL;
2038 * Setup the files_struct for it.
2041 fsp->mode = psbuf->st_mode;
2042 fsp->inode = psbuf->st_ino;
2043 fsp->dev = psbuf->st_dev;
2044 fsp->vuid = current_user.vuid;
2045 fsp->file_pid = global_smbpid;
2046 fsp->can_lock = True;
2047 fsp->can_read = False;
2048 fsp->can_write = False;
2050 fsp->share_access = share_access;
2051 fsp->fh->private_options = create_options;
2052 fsp->access_mask = access_mask;
2054 fsp->print_file = False;
2055 fsp->modified = False;
2056 fsp->oplock_type = NO_OPLOCK;
2057 fsp->sent_oplock_break = NO_BREAK_SENT;
2058 fsp->is_directory = True;
2059 fsp->is_stat = False;
2060 string_set(&fsp->fsp_name,fname);
2062 if (create_options & FILE_DELETE_ON_CLOSE) {
2063 NTSTATUS status = can_set_delete_on_close(fsp, True, 0);
2064 if (!NT_STATUS_IS_OK(status)) {
2065 file_free(fsp);
2066 return NULL;
2070 /* Change the owner if required. */
2071 if ((info == FILE_WAS_CREATED) && lp_inherit_owner(SNUM(conn))) {
2072 change_owner_to_parent(conn, fsp, fsp->fsp_name, psbuf);
2075 if (pinfo) {
2076 *pinfo = info;
2079 conn->num_files_open++;
2081 return fsp;
2084 /****************************************************************************
2085 Open a pseudo-file (no locking checks - a 'stat' open).
2086 ****************************************************************************/
2088 files_struct *open_file_stat(connection_struct *conn, char *fname,
2089 SMB_STRUCT_STAT *psbuf)
2091 files_struct *fsp = NULL;
2093 if (!VALID_STAT(*psbuf))
2094 return NULL;
2096 /* Can't 'stat' open directories. */
2097 if(S_ISDIR(psbuf->st_mode))
2098 return NULL;
2100 fsp = file_new(conn);
2101 if(!fsp)
2102 return NULL;
2104 DEBUG(5,("open_file_stat: 'opening' file %s\n", fname));
2107 * Setup the files_struct for it.
2110 fsp->mode = psbuf->st_mode;
2111 fsp->inode = psbuf->st_ino;
2112 fsp->dev = psbuf->st_dev;
2113 fsp->vuid = current_user.vuid;
2114 fsp->file_pid = global_smbpid;
2115 fsp->can_lock = False;
2116 fsp->can_read = False;
2117 fsp->can_write = False;
2118 fsp->print_file = False;
2119 fsp->modified = False;
2120 fsp->oplock_type = NO_OPLOCK;
2121 fsp->sent_oplock_break = NO_BREAK_SENT;
2122 fsp->is_directory = False;
2123 fsp->is_stat = True;
2124 string_set(&fsp->fsp_name,fname);
2126 conn->num_files_open++;
2128 return fsp;