s3: Re-run make samba3-idl.
[Samba/gebeck_regimport.git] / source3 / smbd / open.c
blob0834e6d3d3950c679c6f67b05cf76f16ecb0bbf9
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 3 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, see <http://www.gnu.org/licenses/>.
22 #include "includes.h"
23 #include "smbd/globals.h"
25 extern const struct generic_mapping file_generic_mapping;
27 struct deferred_open_record {
28 bool delayed_for_oplocks;
29 struct file_id id;
32 static NTSTATUS create_file_unixpath(connection_struct *conn,
33 struct smb_request *req,
34 struct smb_filename *smb_fname,
35 uint32_t access_mask,
36 uint32_t share_access,
37 uint32_t create_disposition,
38 uint32_t create_options,
39 uint32_t file_attributes,
40 uint32_t oplock_request,
41 uint64_t allocation_size,
42 uint32_t private_flags,
43 struct security_descriptor *sd,
44 struct ea_list *ea_list,
46 files_struct **result,
47 int *pinfo);
49 /****************************************************************************
50 SMB1 file varient of se_access_check. Never test FILE_READ_ATTRIBUTES.
51 ****************************************************************************/
53 NTSTATUS smb1_file_se_access_check(struct connection_struct *conn,
54 const struct security_descriptor *sd,
55 const NT_USER_TOKEN *token,
56 uint32_t access_desired,
57 uint32_t *access_granted)
59 *access_granted = 0;
61 if (get_current_uid(conn) == (uid_t)0) {
62 /* I'm sorry sir, I didn't know you were root... */
63 *access_granted = access_desired;
64 if (access_desired & SEC_FLAG_MAXIMUM_ALLOWED) {
65 *access_granted |= FILE_GENERIC_ALL;
67 return NT_STATUS_OK;
70 return se_access_check(sd,
71 token,
72 (access_desired & ~FILE_READ_ATTRIBUTES),
73 access_granted);
76 /****************************************************************************
77 Check if we have open rights.
78 ****************************************************************************/
80 NTSTATUS smbd_check_open_rights(struct connection_struct *conn,
81 const struct smb_filename *smb_fname,
82 uint32_t access_mask,
83 uint32_t *access_granted)
85 /* Check if we have rights to open. */
86 NTSTATUS status;
87 struct security_descriptor *sd = NULL;
89 status = SMB_VFS_GET_NT_ACL(conn, smb_fname->base_name,
90 (OWNER_SECURITY_INFORMATION |
91 GROUP_SECURITY_INFORMATION |
92 DACL_SECURITY_INFORMATION),&sd);
94 if (!NT_STATUS_IS_OK(status)) {
95 DEBUG(10, ("smbd_check_open_rights: Could not get acl "
96 "on %s: %s\n",
97 smb_fname_str_dbg(smb_fname),
98 nt_errstr(status)));
99 return status;
102 status = smb1_file_se_access_check(conn,
104 get_current_nttok(conn),
105 access_mask,
106 access_granted);
108 DEBUG(10,("smbd_check_open_rights: file %s requesting "
109 "0x%x returning 0x%x (%s)\n",
110 smb_fname_str_dbg(smb_fname),
111 (unsigned int)access_mask,
112 (unsigned int)*access_granted,
113 nt_errstr(status) ));
115 if (!NT_STATUS_IS_OK(status)) {
116 if (DEBUGLEVEL >= 10) {
117 DEBUG(10,("smbd_check_open_rights: acl for %s is:\n",
118 smb_fname_str_dbg(smb_fname) ));
119 NDR_PRINT_DEBUG(security_descriptor, sd);
123 TALLOC_FREE(sd);
125 return status;
128 /****************************************************************************
129 fd support routines - attempt to do a dos_open.
130 ****************************************************************************/
132 static NTSTATUS fd_open(struct connection_struct *conn,
133 files_struct *fsp,
134 int flags,
135 mode_t mode)
137 struct smb_filename *smb_fname = fsp->fsp_name;
138 NTSTATUS status = NT_STATUS_OK;
140 #ifdef O_NOFOLLOW
142 * Never follow symlinks on a POSIX client. The
143 * client should be doing this.
146 if (fsp->posix_open || !lp_symlinks(SNUM(conn))) {
147 flags |= O_NOFOLLOW;
149 #endif
151 fsp->fh->fd = SMB_VFS_OPEN(conn, smb_fname, fsp, flags, mode);
152 if (fsp->fh->fd == -1) {
153 status = map_nt_error_from_unix(errno);
154 if (errno == EMFILE) {
155 static time_t last_warned = 0L;
157 if (time((time_t *) NULL) > last_warned) {
158 DEBUG(0,("Too many open files, unable "
159 "to open more! smbd's max "
160 "open files = %d\n",
161 lp_max_open_files()));
162 last_warned = time((time_t *) NULL);
168 DEBUG(10,("fd_open: name %s, flags = 0%o mode = 0%o, fd = %d. %s\n",
169 smb_fname_str_dbg(smb_fname), flags, (int)mode, fsp->fh->fd,
170 (fsp->fh->fd == -1) ? strerror(errno) : "" ));
172 return status;
175 /****************************************************************************
176 Close the file associated with a fsp.
177 ****************************************************************************/
179 NTSTATUS fd_close(files_struct *fsp)
181 int ret;
183 if (fsp->fh->fd == -1) {
184 return NT_STATUS_OK; /* What we used to call a stat open. */
186 if (fsp->fh->ref_count > 1) {
187 return NT_STATUS_OK; /* Shared handle. Only close last reference. */
190 ret = SMB_VFS_CLOSE(fsp);
191 fsp->fh->fd = -1;
192 if (ret == -1) {
193 return map_nt_error_from_unix(errno);
195 return NT_STATUS_OK;
198 /****************************************************************************
199 Change the ownership of a file to that of the parent directory.
200 Do this by fd if possible.
201 ****************************************************************************/
203 void change_file_owner_to_parent(connection_struct *conn,
204 const char *inherit_from_dir,
205 files_struct *fsp)
207 struct smb_filename *smb_fname_parent = NULL;
208 NTSTATUS status;
209 int ret;
211 status = create_synthetic_smb_fname(talloc_tos(), inherit_from_dir,
212 NULL, NULL, &smb_fname_parent);
213 if (!NT_STATUS_IS_OK(status)) {
214 return;
217 ret = SMB_VFS_STAT(conn, smb_fname_parent);
218 if (ret == -1) {
219 DEBUG(0,("change_file_owner_to_parent: failed to stat parent "
220 "directory %s. Error was %s\n",
221 smb_fname_str_dbg(smb_fname_parent),
222 strerror(errno)));
223 return;
226 become_root();
227 ret = SMB_VFS_FCHOWN(fsp, smb_fname_parent->st.st_ex_uid, (gid_t)-1);
228 unbecome_root();
229 if (ret == -1) {
230 DEBUG(0,("change_file_owner_to_parent: failed to fchown "
231 "file %s to parent directory uid %u. Error "
232 "was %s\n", fsp_str_dbg(fsp),
233 (unsigned int)smb_fname_parent->st.st_ex_uid,
234 strerror(errno) ));
237 DEBUG(10,("change_file_owner_to_parent: changed new file %s to "
238 "parent directory uid %u.\n", fsp_str_dbg(fsp),
239 (unsigned int)smb_fname_parent->st.st_ex_uid));
241 TALLOC_FREE(smb_fname_parent);
244 NTSTATUS change_dir_owner_to_parent(connection_struct *conn,
245 const char *inherit_from_dir,
246 const char *fname,
247 SMB_STRUCT_STAT *psbuf)
249 struct smb_filename *smb_fname_parent = NULL;
250 struct smb_filename *smb_fname_cwd = NULL;
251 char *saved_dir = NULL;
252 TALLOC_CTX *ctx = talloc_tos();
253 NTSTATUS status = NT_STATUS_OK;
254 int ret;
256 status = create_synthetic_smb_fname(ctx, inherit_from_dir, NULL, NULL,
257 &smb_fname_parent);
258 if (!NT_STATUS_IS_OK(status)) {
259 return status;
262 ret = SMB_VFS_STAT(conn, smb_fname_parent);
263 if (ret == -1) {
264 status = map_nt_error_from_unix(errno);
265 DEBUG(0,("change_dir_owner_to_parent: failed to stat parent "
266 "directory %s. Error was %s\n",
267 smb_fname_str_dbg(smb_fname_parent),
268 strerror(errno)));
269 goto out;
272 /* We've already done an lstat into psbuf, and we know it's a
273 directory. If we can cd into the directory and the dev/ino
274 are the same then we can safely chown without races as
275 we're locking the directory in place by being in it. This
276 should work on any UNIX (thanks tridge :-). JRA.
279 saved_dir = vfs_GetWd(ctx,conn);
280 if (!saved_dir) {
281 status = map_nt_error_from_unix(errno);
282 DEBUG(0,("change_dir_owner_to_parent: failed to get "
283 "current working directory. Error was %s\n",
284 strerror(errno)));
285 goto out;
288 /* Chdir into the new path. */
289 if (vfs_ChDir(conn, fname) == -1) {
290 status = map_nt_error_from_unix(errno);
291 DEBUG(0,("change_dir_owner_to_parent: failed to change "
292 "current working directory to %s. Error "
293 "was %s\n", fname, strerror(errno) ));
294 goto chdir;
297 status = create_synthetic_smb_fname(ctx, ".", NULL, NULL,
298 &smb_fname_cwd);
299 if (!NT_STATUS_IS_OK(status)) {
300 return status;
303 ret = SMB_VFS_STAT(conn, smb_fname_cwd);
304 if (ret == -1) {
305 status = map_nt_error_from_unix(errno);
306 DEBUG(0,("change_dir_owner_to_parent: failed to stat "
307 "directory '.' (%s) Error was %s\n",
308 fname, strerror(errno)));
309 goto chdir;
312 /* Ensure we're pointing at the same place. */
313 if (smb_fname_cwd->st.st_ex_dev != psbuf->st_ex_dev ||
314 smb_fname_cwd->st.st_ex_ino != psbuf->st_ex_ino ||
315 smb_fname_cwd->st.st_ex_mode != psbuf->st_ex_mode ) {
316 DEBUG(0,("change_dir_owner_to_parent: "
317 "device/inode/mode on directory %s changed. "
318 "Refusing to chown !\n", fname ));
319 status = NT_STATUS_ACCESS_DENIED;
320 goto chdir;
323 become_root();
324 ret = SMB_VFS_CHOWN(conn, ".", smb_fname_parent->st.st_ex_uid,
325 (gid_t)-1);
326 unbecome_root();
327 if (ret == -1) {
328 status = map_nt_error_from_unix(errno);
329 DEBUG(10,("change_dir_owner_to_parent: failed to chown "
330 "directory %s to parent directory uid %u. "
331 "Error was %s\n", fname,
332 (unsigned int)smb_fname_parent->st.st_ex_uid,
333 strerror(errno) ));
334 goto chdir;
337 DEBUG(10,("change_dir_owner_to_parent: changed ownership of new "
338 "directory %s to parent directory uid %u.\n",
339 fname, (unsigned int)smb_fname_parent->st.st_ex_uid ));
341 chdir:
342 vfs_ChDir(conn,saved_dir);
343 out:
344 TALLOC_FREE(smb_fname_parent);
345 TALLOC_FREE(smb_fname_cwd);
346 return status;
349 /****************************************************************************
350 Open a file.
351 ****************************************************************************/
353 static NTSTATUS open_file(files_struct *fsp,
354 connection_struct *conn,
355 struct smb_request *req,
356 const char *parent_dir,
357 int flags,
358 mode_t unx_mode,
359 uint32 access_mask, /* client requested access mask. */
360 uint32 open_access_mask) /* what we're actually using in the open. */
362 struct smb_filename *smb_fname = fsp->fsp_name;
363 NTSTATUS status = NT_STATUS_OK;
364 int accmode = (flags & O_ACCMODE);
365 int local_flags = flags;
366 bool file_existed = VALID_STAT(fsp->fsp_name->st);
368 fsp->fh->fd = -1;
369 errno = EPERM;
371 /* Check permissions */
374 * This code was changed after seeing a client open request
375 * containing the open mode of (DENY_WRITE/read-only) with
376 * the 'create if not exist' bit set. The previous code
377 * would fail to open the file read only on a read-only share
378 * as it was checking the flags parameter directly against O_RDONLY,
379 * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
380 * JRA.
383 if (!CAN_WRITE(conn)) {
384 /* It's a read-only share - fail if we wanted to write. */
385 if(accmode != O_RDONLY || (flags & O_TRUNC) || (flags & O_APPEND)) {
386 DEBUG(3,("Permission denied opening %s\n",
387 smb_fname_str_dbg(smb_fname)));
388 return NT_STATUS_ACCESS_DENIED;
389 } else if(flags & O_CREAT) {
390 /* We don't want to write - but we must make sure that
391 O_CREAT doesn't create the file if we have write
392 access into the directory.
394 flags &= ~(O_CREAT|O_EXCL);
395 local_flags &= ~(O_CREAT|O_EXCL);
400 * This little piece of insanity is inspired by the
401 * fact that an NT client can open a file for O_RDONLY,
402 * but set the create disposition to FILE_EXISTS_TRUNCATE.
403 * If the client *can* write to the file, then it expects to
404 * truncate the file, even though it is opening for readonly.
405 * Quicken uses this stupid trick in backup file creation...
406 * Thanks *greatly* to "David W. Chapman Jr." <dwcjr@inethouston.net>
407 * for helping track this one down. It didn't bite us in 2.0.x
408 * as we always opened files read-write in that release. JRA.
411 if ((accmode == O_RDONLY) && ((flags & O_TRUNC) == O_TRUNC)) {
412 DEBUG(10,("open_file: truncate requested on read-only open "
413 "for file %s\n", smb_fname_str_dbg(smb_fname)));
414 local_flags = (flags & ~O_ACCMODE)|O_RDWR;
417 if ((open_access_mask & (FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA|FILE_EXECUTE)) ||
418 (!file_existed && (local_flags & O_CREAT)) ||
419 ((local_flags & O_TRUNC) == O_TRUNC) ) {
420 const char *wild;
423 * We can't actually truncate here as the file may be locked.
424 * open_file_ntcreate will take care of the truncate later. JRA.
427 local_flags &= ~O_TRUNC;
429 #if defined(O_NONBLOCK) && defined(S_ISFIFO)
431 * We would block on opening a FIFO with no one else on the
432 * other end. Do what we used to do and add O_NONBLOCK to the
433 * open flags. JRA.
436 if (file_existed && S_ISFIFO(smb_fname->st.st_ex_mode)) {
437 local_flags |= O_NONBLOCK;
439 #endif
441 /* Don't create files with Microsoft wildcard characters. */
442 if (fsp->base_fsp) {
444 * wildcard characters are allowed in stream names
445 * only test the basefilename
447 wild = fsp->base_fsp->fsp_name->base_name;
448 } else {
449 wild = smb_fname->base_name;
451 if ((local_flags & O_CREAT) && !file_existed &&
452 ms_has_wild(wild)) {
453 return NT_STATUS_OBJECT_NAME_INVALID;
456 /* Actually do the open */
457 status = fd_open(conn, fsp, local_flags, unx_mode);
458 if (!NT_STATUS_IS_OK(status)) {
459 DEBUG(3,("Error opening file %s (%s) (local_flags=%d) "
460 "(flags=%d)\n", smb_fname_str_dbg(smb_fname),
461 nt_errstr(status),local_flags,flags));
462 return status;
465 if ((local_flags & O_CREAT) && !file_existed) {
467 /* Inherit the ACL if required */
468 if (lp_inherit_perms(SNUM(conn))) {
469 inherit_access_posix_acl(conn, parent_dir,
470 smb_fname->base_name,
471 unx_mode);
474 /* Change the owner if required. */
475 if (lp_inherit_owner(SNUM(conn))) {
476 change_file_owner_to_parent(conn, parent_dir,
477 fsp);
480 notify_fname(conn, NOTIFY_ACTION_ADDED,
481 FILE_NOTIFY_CHANGE_FILE_NAME,
482 smb_fname->base_name);
485 } else {
486 fsp->fh->fd = -1; /* What we used to call a stat open. */
487 if (file_existed) {
488 uint32_t access_granted = 0;
490 status = smbd_check_open_rights(conn,
491 smb_fname,
492 access_mask,
493 &access_granted);
494 if (!NT_STATUS_IS_OK(status)) {
495 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
497 * On NT_STATUS_ACCESS_DENIED, access_granted
498 * contains the denied bits.
501 if ((access_mask & FILE_WRITE_ATTRIBUTES) &&
502 (access_granted & FILE_WRITE_ATTRIBUTES) &&
503 (lp_map_readonly(SNUM(conn)) ||
504 lp_map_archive(SNUM(conn)) ||
505 lp_map_hidden(SNUM(conn)) ||
506 lp_map_system(SNUM(conn)))) {
507 access_granted &= ~FILE_WRITE_ATTRIBUTES;
509 DEBUG(10,("open_file: "
510 "overrode "
511 "FILE_WRITE_"
512 "ATTRIBUTES "
513 "on file %s\n",
514 smb_fname_str_dbg(
515 smb_fname)));
518 if ((access_mask & DELETE_ACCESS) &&
519 (access_granted & DELETE_ACCESS) &&
520 can_delete_file_in_directory(conn,
521 smb_fname)) {
522 /* Were we trying to do a stat open
523 * for delete and didn't get DELETE
524 * access (only) ? Check if the
525 * directory allows DELETE_CHILD.
526 * See here:
527 * http://blogs.msdn.com/oldnewthing/archive/2004/06/04/148426.aspx
528 * for details. */
530 access_granted &= ~DELETE_ACCESS;
532 DEBUG(10,("open_file: "
533 "overrode "
534 "DELETE_ACCESS on "
535 "file %s\n",
536 smb_fname_str_dbg(
537 smb_fname)));
540 if (access_granted != 0) {
541 DEBUG(10,("open_file: Access "
542 "denied on file "
543 "%s\n",
544 smb_fname_str_dbg(
545 smb_fname)));
546 return status;
548 } else if (NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND) &&
549 fsp->posix_open &&
550 S_ISLNK(smb_fname->st.st_ex_mode)) {
551 /* This is a POSIX stat open for delete
552 * or rename on a symlink that points
553 * nowhere. Allow. */
554 DEBUG(10,("open_file: allowing POSIX "
555 "open on bad symlink %s\n",
556 smb_fname_str_dbg(
557 smb_fname)));
558 } else {
559 DEBUG(10,("open_file: "
560 "smbd_check_open_rights on file "
561 "%s returned %s\n",
562 smb_fname_str_dbg(smb_fname),
563 nt_errstr(status) ));
564 return status;
570 if (!file_existed) {
571 int ret;
573 if (fsp->fh->fd == -1) {
574 ret = SMB_VFS_STAT(conn, smb_fname);
575 } else {
576 ret = SMB_VFS_FSTAT(fsp, &smb_fname->st);
577 /* If we have an fd, this stat should succeed. */
578 if (ret == -1) {
579 DEBUG(0,("Error doing fstat on open file %s "
580 "(%s)\n",
581 smb_fname_str_dbg(smb_fname),
582 strerror(errno) ));
586 /* For a non-io open, this stat failing means file not found. JRA */
587 if (ret == -1) {
588 status = map_nt_error_from_unix(errno);
589 fd_close(fsp);
590 return status;
595 * POSIX allows read-only opens of directories. We don't
596 * want to do this (we use a different code path for this)
597 * so catch a directory open and return an EISDIR. JRA.
600 if(S_ISDIR(smb_fname->st.st_ex_mode)) {
601 fd_close(fsp);
602 errno = EISDIR;
603 return NT_STATUS_FILE_IS_A_DIRECTORY;
606 fsp->mode = smb_fname->st.st_ex_mode;
607 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
608 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
609 fsp->file_pid = req ? req->smbpid : 0;
610 fsp->can_lock = True;
611 fsp->can_read = (access_mask & (FILE_READ_DATA)) ? True : False;
612 if (!CAN_WRITE(conn)) {
613 fsp->can_write = False;
614 } else {
615 fsp->can_write = (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ?
616 True : False;
618 fsp->print_file = False;
619 fsp->modified = False;
620 fsp->sent_oplock_break = NO_BREAK_SENT;
621 fsp->is_directory = False;
622 if (conn->aio_write_behind_list &&
623 is_in_path(smb_fname->base_name, conn->aio_write_behind_list,
624 conn->case_sensitive)) {
625 fsp->aio_write_behind = True;
628 fsp->wcp = NULL; /* Write cache pointer. */
630 DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
631 conn->server_info->unix_name,
632 smb_fname_str_dbg(smb_fname),
633 BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
634 conn->num_files_open));
636 errno = 0;
637 return NT_STATUS_OK;
640 /*******************************************************************
641 Return True if the filename is one of the special executable types.
642 ********************************************************************/
644 bool is_executable(const char *fname)
646 if ((fname = strrchr_m(fname,'.'))) {
647 if (strequal(fname,".com") ||
648 strequal(fname,".dll") ||
649 strequal(fname,".exe") ||
650 strequal(fname,".sym")) {
651 return True;
654 return False;
657 /****************************************************************************
658 Check if we can open a file with a share mode.
659 Returns True if conflict, False if not.
660 ****************************************************************************/
662 static bool share_conflict(struct share_mode_entry *entry,
663 uint32 access_mask,
664 uint32 share_access)
666 DEBUG(10,("share_conflict: entry->access_mask = 0x%x, "
667 "entry->share_access = 0x%x, "
668 "entry->private_options = 0x%x\n",
669 (unsigned int)entry->access_mask,
670 (unsigned int)entry->share_access,
671 (unsigned int)entry->private_options));
673 DEBUG(10,("share_conflict: access_mask = 0x%x, share_access = 0x%x\n",
674 (unsigned int)access_mask, (unsigned int)share_access));
676 if ((entry->access_mask & (FILE_WRITE_DATA|
677 FILE_APPEND_DATA|
678 FILE_READ_DATA|
679 FILE_EXECUTE|
680 DELETE_ACCESS)) == 0) {
681 DEBUG(10,("share_conflict: No conflict due to "
682 "entry->access_mask = 0x%x\n",
683 (unsigned int)entry->access_mask ));
684 return False;
687 if ((access_mask & (FILE_WRITE_DATA|
688 FILE_APPEND_DATA|
689 FILE_READ_DATA|
690 FILE_EXECUTE|
691 DELETE_ACCESS)) == 0) {
692 DEBUG(10,("share_conflict: No conflict due to "
693 "access_mask = 0x%x\n",
694 (unsigned int)access_mask ));
695 return False;
698 #if 1 /* JRA TEST - Superdebug. */
699 #define CHECK_MASK(num, am, right, sa, share) \
700 DEBUG(10,("share_conflict: [%d] am (0x%x) & right (0x%x) = 0x%x\n", \
701 (unsigned int)(num), (unsigned int)(am), \
702 (unsigned int)(right), (unsigned int)(am)&(right) )); \
703 DEBUG(10,("share_conflict: [%d] sa (0x%x) & share (0x%x) = 0x%x\n", \
704 (unsigned int)(num), (unsigned int)(sa), \
705 (unsigned int)(share), (unsigned int)(sa)&(share) )); \
706 if (((am) & (right)) && !((sa) & (share))) { \
707 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
708 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
709 (unsigned int)(share) )); \
710 return True; \
712 #else
713 #define CHECK_MASK(num, am, right, sa, share) \
714 if (((am) & (right)) && !((sa) & (share))) { \
715 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
716 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
717 (unsigned int)(share) )); \
718 return True; \
720 #endif
722 CHECK_MASK(1, entry->access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
723 share_access, FILE_SHARE_WRITE);
724 CHECK_MASK(2, access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
725 entry->share_access, FILE_SHARE_WRITE);
727 CHECK_MASK(3, entry->access_mask, FILE_READ_DATA | FILE_EXECUTE,
728 share_access, FILE_SHARE_READ);
729 CHECK_MASK(4, access_mask, FILE_READ_DATA | FILE_EXECUTE,
730 entry->share_access, FILE_SHARE_READ);
732 CHECK_MASK(5, entry->access_mask, DELETE_ACCESS,
733 share_access, FILE_SHARE_DELETE);
734 CHECK_MASK(6, access_mask, DELETE_ACCESS,
735 entry->share_access, FILE_SHARE_DELETE);
737 DEBUG(10,("share_conflict: No conflict.\n"));
738 return False;
741 #if defined(DEVELOPER)
742 static void validate_my_share_entries(int num,
743 struct share_mode_entry *share_entry)
745 files_struct *fsp;
747 if (!procid_is_me(&share_entry->pid)) {
748 return;
751 if (is_deferred_open_entry(share_entry) &&
752 !open_was_deferred(share_entry->op_mid)) {
753 char *str = talloc_asprintf(talloc_tos(),
754 "Got a deferred entry without a request: "
755 "PANIC: %s\n",
756 share_mode_str(talloc_tos(), num, share_entry));
757 smb_panic(str);
760 if (!is_valid_share_mode_entry(share_entry)) {
761 return;
764 fsp = file_find_dif(share_entry->id,
765 share_entry->share_file_id);
766 if (!fsp) {
767 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
768 share_mode_str(talloc_tos(), num, share_entry) ));
769 smb_panic("validate_my_share_entries: Cannot match a "
770 "share entry with an open file\n");
773 if (is_deferred_open_entry(share_entry) ||
774 is_unused_share_mode_entry(share_entry)) {
775 goto panic;
778 if ((share_entry->op_type == NO_OPLOCK) &&
779 (fsp->oplock_type == FAKE_LEVEL_II_OPLOCK)) {
780 /* Someone has already written to it, but I haven't yet
781 * noticed */
782 return;
785 if (((uint16)fsp->oplock_type) != share_entry->op_type) {
786 goto panic;
789 return;
791 panic:
793 char *str;
794 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
795 share_mode_str(talloc_tos(), num, share_entry) ));
796 str = talloc_asprintf(talloc_tos(),
797 "validate_my_share_entries: "
798 "file %s, oplock_type = 0x%x, op_type = 0x%x\n",
799 fsp->fsp_name->base_name,
800 (unsigned int)fsp->oplock_type,
801 (unsigned int)share_entry->op_type );
802 smb_panic(str);
805 #endif
807 bool is_stat_open(uint32 access_mask)
809 return (access_mask &&
810 ((access_mask & ~(SYNCHRONIZE_ACCESS| FILE_READ_ATTRIBUTES|
811 FILE_WRITE_ATTRIBUTES))==0) &&
812 ((access_mask & (SYNCHRONIZE_ACCESS|FILE_READ_ATTRIBUTES|
813 FILE_WRITE_ATTRIBUTES)) != 0));
816 /****************************************************************************
817 Deal with share modes
818 Invarient: Share mode must be locked on entry and exit.
819 Returns -1 on error, or number of share modes on success (may be zero).
820 ****************************************************************************/
822 static NTSTATUS open_mode_check(connection_struct *conn,
823 struct share_mode_lock *lck,
824 uint32 access_mask,
825 uint32 share_access,
826 uint32 create_options,
827 bool *file_existed)
829 int i;
831 if(lck->num_share_modes == 0) {
832 return NT_STATUS_OK;
835 *file_existed = True;
837 /* A delete on close prohibits everything */
839 if (lck->delete_on_close) {
840 return NT_STATUS_DELETE_PENDING;
843 if (is_stat_open(access_mask)) {
844 /* Stat open that doesn't trigger oplock breaks or share mode
845 * checks... ! JRA. */
846 return NT_STATUS_OK;
850 * Check if the share modes will give us access.
853 #if defined(DEVELOPER)
854 for(i = 0; i < lck->num_share_modes; i++) {
855 validate_my_share_entries(i, &lck->share_modes[i]);
857 #endif
859 if (!lp_share_modes(SNUM(conn))) {
860 return NT_STATUS_OK;
863 /* Now we check the share modes, after any oplock breaks. */
864 for(i = 0; i < lck->num_share_modes; i++) {
866 if (!is_valid_share_mode_entry(&lck->share_modes[i])) {
867 continue;
870 /* someone else has a share lock on it, check to see if we can
871 * too */
872 if (share_conflict(&lck->share_modes[i],
873 access_mask, share_access)) {
874 return NT_STATUS_SHARING_VIOLATION;
878 return NT_STATUS_OK;
881 static bool is_delete_request(files_struct *fsp) {
882 return ((fsp->access_mask == DELETE_ACCESS) &&
883 (fsp->oplock_type == NO_OPLOCK));
887 * Send a break message to the oplock holder and delay the open for
888 * our client.
891 static NTSTATUS send_break_message(files_struct *fsp,
892 struct share_mode_entry *exclusive,
893 uint16 mid,
894 int oplock_request)
896 NTSTATUS status;
897 char msg[MSG_SMB_SHARE_MODE_ENTRY_SIZE];
899 DEBUG(10, ("Sending break request to PID %s\n",
900 procid_str_static(&exclusive->pid)));
901 exclusive->op_mid = mid;
903 /* Create the message. */
904 share_mode_entry_to_message(msg, exclusive);
906 /* Add in the FORCE_OPLOCK_BREAK_TO_NONE bit in the message if set. We
907 don't want this set in the share mode struct pointed to by lck. */
909 if (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE) {
910 SSVAL(msg,6,exclusive->op_type | FORCE_OPLOCK_BREAK_TO_NONE);
913 status = messaging_send_buf(smbd_messaging_context(), exclusive->pid,
914 MSG_SMB_BREAK_REQUEST,
915 (uint8 *)msg,
916 MSG_SMB_SHARE_MODE_ENTRY_SIZE);
917 if (!NT_STATUS_IS_OK(status)) {
918 DEBUG(3, ("Could not send oplock break message: %s\n",
919 nt_errstr(status)));
922 return status;
926 * 1) No files open at all or internal open: Grant whatever the client wants.
928 * 2) Exclusive (or batch) oplock around: If the requested access is a delete
929 * request, break if the oplock around is a batch oplock. If it's another
930 * requested access type, break.
932 * 3) Only level2 around: Grant level2 and do nothing else.
935 static bool delay_for_oplocks(struct share_mode_lock *lck,
936 files_struct *fsp,
937 uint16 mid,
938 int pass_number,
939 int oplock_request)
941 int i;
942 struct share_mode_entry *exclusive = NULL;
943 bool valid_entry = false;
944 bool have_level2 = false;
945 bool have_a_none_oplock = false;
946 bool allow_level2 = (global_client_caps & CAP_LEVEL_II_OPLOCKS) &&
947 lp_level2_oplocks(SNUM(fsp->conn));
949 if (oplock_request & INTERNAL_OPEN_ONLY) {
950 fsp->oplock_type = NO_OPLOCK;
953 if ((oplock_request & INTERNAL_OPEN_ONLY) || is_stat_open(fsp->access_mask)) {
954 return false;
957 for (i=0; i<lck->num_share_modes; i++) {
959 if (!is_valid_share_mode_entry(&lck->share_modes[i])) {
960 continue;
963 /* At least one entry is not an invalid or deferred entry. */
964 valid_entry = true;
966 if (pass_number == 1) {
967 if (BATCH_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
968 SMB_ASSERT(exclusive == NULL);
969 exclusive = &lck->share_modes[i];
971 } else {
972 if (EXCLUSIVE_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
973 SMB_ASSERT(exclusive == NULL);
974 exclusive = &lck->share_modes[i];
978 if (LEVEL_II_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
979 SMB_ASSERT(exclusive == NULL);
980 have_level2 = true;
983 if (lck->share_modes[i].op_type == NO_OPLOCK) {
984 have_a_none_oplock = true;
988 if (exclusive != NULL) { /* Found an exclusive oplock */
989 bool delay_it = is_delete_request(fsp) ?
990 BATCH_OPLOCK_TYPE(exclusive->op_type) : true;
991 SMB_ASSERT(!have_level2);
992 if (delay_it) {
993 send_break_message(fsp, exclusive, mid, oplock_request);
994 return true;
999 * Match what was requested (fsp->oplock_type) with
1000 * what was found in the existing share modes.
1003 if (!valid_entry) {
1004 /* All entries are placeholders or deferred.
1005 * Directly grant whatever the client wants. */
1006 if (fsp->oplock_type == NO_OPLOCK) {
1007 /* Store a level2 oplock, but don't tell the client */
1008 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1010 } else if (have_a_none_oplock) {
1011 fsp->oplock_type = NO_OPLOCK;
1012 } else if (have_level2) {
1013 if (fsp->oplock_type == NO_OPLOCK ||
1014 fsp->oplock_type == FAKE_LEVEL_II_OPLOCK) {
1015 /* Store a level2 oplock, but don't tell the client */
1016 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1017 } else {
1018 fsp->oplock_type = LEVEL_II_OPLOCK;
1020 } else {
1021 /* This case can never happen. */
1022 SMB_ASSERT(1);
1026 * Don't grant level2 to clients that don't want them
1027 * or if we've turned them off.
1029 if (fsp->oplock_type == LEVEL_II_OPLOCK && !allow_level2) {
1030 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1033 DEBUG(10,("delay_for_oplocks: oplock type 0x%x on file %s\n",
1034 fsp->oplock_type, fsp_str_dbg(fsp)));
1036 /* No delay. */
1037 return false;
1040 bool request_timed_out(struct timeval request_time,
1041 struct timeval timeout)
1043 struct timeval now, end_time;
1044 GetTimeOfDay(&now);
1045 end_time = timeval_sum(&request_time, &timeout);
1046 return (timeval_compare(&end_time, &now) < 0);
1049 /****************************************************************************
1050 Handle the 1 second delay in returning a SHARING_VIOLATION error.
1051 ****************************************************************************/
1053 static void defer_open(struct share_mode_lock *lck,
1054 struct timeval request_time,
1055 struct timeval timeout,
1056 struct smb_request *req,
1057 struct deferred_open_record *state)
1059 int i;
1061 /* Paranoia check */
1063 for (i=0; i<lck->num_share_modes; i++) {
1064 struct share_mode_entry *e = &lck->share_modes[i];
1066 if (!is_deferred_open_entry(e)) {
1067 continue;
1070 if (procid_is_me(&e->pid) && (e->op_mid == req->mid)) {
1071 DEBUG(0, ("Trying to defer an already deferred "
1072 "request: mid=%d, exiting\n", req->mid));
1073 exit_server("attempt to defer a deferred request");
1077 /* End paranoia check */
1079 DEBUG(10,("defer_open_sharing_error: time [%u.%06u] adding deferred "
1080 "open entry for mid %u\n",
1081 (unsigned int)request_time.tv_sec,
1082 (unsigned int)request_time.tv_usec,
1083 (unsigned int)req->mid));
1085 if (!push_deferred_smb_message(req, request_time, timeout,
1086 (char *)state, sizeof(*state))) {
1087 exit_server("push_deferred_smb_message failed");
1089 add_deferred_open(lck, req->mid, request_time, state->id);
1093 /****************************************************************************
1094 On overwrite open ensure that the attributes match.
1095 ****************************************************************************/
1097 bool open_match_attributes(connection_struct *conn,
1098 uint32 old_dos_attr,
1099 uint32 new_dos_attr,
1100 mode_t existing_unx_mode,
1101 mode_t new_unx_mode,
1102 mode_t *returned_unx_mode)
1104 uint32 noarch_old_dos_attr, noarch_new_dos_attr;
1106 noarch_old_dos_attr = (old_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
1107 noarch_new_dos_attr = (new_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
1109 if((noarch_old_dos_attr == 0 && noarch_new_dos_attr != 0) ||
1110 (noarch_old_dos_attr != 0 && ((noarch_old_dos_attr & noarch_new_dos_attr) == noarch_old_dos_attr))) {
1111 *returned_unx_mode = new_unx_mode;
1112 } else {
1113 *returned_unx_mode = (mode_t)0;
1116 DEBUG(10,("open_match_attributes: old_dos_attr = 0x%x, "
1117 "existing_unx_mode = 0%o, new_dos_attr = 0x%x "
1118 "returned_unx_mode = 0%o\n",
1119 (unsigned int)old_dos_attr,
1120 (unsigned int)existing_unx_mode,
1121 (unsigned int)new_dos_attr,
1122 (unsigned int)*returned_unx_mode ));
1124 /* If we're mapping SYSTEM and HIDDEN ensure they match. */
1125 if (lp_map_system(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
1126 if ((old_dos_attr & FILE_ATTRIBUTE_SYSTEM) &&
1127 !(new_dos_attr & FILE_ATTRIBUTE_SYSTEM)) {
1128 return False;
1131 if (lp_map_hidden(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
1132 if ((old_dos_attr & FILE_ATTRIBUTE_HIDDEN) &&
1133 !(new_dos_attr & FILE_ATTRIBUTE_HIDDEN)) {
1134 return False;
1137 return True;
1140 /****************************************************************************
1141 Special FCB or DOS processing in the case of a sharing violation.
1142 Try and find a duplicated file handle.
1143 ****************************************************************************/
1145 NTSTATUS fcb_or_dos_open(struct smb_request *req,
1146 connection_struct *conn,
1147 files_struct *fsp_to_dup_into,
1148 const struct smb_filename *smb_fname,
1149 struct file_id id,
1150 uint16 file_pid,
1151 uint16 vuid,
1152 uint32 access_mask,
1153 uint32 share_access,
1154 uint32 create_options)
1156 files_struct *fsp;
1158 DEBUG(5,("fcb_or_dos_open: attempting old open semantics for "
1159 "file %s.\n", smb_fname_str_dbg(smb_fname)));
1161 for(fsp = file_find_di_first(id); fsp;
1162 fsp = file_find_di_next(fsp)) {
1164 DEBUG(10,("fcb_or_dos_open: checking file %s, fd = %d, "
1165 "vuid = %u, file_pid = %u, private_options = 0x%x "
1166 "access_mask = 0x%x\n", fsp_str_dbg(fsp),
1167 fsp->fh->fd, (unsigned int)fsp->vuid,
1168 (unsigned int)fsp->file_pid,
1169 (unsigned int)fsp->fh->private_options,
1170 (unsigned int)fsp->access_mask ));
1172 if (fsp->fh->fd != -1 &&
1173 fsp->vuid == vuid &&
1174 fsp->file_pid == file_pid &&
1175 (fsp->fh->private_options & (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS |
1176 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) &&
1177 (fsp->access_mask & FILE_WRITE_DATA) &&
1178 strequal(fsp->fsp_name->base_name, smb_fname->base_name) &&
1179 strequal(fsp->fsp_name->stream_name,
1180 smb_fname->stream_name)) {
1181 DEBUG(10,("fcb_or_dos_open: file match\n"));
1182 break;
1186 if (!fsp) {
1187 return NT_STATUS_NOT_FOUND;
1190 /* quite an insane set of semantics ... */
1191 if (is_executable(smb_fname->base_name) &&
1192 (fsp->fh->private_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS)) {
1193 DEBUG(10,("fcb_or_dos_open: file fail due to is_executable.\n"));
1194 return NT_STATUS_INVALID_PARAMETER;
1197 /* We need to duplicate this fsp. */
1198 return dup_file_fsp(req, fsp, access_mask, share_access,
1199 create_options, fsp_to_dup_into);
1202 /****************************************************************************
1203 Open a file with a share mode - old openX method - map into NTCreate.
1204 ****************************************************************************/
1206 bool map_open_params_to_ntcreate(const struct smb_filename *smb_fname,
1207 int deny_mode, int open_func,
1208 uint32 *paccess_mask,
1209 uint32 *pshare_mode,
1210 uint32 *pcreate_disposition,
1211 uint32 *pcreate_options,
1212 uint32_t *pprivate_flags)
1214 uint32 access_mask;
1215 uint32 share_mode;
1216 uint32 create_disposition;
1217 uint32 create_options = FILE_NON_DIRECTORY_FILE;
1218 uint32_t private_flags = 0;
1220 DEBUG(10,("map_open_params_to_ntcreate: fname = %s, deny_mode = 0x%x, "
1221 "open_func = 0x%x\n",
1222 smb_fname_str_dbg(smb_fname), (unsigned int)deny_mode,
1223 (unsigned int)open_func ));
1225 /* Create the NT compatible access_mask. */
1226 switch (GET_OPENX_MODE(deny_mode)) {
1227 case DOS_OPEN_EXEC: /* Implies read-only - used to be FILE_READ_DATA */
1228 case DOS_OPEN_RDONLY:
1229 access_mask = FILE_GENERIC_READ;
1230 break;
1231 case DOS_OPEN_WRONLY:
1232 access_mask = FILE_GENERIC_WRITE;
1233 break;
1234 case DOS_OPEN_RDWR:
1235 case DOS_OPEN_FCB:
1236 access_mask = FILE_GENERIC_READ|FILE_GENERIC_WRITE;
1237 break;
1238 default:
1239 DEBUG(10,("map_open_params_to_ntcreate: bad open mode = 0x%x\n",
1240 (unsigned int)GET_OPENX_MODE(deny_mode)));
1241 return False;
1244 /* Create the NT compatible create_disposition. */
1245 switch (open_func) {
1246 case OPENX_FILE_EXISTS_FAIL|OPENX_FILE_CREATE_IF_NOT_EXIST:
1247 create_disposition = FILE_CREATE;
1248 break;
1250 case OPENX_FILE_EXISTS_OPEN:
1251 create_disposition = FILE_OPEN;
1252 break;
1254 case OPENX_FILE_EXISTS_OPEN|OPENX_FILE_CREATE_IF_NOT_EXIST:
1255 create_disposition = FILE_OPEN_IF;
1256 break;
1258 case OPENX_FILE_EXISTS_TRUNCATE:
1259 create_disposition = FILE_OVERWRITE;
1260 break;
1262 case OPENX_FILE_EXISTS_TRUNCATE|OPENX_FILE_CREATE_IF_NOT_EXIST:
1263 create_disposition = FILE_OVERWRITE_IF;
1264 break;
1266 default:
1267 /* From samba4 - to be confirmed. */
1268 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_EXEC) {
1269 create_disposition = FILE_CREATE;
1270 break;
1272 DEBUG(10,("map_open_params_to_ntcreate: bad "
1273 "open_func 0x%x\n", (unsigned int)open_func));
1274 return False;
1277 /* Create the NT compatible share modes. */
1278 switch (GET_DENY_MODE(deny_mode)) {
1279 case DENY_ALL:
1280 share_mode = FILE_SHARE_NONE;
1281 break;
1283 case DENY_WRITE:
1284 share_mode = FILE_SHARE_READ;
1285 break;
1287 case DENY_READ:
1288 share_mode = FILE_SHARE_WRITE;
1289 break;
1291 case DENY_NONE:
1292 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1293 break;
1295 case DENY_DOS:
1296 private_flags |= NTCREATEX_OPTIONS_PRIVATE_DENY_DOS;
1297 if (is_executable(smb_fname->base_name)) {
1298 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1299 } else {
1300 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_RDONLY) {
1301 share_mode = FILE_SHARE_READ;
1302 } else {
1303 share_mode = FILE_SHARE_NONE;
1306 break;
1308 case DENY_FCB:
1309 private_flags |= NTCREATEX_OPTIONS_PRIVATE_DENY_FCB;
1310 share_mode = FILE_SHARE_NONE;
1311 break;
1313 default:
1314 DEBUG(10,("map_open_params_to_ntcreate: bad deny_mode 0x%x\n",
1315 (unsigned int)GET_DENY_MODE(deny_mode) ));
1316 return False;
1319 DEBUG(10,("map_open_params_to_ntcreate: file %s, access_mask = 0x%x, "
1320 "share_mode = 0x%x, create_disposition = 0x%x, "
1321 "create_options = 0x%x private_flags = 0x%x\n",
1322 smb_fname_str_dbg(smb_fname),
1323 (unsigned int)access_mask,
1324 (unsigned int)share_mode,
1325 (unsigned int)create_disposition,
1326 (unsigned int)create_options,
1327 (unsigned int)private_flags));
1329 if (paccess_mask) {
1330 *paccess_mask = access_mask;
1332 if (pshare_mode) {
1333 *pshare_mode = share_mode;
1335 if (pcreate_disposition) {
1336 *pcreate_disposition = create_disposition;
1338 if (pcreate_options) {
1339 *pcreate_options = create_options;
1341 if (pprivate_flags) {
1342 *pprivate_flags = private_flags;
1345 return True;
1349 static void schedule_defer_open(struct share_mode_lock *lck,
1350 struct timeval request_time,
1351 struct smb_request *req)
1353 struct deferred_open_record state;
1355 /* This is a relative time, added to the absolute
1356 request_time value to get the absolute timeout time.
1357 Note that if this is the second or greater time we enter
1358 this codepath for this particular request mid then
1359 request_time is left as the absolute time of the *first*
1360 time this request mid was processed. This is what allows
1361 the request to eventually time out. */
1363 struct timeval timeout;
1365 /* Normally the smbd we asked should respond within
1366 * OPLOCK_BREAK_TIMEOUT seconds regardless of whether
1367 * the client did, give twice the timeout as a safety
1368 * measure here in case the other smbd is stuck
1369 * somewhere else. */
1371 timeout = timeval_set(OPLOCK_BREAK_TIMEOUT*2, 0);
1373 /* Nothing actually uses state.delayed_for_oplocks
1374 but it's handy to differentiate in debug messages
1375 between a 30 second delay due to oplock break, and
1376 a 1 second delay for share mode conflicts. */
1378 state.delayed_for_oplocks = True;
1379 state.id = lck->id;
1381 if (!request_timed_out(request_time, timeout)) {
1382 defer_open(lck, request_time, timeout, req, &state);
1386 /****************************************************************************
1387 Work out what access_mask to use from what the client sent us.
1388 ****************************************************************************/
1390 static NTSTATUS calculate_access_mask(connection_struct *conn,
1391 const struct smb_filename *smb_fname,
1392 bool file_existed,
1393 uint32_t access_mask,
1394 uint32_t *access_mask_out)
1396 NTSTATUS status;
1399 * Convert GENERIC bits to specific bits.
1402 se_map_generic(&access_mask, &file_generic_mapping);
1404 /* Calculate MAXIMUM_ALLOWED_ACCESS if requested. */
1405 if (access_mask & MAXIMUM_ALLOWED_ACCESS) {
1406 if (file_existed) {
1408 struct security_descriptor *sd;
1409 uint32_t access_granted = 0;
1411 status = SMB_VFS_GET_NT_ACL(conn, smb_fname->base_name,
1412 (OWNER_SECURITY_INFORMATION |
1413 GROUP_SECURITY_INFORMATION |
1414 DACL_SECURITY_INFORMATION),&sd);
1416 if (!NT_STATUS_IS_OK(status)) {
1417 DEBUG(10, ("calculate_access_mask: Could not get acl "
1418 "on file %s: %s\n",
1419 smb_fname_str_dbg(smb_fname),
1420 nt_errstr(status)));
1421 return NT_STATUS_ACCESS_DENIED;
1424 status = smb1_file_se_access_check(conn,
1426 get_current_nttok(conn),
1427 access_mask,
1428 &access_granted);
1430 TALLOC_FREE(sd);
1432 if (!NT_STATUS_IS_OK(status)) {
1433 DEBUG(10, ("calculate_access_mask: Access denied on "
1434 "file %s: when calculating maximum access\n",
1435 smb_fname_str_dbg(smb_fname)));
1436 return NT_STATUS_ACCESS_DENIED;
1439 access_mask = access_granted;
1440 } else {
1441 access_mask = FILE_GENERIC_ALL;
1445 *access_mask_out = access_mask;
1446 return NT_STATUS_OK;
1449 /****************************************************************************
1450 Open a file with a share mode. Passed in an already created files_struct *.
1451 ****************************************************************************/
1453 static NTSTATUS open_file_ntcreate(connection_struct *conn,
1454 struct smb_request *req,
1455 uint32 access_mask, /* access bits (FILE_READ_DATA etc.) */
1456 uint32 share_access, /* share constants (FILE_SHARE_READ etc) */
1457 uint32 create_disposition, /* FILE_OPEN_IF etc. */
1458 uint32 create_options, /* options such as delete on close. */
1459 uint32 new_dos_attributes, /* attributes used for new file. */
1460 int oplock_request, /* internal Samba oplock codes. */
1461 /* Information (FILE_EXISTS etc.) */
1462 uint32_t private_flags, /* Samba specific flags. */
1463 int *pinfo,
1464 files_struct *fsp)
1466 struct smb_filename *smb_fname = fsp->fsp_name;
1467 int flags=0;
1468 int flags2=0;
1469 bool file_existed = VALID_STAT(smb_fname->st);
1470 bool def_acl = False;
1471 bool posix_open = False;
1472 bool new_file_created = False;
1473 bool clear_ads = false;
1474 struct file_id id;
1475 NTSTATUS fsp_open = NT_STATUS_ACCESS_DENIED;
1476 mode_t new_unx_mode = (mode_t)0;
1477 mode_t unx_mode = (mode_t)0;
1478 int info;
1479 uint32 existing_dos_attributes = 0;
1480 struct pending_message_list *pml = NULL;
1481 struct timeval request_time = timeval_zero();
1482 struct share_mode_lock *lck = NULL;
1483 uint32 open_access_mask = access_mask;
1484 NTSTATUS status;
1485 char *parent_dir;
1487 ZERO_STRUCT(id);
1489 if (conn->printer) {
1491 * Printers are handled completely differently.
1492 * Most of the passed parameters are ignored.
1495 if (pinfo) {
1496 *pinfo = FILE_WAS_CREATED;
1499 DEBUG(10, ("open_file_ntcreate: printer open fname=%s\n",
1500 smb_fname_str_dbg(smb_fname)));
1502 if (!req) {
1503 DEBUG(0,("open_file_ntcreate: printer open without "
1504 "an SMB request!\n"));
1505 return NT_STATUS_INTERNAL_ERROR;
1508 return print_fsp_open(req, conn, smb_fname->base_name,
1509 req->vuid, fsp);
1512 if (!parent_dirname(talloc_tos(), smb_fname->base_name, &parent_dir,
1513 NULL)) {
1514 return NT_STATUS_NO_MEMORY;
1517 if (new_dos_attributes & FILE_FLAG_POSIX_SEMANTICS) {
1518 posix_open = True;
1519 unx_mode = (mode_t)(new_dos_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
1520 new_dos_attributes = 0;
1521 } else {
1522 /* We add aARCH to this as this mode is only used if the file is
1523 * created new. */
1524 unx_mode = unix_mode(conn, new_dos_attributes | aARCH,
1525 smb_fname, parent_dir);
1528 DEBUG(10, ("open_file_ntcreate: fname=%s, dos_attrs=0x%x "
1529 "access_mask=0x%x share_access=0x%x "
1530 "create_disposition = 0x%x create_options=0x%x "
1531 "unix mode=0%o oplock_request=%d private_flags = 0x%x\n",
1532 smb_fname_str_dbg(smb_fname), new_dos_attributes,
1533 access_mask, share_access, create_disposition,
1534 create_options, (unsigned int)unx_mode, oplock_request,
1535 (unsigned int)private_flags));
1537 if ((req == NULL) && ((oplock_request & INTERNAL_OPEN_ONLY) == 0)) {
1538 DEBUG(0, ("No smb request but not an internal only open!\n"));
1539 return NT_STATUS_INTERNAL_ERROR;
1543 * Only non-internal opens can be deferred at all
1546 if ((req != NULL)
1547 && ((pml = get_open_deferred_message(req->mid)) != NULL)) {
1548 struct deferred_open_record *state =
1549 (struct deferred_open_record *)pml->private_data.data;
1551 /* Remember the absolute time of the original
1552 request with this mid. We'll use it later to
1553 see if this has timed out. */
1555 request_time = pml->request_time;
1557 /* Remove the deferred open entry under lock. */
1558 lck = get_share_mode_lock(talloc_tos(), state->id, NULL, NULL,
1559 NULL);
1560 if (lck == NULL) {
1561 DEBUG(0, ("could not get share mode lock\n"));
1562 } else {
1563 del_deferred_open_entry(lck, req->mid);
1564 TALLOC_FREE(lck);
1567 /* Ensure we don't reprocess this message. */
1568 remove_deferred_open_smb_message(req->mid);
1571 status = check_name(conn, smb_fname->base_name);
1572 if (!NT_STATUS_IS_OK(status)) {
1573 return status;
1576 if (!posix_open) {
1577 new_dos_attributes &= SAMBA_ATTRIBUTES_MASK;
1578 if (file_existed) {
1579 existing_dos_attributes = dos_mode(conn, smb_fname);
1583 /* ignore any oplock requests if oplocks are disabled */
1584 if (!lp_oplocks(SNUM(conn)) || global_client_failed_oplock_break ||
1585 IS_VETO_OPLOCK_PATH(conn, smb_fname->base_name)) {
1586 /* Mask off everything except the private Samba bits. */
1587 oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
1590 /* this is for OS/2 long file names - say we don't support them */
1591 if (!lp_posix_pathnames() && strstr(smb_fname->base_name,".+,;=[].")) {
1592 /* OS/2 Workplace shell fix may be main code stream in a later
1593 * release. */
1594 DEBUG(5,("open_file_ntcreate: OS/2 long filenames are not "
1595 "supported.\n"));
1596 if (use_nt_status()) {
1597 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1599 return NT_STATUS_DOS(ERRDOS, ERRcannotopen);
1602 switch( create_disposition ) {
1604 * Currently we're using FILE_SUPERSEDE as the same as
1605 * FILE_OVERWRITE_IF but they really are
1606 * different. FILE_SUPERSEDE deletes an existing file
1607 * (requiring delete access) then recreates it.
1609 case FILE_SUPERSEDE:
1610 /* If file exists replace/overwrite. If file doesn't
1611 * exist create. */
1612 flags2 |= (O_CREAT | O_TRUNC);
1613 clear_ads = true;
1614 break;
1616 case FILE_OVERWRITE_IF:
1617 /* If file exists replace/overwrite. If file doesn't
1618 * exist create. */
1619 flags2 |= (O_CREAT | O_TRUNC);
1620 clear_ads = true;
1621 break;
1623 case FILE_OPEN:
1624 /* If file exists open. If file doesn't exist error. */
1625 if (!file_existed) {
1626 DEBUG(5,("open_file_ntcreate: FILE_OPEN "
1627 "requested for file %s and file "
1628 "doesn't exist.\n",
1629 smb_fname_str_dbg(smb_fname)));
1630 errno = ENOENT;
1631 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1633 break;
1635 case FILE_OVERWRITE:
1636 /* If file exists overwrite. If file doesn't exist
1637 * error. */
1638 if (!file_existed) {
1639 DEBUG(5,("open_file_ntcreate: FILE_OVERWRITE "
1640 "requested for file %s and file "
1641 "doesn't exist.\n",
1642 smb_fname_str_dbg(smb_fname) ));
1643 errno = ENOENT;
1644 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1646 flags2 |= O_TRUNC;
1647 clear_ads = true;
1648 break;
1650 case FILE_CREATE:
1651 /* If file exists error. If file doesn't exist
1652 * create. */
1653 if (file_existed) {
1654 DEBUG(5,("open_file_ntcreate: FILE_CREATE "
1655 "requested for file %s and file "
1656 "already exists.\n",
1657 smb_fname_str_dbg(smb_fname)));
1658 if (S_ISDIR(smb_fname->st.st_ex_mode)) {
1659 errno = EISDIR;
1660 } else {
1661 errno = EEXIST;
1663 return map_nt_error_from_unix(errno);
1665 flags2 |= (O_CREAT|O_EXCL);
1666 break;
1668 case FILE_OPEN_IF:
1669 /* If file exists open. If file doesn't exist
1670 * create. */
1671 flags2 |= O_CREAT;
1672 break;
1674 default:
1675 return NT_STATUS_INVALID_PARAMETER;
1678 /* We only care about matching attributes on file exists and
1679 * overwrite. */
1681 if (!posix_open && file_existed && ((create_disposition == FILE_OVERWRITE) ||
1682 (create_disposition == FILE_OVERWRITE_IF))) {
1683 if (!open_match_attributes(conn, existing_dos_attributes,
1684 new_dos_attributes,
1685 smb_fname->st.st_ex_mode,
1686 unx_mode, &new_unx_mode)) {
1687 DEBUG(5,("open_file_ntcreate: attributes missmatch "
1688 "for file %s (%x %x) (0%o, 0%o)\n",
1689 smb_fname_str_dbg(smb_fname),
1690 existing_dos_attributes,
1691 new_dos_attributes,
1692 (unsigned int)smb_fname->st.st_ex_mode,
1693 (unsigned int)unx_mode ));
1694 errno = EACCES;
1695 return NT_STATUS_ACCESS_DENIED;
1699 status = calculate_access_mask(conn, smb_fname, file_existed,
1700 access_mask,
1701 &access_mask);
1702 if (!NT_STATUS_IS_OK(status)) {
1703 DEBUG(10, ("open_file_ntcreate: calculate_access_mask "
1704 "on file %s returned %s\n",
1705 smb_fname_str_dbg(smb_fname), nt_errstr(status)));
1706 return status;
1709 open_access_mask = access_mask;
1711 if ((flags2 & O_TRUNC) || (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
1712 open_access_mask |= FILE_WRITE_DATA; /* This will cause oplock breaks. */
1715 DEBUG(10, ("open_file_ntcreate: fname=%s, after mapping "
1716 "access_mask=0x%x\n", smb_fname_str_dbg(smb_fname),
1717 access_mask));
1720 * Note that we ignore the append flag as append does not
1721 * mean the same thing under DOS and Unix.
1724 if ((access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ||
1725 (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
1726 /* DENY_DOS opens are always underlying read-write on the
1727 file handle, no matter what the requested access mask
1728 says. */
1729 if ((private_flags & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS) ||
1730 access_mask & (FILE_READ_ATTRIBUTES|FILE_READ_DATA|FILE_READ_EA|FILE_EXECUTE)) {
1731 flags = O_RDWR;
1732 } else {
1733 flags = O_WRONLY;
1735 } else {
1736 flags = O_RDONLY;
1740 * Currently we only look at FILE_WRITE_THROUGH for create options.
1743 #if defined(O_SYNC)
1744 if ((create_options & FILE_WRITE_THROUGH) && lp_strict_sync(SNUM(conn))) {
1745 flags2 |= O_SYNC;
1747 #endif /* O_SYNC */
1749 if (posix_open && (access_mask & FILE_APPEND_DATA)) {
1750 flags2 |= O_APPEND;
1753 if (!posix_open && !CAN_WRITE(conn)) {
1755 * We should really return a permission denied error if either
1756 * O_CREAT or O_TRUNC are set, but for compatibility with
1757 * older versions of Samba we just AND them out.
1759 flags2 &= ~(O_CREAT|O_TRUNC);
1763 * Ensure we can't write on a read-only share or file.
1766 if (flags != O_RDONLY && file_existed &&
1767 (!CAN_WRITE(conn) || IS_DOS_READONLY(existing_dos_attributes))) {
1768 DEBUG(5,("open_file_ntcreate: write access requested for "
1769 "file %s on read only %s\n",
1770 smb_fname_str_dbg(smb_fname),
1771 !CAN_WRITE(conn) ? "share" : "file" ));
1772 errno = EACCES;
1773 return NT_STATUS_ACCESS_DENIED;
1776 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
1777 fsp->share_access = share_access;
1778 fsp->fh->private_options = private_flags;
1779 fsp->access_mask = open_access_mask; /* We change this to the
1780 * requested access_mask after
1781 * the open is done. */
1782 fsp->posix_open = posix_open;
1784 /* Ensure no SAMBA_PRIVATE bits can be set. */
1785 fsp->oplock_type = (oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK);
1787 if (timeval_is_zero(&request_time)) {
1788 request_time = fsp->open_time;
1791 if (file_existed) {
1792 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
1793 id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
1795 lck = get_share_mode_lock(talloc_tos(), id,
1796 conn->connectpath,
1797 smb_fname, &old_write_time);
1799 if (lck == NULL) {
1800 DEBUG(0, ("Could not get share mode lock\n"));
1801 return NT_STATUS_SHARING_VIOLATION;
1804 /* First pass - send break only on batch oplocks. */
1805 if ((req != NULL)
1806 && delay_for_oplocks(lck, fsp, req->mid, 1,
1807 oplock_request)) {
1808 schedule_defer_open(lck, request_time, req);
1809 TALLOC_FREE(lck);
1810 return NT_STATUS_SHARING_VIOLATION;
1813 /* Use the client requested access mask here, not the one we
1814 * open with. */
1815 status = open_mode_check(conn, lck, access_mask, share_access,
1816 create_options, &file_existed);
1818 if (NT_STATUS_IS_OK(status)) {
1819 /* We might be going to allow this open. Check oplock
1820 * status again. */
1821 /* Second pass - send break for both batch or
1822 * exclusive oplocks. */
1823 if ((req != NULL)
1824 && delay_for_oplocks(lck, fsp, req->mid, 2,
1825 oplock_request)) {
1826 schedule_defer_open(lck, request_time, req);
1827 TALLOC_FREE(lck);
1828 return NT_STATUS_SHARING_VIOLATION;
1832 if (NT_STATUS_EQUAL(status, NT_STATUS_DELETE_PENDING)) {
1833 /* DELETE_PENDING is not deferred for a second */
1834 TALLOC_FREE(lck);
1835 return status;
1838 if (!NT_STATUS_IS_OK(status)) {
1839 uint32 can_access_mask;
1840 bool can_access = True;
1842 SMB_ASSERT(NT_STATUS_EQUAL(status, NT_STATUS_SHARING_VIOLATION));
1844 /* Check if this can be done with the deny_dos and fcb
1845 * calls. */
1846 if (private_flags &
1847 (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
1848 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
1849 if (req == NULL) {
1850 DEBUG(0, ("DOS open without an SMB "
1851 "request!\n"));
1852 TALLOC_FREE(lck);
1853 return NT_STATUS_INTERNAL_ERROR;
1856 /* Use the client requested access mask here,
1857 * not the one we open with. */
1858 status = fcb_or_dos_open(req,
1859 conn,
1860 fsp,
1861 smb_fname,
1863 req->smbpid,
1864 req->vuid,
1865 access_mask,
1866 share_access,
1867 create_options);
1869 if (NT_STATUS_IS_OK(status)) {
1870 TALLOC_FREE(lck);
1871 if (pinfo) {
1872 *pinfo = FILE_WAS_OPENED;
1874 return NT_STATUS_OK;
1879 * This next line is a subtlety we need for
1880 * MS-Access. If a file open will fail due to share
1881 * permissions and also for security (access) reasons,
1882 * we need to return the access failed error, not the
1883 * share error. We can't open the file due to kernel
1884 * oplock deadlock (it's possible we failed above on
1885 * the open_mode_check()) so use a userspace check.
1888 if (flags & O_RDWR) {
1889 can_access_mask = FILE_READ_DATA|FILE_WRITE_DATA;
1890 } else if (flags & O_WRONLY) {
1891 can_access_mask = FILE_WRITE_DATA;
1892 } else {
1893 can_access_mask = FILE_READ_DATA;
1896 if (((can_access_mask & FILE_WRITE_DATA) &&
1897 !CAN_WRITE(conn)) ||
1898 !can_access_file_data(conn, smb_fname,
1899 can_access_mask)) {
1900 can_access = False;
1904 * If we're returning a share violation, ensure we
1905 * cope with the braindead 1 second delay.
1908 if (!(oplock_request & INTERNAL_OPEN_ONLY) &&
1909 lp_defer_sharing_violations()) {
1910 struct timeval timeout;
1911 struct deferred_open_record state;
1912 int timeout_usecs;
1914 /* this is a hack to speed up torture tests
1915 in 'make test' */
1916 timeout_usecs = lp_parm_int(SNUM(conn),
1917 "smbd","sharedelay",
1918 SHARING_VIOLATION_USEC_WAIT);
1920 /* This is a relative time, added to the absolute
1921 request_time value to get the absolute timeout time.
1922 Note that if this is the second or greater time we enter
1923 this codepath for this particular request mid then
1924 request_time is left as the absolute time of the *first*
1925 time this request mid was processed. This is what allows
1926 the request to eventually time out. */
1928 timeout = timeval_set(0, timeout_usecs);
1930 /* Nothing actually uses state.delayed_for_oplocks
1931 but it's handy to differentiate in debug messages
1932 between a 30 second delay due to oplock break, and
1933 a 1 second delay for share mode conflicts. */
1935 state.delayed_for_oplocks = False;
1936 state.id = id;
1938 if ((req != NULL)
1939 && !request_timed_out(request_time,
1940 timeout)) {
1941 defer_open(lck, request_time, timeout,
1942 req, &state);
1946 TALLOC_FREE(lck);
1947 if (can_access) {
1949 * We have detected a sharing violation here
1950 * so return the correct error code
1952 status = NT_STATUS_SHARING_VIOLATION;
1953 } else {
1954 status = NT_STATUS_ACCESS_DENIED;
1956 return status;
1960 * We exit this block with the share entry *locked*.....
1964 SMB_ASSERT(!file_existed || (lck != NULL));
1967 * Ensure we pay attention to default ACLs on directories if required.
1970 if ((flags2 & O_CREAT) && lp_inherit_acls(SNUM(conn)) &&
1971 (def_acl = directory_has_default_acl(conn, parent_dir))) {
1972 unx_mode = 0777;
1975 DEBUG(4,("calling open_file with flags=0x%X flags2=0x%X mode=0%o, "
1976 "access_mask = 0x%x, open_access_mask = 0x%x\n",
1977 (unsigned int)flags, (unsigned int)flags2,
1978 (unsigned int)unx_mode, (unsigned int)access_mask,
1979 (unsigned int)open_access_mask));
1982 * open_file strips any O_TRUNC flags itself.
1985 fsp_open = open_file(fsp, conn, req, parent_dir,
1986 flags|flags2, unx_mode, access_mask,
1987 open_access_mask);
1989 if (!NT_STATUS_IS_OK(fsp_open)) {
1990 if (lck != NULL) {
1991 TALLOC_FREE(lck);
1993 return fsp_open;
1996 if (!file_existed) {
1997 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
1999 * Deal with the race condition where two smbd's detect the
2000 * file doesn't exist and do the create at the same time. One
2001 * of them will win and set a share mode, the other (ie. this
2002 * one) should check if the requested share mode for this
2003 * create is allowed.
2007 * Now the file exists and fsp is successfully opened,
2008 * fsp->dev and fsp->inode are valid and should replace the
2009 * dev=0,inode=0 from a non existent file. Spotted by
2010 * Nadav Danieli <nadavd@exanet.com>. JRA.
2013 id = fsp->file_id;
2015 lck = get_share_mode_lock(talloc_tos(), id,
2016 conn->connectpath,
2017 smb_fname, &old_write_time);
2019 if (lck == NULL) {
2020 DEBUG(0, ("open_file_ntcreate: Could not get share "
2021 "mode lock for %s\n",
2022 smb_fname_str_dbg(smb_fname)));
2023 fd_close(fsp);
2024 return NT_STATUS_SHARING_VIOLATION;
2027 /* First pass - send break only on batch oplocks. */
2028 if ((req != NULL)
2029 && delay_for_oplocks(lck, fsp, req->mid, 1,
2030 oplock_request)) {
2031 schedule_defer_open(lck, request_time, req);
2032 TALLOC_FREE(lck);
2033 fd_close(fsp);
2034 return NT_STATUS_SHARING_VIOLATION;
2037 status = open_mode_check(conn, lck, access_mask, share_access,
2038 create_options, &file_existed);
2040 if (NT_STATUS_IS_OK(status)) {
2041 /* We might be going to allow this open. Check oplock
2042 * status again. */
2043 /* Second pass - send break for both batch or
2044 * exclusive oplocks. */
2045 if ((req != NULL)
2046 && delay_for_oplocks(lck, fsp, req->mid, 2,
2047 oplock_request)) {
2048 schedule_defer_open(lck, request_time, req);
2049 TALLOC_FREE(lck);
2050 fd_close(fsp);
2051 return NT_STATUS_SHARING_VIOLATION;
2055 if (!NT_STATUS_IS_OK(status)) {
2056 struct deferred_open_record state;
2058 fd_close(fsp);
2060 state.delayed_for_oplocks = False;
2061 state.id = id;
2063 /* Do it all over again immediately. In the second
2064 * round we will find that the file existed and handle
2065 * the DELETE_PENDING and FCB cases correctly. No need
2066 * to duplicate the code here. Essentially this is a
2067 * "goto top of this function", but don't tell
2068 * anybody... */
2070 if (req != NULL) {
2071 defer_open(lck, request_time, timeval_zero(),
2072 req, &state);
2074 TALLOC_FREE(lck);
2075 return status;
2079 * We exit this block with the share entry *locked*.....
2084 SMB_ASSERT(lck != NULL);
2086 /* Delete streams if create_disposition requires it */
2087 if (file_existed && clear_ads &&
2088 !is_ntfs_stream_smb_fname(smb_fname)) {
2089 status = delete_all_streams(conn, smb_fname->base_name);
2090 if (!NT_STATUS_IS_OK(status)) {
2091 TALLOC_FREE(lck);
2092 fd_close(fsp);
2093 return status;
2097 /* note that we ignore failure for the following. It is
2098 basically a hack for NFS, and NFS will never set one of
2099 these only read them. Nobody but Samba can ever set a deny
2100 mode and we have already checked our more authoritative
2101 locking database for permission to set this deny mode. If
2102 the kernel refuses the operations then the kernel is wrong.
2103 note that GPFS supports it as well - jmcd */
2105 if (fsp->fh->fd != -1) {
2106 int ret_flock;
2107 ret_flock = SMB_VFS_KERNEL_FLOCK(fsp, share_access, access_mask);
2108 if(ret_flock == -1 ){
2110 TALLOC_FREE(lck);
2111 fd_close(fsp);
2113 return NT_STATUS_SHARING_VIOLATION;
2118 * At this point onwards, we can guarentee that the share entry
2119 * is locked, whether we created the file or not, and that the
2120 * deny mode is compatible with all current opens.
2124 * If requested, truncate the file.
2127 if (flags2&O_TRUNC) {
2129 * We are modifing the file after open - update the stat
2130 * struct..
2132 if ((SMB_VFS_FTRUNCATE(fsp, 0) == -1) ||
2133 (SMB_VFS_FSTAT(fsp, &smb_fname->st)==-1)) {
2134 status = map_nt_error_from_unix(errno);
2135 TALLOC_FREE(lck);
2136 fd_close(fsp);
2137 return status;
2142 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
2144 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
2146 if (file_existed) {
2147 /* stat opens on existing files don't get oplocks. */
2148 if (is_stat_open(open_access_mask)) {
2149 fsp->oplock_type = NO_OPLOCK;
2152 if (!(flags2 & O_TRUNC)) {
2153 info = FILE_WAS_OPENED;
2154 } else {
2155 info = FILE_WAS_OVERWRITTEN;
2157 } else {
2158 info = FILE_WAS_CREATED;
2161 if (pinfo) {
2162 *pinfo = info;
2166 * Setup the oplock info in both the shared memory and
2167 * file structs.
2170 if (!set_file_oplock(fsp, fsp->oplock_type)) {
2171 /* Could not get the kernel oplock */
2172 fsp->oplock_type = NO_OPLOCK;
2175 if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED || info == FILE_WAS_SUPERSEDED) {
2176 new_file_created = True;
2179 set_share_mode(lck, fsp, get_current_uid(conn), 0,
2180 fsp->oplock_type);
2182 /* Handle strange delete on close create semantics. */
2183 if (create_options & FILE_DELETE_ON_CLOSE) {
2185 status = can_set_delete_on_close(fsp, new_dos_attributes);
2187 if (!NT_STATUS_IS_OK(status)) {
2188 /* Remember to delete the mode we just added. */
2189 del_share_mode(lck, fsp);
2190 TALLOC_FREE(lck);
2191 fd_close(fsp);
2192 return status;
2194 /* Note that here we set the *inital* delete on close flag,
2195 not the regular one. The magic gets handled in close. */
2196 fsp->initial_delete_on_close = True;
2199 if (new_file_created) {
2200 /* Files should be initially set as archive */
2201 if (lp_map_archive(SNUM(conn)) ||
2202 lp_store_dos_attributes(SNUM(conn))) {
2203 if (!posix_open) {
2204 if (file_set_dosmode(conn, smb_fname,
2205 new_dos_attributes | aARCH,
2206 parent_dir, true) == 0) {
2207 unx_mode = smb_fname->st.st_ex_mode;
2214 * Take care of inherited ACLs on created files - if default ACL not
2215 * selected.
2218 if (!posix_open && !file_existed && !def_acl) {
2220 int saved_errno = errno; /* We might get ENOSYS in the next
2221 * call.. */
2223 if (SMB_VFS_FCHMOD_ACL(fsp, unx_mode) == -1 &&
2224 errno == ENOSYS) {
2225 errno = saved_errno; /* Ignore ENOSYS */
2228 } else if (new_unx_mode) {
2230 int ret = -1;
2232 /* Attributes need changing. File already existed. */
2235 int saved_errno = errno; /* We might get ENOSYS in the
2236 * next call.. */
2237 ret = SMB_VFS_FCHMOD_ACL(fsp, new_unx_mode);
2239 if (ret == -1 && errno == ENOSYS) {
2240 errno = saved_errno; /* Ignore ENOSYS */
2241 } else {
2242 DEBUG(5, ("open_file_ntcreate: reset "
2243 "attributes of file %s to 0%o\n",
2244 smb_fname_str_dbg(smb_fname),
2245 (unsigned int)new_unx_mode));
2246 ret = 0; /* Don't do the fchmod below. */
2250 if ((ret == -1) &&
2251 (SMB_VFS_FCHMOD(fsp, new_unx_mode) == -1))
2252 DEBUG(5, ("open_file_ntcreate: failed to reset "
2253 "attributes of file %s to 0%o\n",
2254 smb_fname_str_dbg(smb_fname),
2255 (unsigned int)new_unx_mode));
2258 /* If this is a successful open, we must remove any deferred open
2259 * records. */
2260 if (req != NULL) {
2261 del_deferred_open_entry(lck, req->mid);
2263 TALLOC_FREE(lck);
2265 return NT_STATUS_OK;
2269 /****************************************************************************
2270 Open a file for for write to ensure that we can fchmod it.
2271 ****************************************************************************/
2273 NTSTATUS open_file_fchmod(struct smb_request *req, connection_struct *conn,
2274 struct smb_filename *smb_fname,
2275 files_struct **result)
2277 files_struct *fsp = NULL;
2278 NTSTATUS status;
2280 if (!VALID_STAT(smb_fname->st)) {
2281 return NT_STATUS_INVALID_PARAMETER;
2284 status = file_new(req, conn, &fsp);
2285 if(!NT_STATUS_IS_OK(status)) {
2286 return status;
2289 status = SMB_VFS_CREATE_FILE(
2290 conn, /* conn */
2291 NULL, /* req */
2292 0, /* root_dir_fid */
2293 smb_fname, /* fname */
2294 FILE_WRITE_DATA, /* access_mask */
2295 (FILE_SHARE_READ | FILE_SHARE_WRITE | /* share_access */
2296 FILE_SHARE_DELETE),
2297 FILE_OPEN, /* create_disposition*/
2298 0, /* create_options */
2299 0, /* file_attributes */
2300 0, /* oplock_request */
2301 0, /* allocation_size */
2302 0, /* private_flags */
2303 NULL, /* sd */
2304 NULL, /* ea_list */
2305 &fsp, /* result */
2306 NULL); /* pinfo */
2309 * This is not a user visible file open.
2310 * Don't set a share mode.
2313 if (!NT_STATUS_IS_OK(status)) {
2314 file_free(req, fsp);
2315 return status;
2318 *result = fsp;
2319 return NT_STATUS_OK;
2322 /****************************************************************************
2323 Close the fchmod file fd - ensure no locks are lost.
2324 ****************************************************************************/
2326 NTSTATUS close_file_fchmod(struct smb_request *req, files_struct *fsp)
2328 NTSTATUS status = fd_close(fsp);
2329 file_free(req, fsp);
2330 return status;
2333 static NTSTATUS mkdir_internal(connection_struct *conn,
2334 struct smb_filename *smb_dname,
2335 uint32 file_attributes)
2337 mode_t mode;
2338 char *parent_dir;
2339 NTSTATUS status;
2340 bool posix_open = false;
2342 if(!CAN_WRITE(conn)) {
2343 DEBUG(5,("mkdir_internal: failing create on read-only share "
2344 "%s\n", lp_servicename(SNUM(conn))));
2345 return NT_STATUS_ACCESS_DENIED;
2348 status = check_name(conn, smb_dname->base_name);
2349 if (!NT_STATUS_IS_OK(status)) {
2350 return status;
2353 if (!parent_dirname(talloc_tos(), smb_dname->base_name, &parent_dir,
2354 NULL)) {
2355 return NT_STATUS_NO_MEMORY;
2358 if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
2359 posix_open = true;
2360 mode = (mode_t)(file_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
2361 } else {
2362 mode = unix_mode(conn, aDIR, smb_dname, parent_dir);
2365 if (SMB_VFS_MKDIR(conn, smb_dname->base_name, mode) != 0) {
2366 return map_nt_error_from_unix(errno);
2369 /* Ensure we're checking for a symlink here.... */
2370 /* We don't want to get caught by a symlink racer. */
2372 if (SMB_VFS_LSTAT(conn, smb_dname) == -1) {
2373 DEBUG(2, ("Could not stat directory '%s' just created: %s\n",
2374 smb_fname_str_dbg(smb_dname), strerror(errno)));
2375 return map_nt_error_from_unix(errno);
2378 if (!S_ISDIR(smb_dname->st.st_ex_mode)) {
2379 DEBUG(0, ("Directory just '%s' created is not a directory\n",
2380 smb_fname_str_dbg(smb_dname)));
2381 return NT_STATUS_ACCESS_DENIED;
2384 if (lp_store_dos_attributes(SNUM(conn))) {
2385 if (!posix_open) {
2386 file_set_dosmode(conn, smb_dname,
2387 file_attributes | aDIR,
2388 parent_dir, true);
2392 if (lp_inherit_perms(SNUM(conn))) {
2393 inherit_access_posix_acl(conn, parent_dir,
2394 smb_dname->base_name, mode);
2397 if (!posix_open) {
2399 * Check if high bits should have been set,
2400 * then (if bits are missing): add them.
2401 * Consider bits automagically set by UNIX, i.e. SGID bit from parent
2402 * dir.
2404 if ((mode & ~(S_IRWXU|S_IRWXG|S_IRWXO)) &&
2405 (mode & ~smb_dname->st.st_ex_mode)) {
2406 SMB_VFS_CHMOD(conn, smb_dname->base_name,
2407 (smb_dname->st.st_ex_mode |
2408 (mode & ~smb_dname->st.st_ex_mode)));
2412 /* Change the owner if required. */
2413 if (lp_inherit_owner(SNUM(conn))) {
2414 change_dir_owner_to_parent(conn, parent_dir,
2415 smb_dname->base_name,
2416 &smb_dname->st);
2419 notify_fname(conn, NOTIFY_ACTION_ADDED, FILE_NOTIFY_CHANGE_DIR_NAME,
2420 smb_dname->base_name);
2422 return NT_STATUS_OK;
2425 /****************************************************************************
2426 Open a directory from an NT SMB call.
2427 ****************************************************************************/
2429 static NTSTATUS open_directory(connection_struct *conn,
2430 struct smb_request *req,
2431 struct smb_filename *smb_dname,
2432 uint32 access_mask,
2433 uint32 share_access,
2434 uint32 create_disposition,
2435 uint32 create_options,
2436 uint32 file_attributes,
2437 int *pinfo,
2438 files_struct **result)
2440 files_struct *fsp = NULL;
2441 bool dir_existed = VALID_STAT(smb_dname->st) ? True : False;
2442 struct share_mode_lock *lck = NULL;
2443 NTSTATUS status;
2444 struct timespec mtimespec;
2445 int info = 0;
2447 SMB_ASSERT(!is_ntfs_stream_smb_fname(smb_dname));
2449 DEBUG(5,("open_directory: opening directory %s, access_mask = 0x%x, "
2450 "share_access = 0x%x create_options = 0x%x, "
2451 "create_disposition = 0x%x, file_attributes = 0x%x\n",
2452 smb_fname_str_dbg(smb_dname),
2453 (unsigned int)access_mask,
2454 (unsigned int)share_access,
2455 (unsigned int)create_options,
2456 (unsigned int)create_disposition,
2457 (unsigned int)file_attributes));
2459 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
2460 (conn->fs_capabilities & FILE_NAMED_STREAMS) &&
2461 is_ntfs_stream_smb_fname(smb_dname)) {
2462 DEBUG(2, ("open_directory: %s is a stream name!\n",
2463 smb_fname_str_dbg(smb_dname)));
2464 return NT_STATUS_NOT_A_DIRECTORY;
2467 status = calculate_access_mask(conn, smb_dname, dir_existed,
2468 access_mask, &access_mask);
2469 if (!NT_STATUS_IS_OK(status)) {
2470 DEBUG(10, ("open_directory: calculate_access_mask "
2471 "on file %s returned %s\n",
2472 smb_fname_str_dbg(smb_dname),
2473 nt_errstr(status)));
2474 return status;
2477 /* We need to support SeSecurityPrivilege for this. */
2478 if (access_mask & SEC_FLAG_SYSTEM_SECURITY) {
2479 DEBUG(10, ("open_directory: open on %s "
2480 "failed - SEC_FLAG_SYSTEM_SECURITY denied.\n",
2481 smb_fname_str_dbg(smb_dname)));
2482 return NT_STATUS_PRIVILEGE_NOT_HELD;
2485 switch( create_disposition ) {
2486 case FILE_OPEN:
2488 info = FILE_WAS_OPENED;
2491 * We want to follow symlinks here.
2494 if (SMB_VFS_STAT(conn, smb_dname) != 0) {
2495 return map_nt_error_from_unix(errno);
2498 break;
2500 case FILE_CREATE:
2502 /* If directory exists error. If directory doesn't
2503 * exist create. */
2505 status = mkdir_internal(conn, smb_dname,
2506 file_attributes);
2508 if (!NT_STATUS_IS_OK(status)) {
2509 DEBUG(2, ("open_directory: unable to create "
2510 "%s. Error was %s\n",
2511 smb_fname_str_dbg(smb_dname),
2512 nt_errstr(status)));
2513 return status;
2516 info = FILE_WAS_CREATED;
2517 break;
2519 case FILE_OPEN_IF:
2521 * If directory exists open. If directory doesn't
2522 * exist create.
2525 status = mkdir_internal(conn, smb_dname,
2526 file_attributes);
2528 if (NT_STATUS_IS_OK(status)) {
2529 info = FILE_WAS_CREATED;
2532 if (NT_STATUS_EQUAL(status,
2533 NT_STATUS_OBJECT_NAME_COLLISION)) {
2534 info = FILE_WAS_OPENED;
2535 status = NT_STATUS_OK;
2538 break;
2540 case FILE_SUPERSEDE:
2541 case FILE_OVERWRITE:
2542 case FILE_OVERWRITE_IF:
2543 default:
2544 DEBUG(5,("open_directory: invalid create_disposition "
2545 "0x%x for directory %s\n",
2546 (unsigned int)create_disposition,
2547 smb_fname_str_dbg(smb_dname)));
2548 return NT_STATUS_INVALID_PARAMETER;
2551 if(!S_ISDIR(smb_dname->st.st_ex_mode)) {
2552 DEBUG(5,("open_directory: %s is not a directory !\n",
2553 smb_fname_str_dbg(smb_dname)));
2554 return NT_STATUS_NOT_A_DIRECTORY;
2557 if (info == FILE_WAS_OPENED) {
2558 uint32_t access_granted = 0;
2559 status = smbd_check_open_rights(conn, smb_dname, access_mask,
2560 &access_granted);
2562 /* Were we trying to do a directory open
2563 * for delete and didn't get DELETE
2564 * access (only) ? Check if the
2565 * directory allows DELETE_CHILD.
2566 * See here:
2567 * http://blogs.msdn.com/oldnewthing/archive/2004/06/04/148426.aspx
2568 * for details. */
2570 if ((NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED) &&
2571 (access_mask & DELETE_ACCESS) &&
2572 (access_granted == DELETE_ACCESS) &&
2573 can_delete_file_in_directory(conn, smb_dname))) {
2574 DEBUG(10,("open_directory: overrode ACCESS_DENIED "
2575 "on directory %s\n",
2576 smb_fname_str_dbg(smb_dname)));
2577 status = NT_STATUS_OK;
2580 if (!NT_STATUS_IS_OK(status)) {
2581 DEBUG(10, ("open_directory: smbd_check_open_rights on "
2582 "file %s failed with %s\n",
2583 smb_fname_str_dbg(smb_dname),
2584 nt_errstr(status)));
2585 return status;
2589 status = file_new(req, conn, &fsp);
2590 if(!NT_STATUS_IS_OK(status)) {
2591 return status;
2595 * Setup the files_struct for it.
2598 fsp->mode = smb_dname->st.st_ex_mode;
2599 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_dname->st);
2600 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
2601 fsp->file_pid = req ? req->smbpid : 0;
2602 fsp->can_lock = False;
2603 fsp->can_read = False;
2604 fsp->can_write = False;
2606 fsp->share_access = share_access;
2607 fsp->fh->private_options = 0;
2609 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
2611 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
2612 fsp->print_file = False;
2613 fsp->modified = False;
2614 fsp->oplock_type = NO_OPLOCK;
2615 fsp->sent_oplock_break = NO_BREAK_SENT;
2616 fsp->is_directory = True;
2617 fsp->posix_open = (file_attributes & FILE_FLAG_POSIX_SEMANTICS) ? True : False;
2618 status = fsp_set_smb_fname(fsp, smb_dname);
2619 if (!NT_STATUS_IS_OK(status)) {
2620 return status;
2623 mtimespec = smb_dname->st.st_ex_mtime;
2625 lck = get_share_mode_lock(talloc_tos(), fsp->file_id,
2626 conn->connectpath, smb_dname, &mtimespec);
2628 if (lck == NULL) {
2629 DEBUG(0, ("open_directory: Could not get share mode lock for "
2630 "%s\n", smb_fname_str_dbg(smb_dname)));
2631 file_free(req, fsp);
2632 return NT_STATUS_SHARING_VIOLATION;
2635 status = open_mode_check(conn, lck, access_mask, share_access,
2636 create_options, &dir_existed);
2638 if (!NT_STATUS_IS_OK(status)) {
2639 TALLOC_FREE(lck);
2640 file_free(req, fsp);
2641 return status;
2644 set_share_mode(lck, fsp, get_current_uid(conn), 0, NO_OPLOCK);
2646 /* For directories the delete on close bit at open time seems
2647 always to be honored on close... See test 19 in Samba4 BASE-DELETE. */
2648 if (create_options & FILE_DELETE_ON_CLOSE) {
2649 status = can_set_delete_on_close(fsp, 0);
2650 if (!NT_STATUS_IS_OK(status) && !NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
2651 TALLOC_FREE(lck);
2652 file_free(req, fsp);
2653 return status;
2656 if (NT_STATUS_IS_OK(status)) {
2657 /* Note that here we set the *inital* delete on close flag,
2658 not the regular one. The magic gets handled in close. */
2659 fsp->initial_delete_on_close = True;
2663 TALLOC_FREE(lck);
2665 if (pinfo) {
2666 *pinfo = info;
2669 *result = fsp;
2670 return NT_STATUS_OK;
2673 NTSTATUS create_directory(connection_struct *conn, struct smb_request *req,
2674 struct smb_filename *smb_dname)
2676 NTSTATUS status;
2677 files_struct *fsp;
2679 status = SMB_VFS_CREATE_FILE(
2680 conn, /* conn */
2681 req, /* req */
2682 0, /* root_dir_fid */
2683 smb_dname, /* fname */
2684 FILE_READ_ATTRIBUTES, /* access_mask */
2685 FILE_SHARE_NONE, /* share_access */
2686 FILE_CREATE, /* create_disposition*/
2687 FILE_DIRECTORY_FILE, /* create_options */
2688 FILE_ATTRIBUTE_DIRECTORY, /* file_attributes */
2689 0, /* oplock_request */
2690 0, /* allocation_size */
2691 0, /* private_flags */
2692 NULL, /* sd */
2693 NULL, /* ea_list */
2694 &fsp, /* result */
2695 NULL); /* pinfo */
2697 if (NT_STATUS_IS_OK(status)) {
2698 close_file(req, fsp, NORMAL_CLOSE);
2701 return status;
2704 /****************************************************************************
2705 Receive notification that one of our open files has been renamed by another
2706 smbd process.
2707 ****************************************************************************/
2709 void msg_file_was_renamed(struct messaging_context *msg,
2710 void *private_data,
2711 uint32_t msg_type,
2712 struct server_id server_id,
2713 DATA_BLOB *data)
2715 files_struct *fsp;
2716 char *frm = (char *)data->data;
2717 struct file_id id;
2718 const char *sharepath;
2719 const char *base_name;
2720 const char *stream_name;
2721 struct smb_filename *smb_fname = NULL;
2722 size_t sp_len, bn_len;
2723 NTSTATUS status;
2725 if (data->data == NULL
2726 || data->length < MSG_FILE_RENAMED_MIN_SIZE + 2) {
2727 DEBUG(0, ("msg_file_was_renamed: Got invalid msg len %d\n",
2728 (int)data->length));
2729 return;
2732 /* Unpack the message. */
2733 pull_file_id_24(frm, &id);
2734 sharepath = &frm[24];
2735 sp_len = strlen(sharepath);
2736 base_name = sharepath + sp_len + 1;
2737 bn_len = strlen(base_name);
2738 stream_name = sharepath + sp_len + 1 + bn_len + 1;
2740 /* stream_name must always be NULL if there is no stream. */
2741 if (stream_name[0] == '\0') {
2742 stream_name = NULL;
2745 status = create_synthetic_smb_fname(talloc_tos(), base_name,
2746 stream_name, NULL, &smb_fname);
2747 if (!NT_STATUS_IS_OK(status)) {
2748 return;
2751 DEBUG(10,("msg_file_was_renamed: Got rename message for sharepath %s, new name %s, "
2752 "file_id %s\n",
2753 sharepath, smb_fname_str_dbg(smb_fname),
2754 file_id_string_tos(&id)));
2756 for(fsp = file_find_di_first(id); fsp; fsp = file_find_di_next(fsp)) {
2757 if (memcmp(fsp->conn->connectpath, sharepath, sp_len) == 0) {
2759 DEBUG(10,("msg_file_was_renamed: renaming file fnum %d from %s -> %s\n",
2760 fsp->fnum, fsp_str_dbg(fsp),
2761 smb_fname_str_dbg(smb_fname)));
2762 status = fsp_set_smb_fname(fsp, smb_fname);
2763 if (!NT_STATUS_IS_OK(status)) {
2764 goto out;
2766 } else {
2767 /* TODO. JRA. */
2768 /* Now we have the complete path we can work out if this is
2769 actually within this share and adjust newname accordingly. */
2770 DEBUG(10,("msg_file_was_renamed: share mismatch (sharepath %s "
2771 "not sharepath %s) "
2772 "fnum %d from %s -> %s\n",
2773 fsp->conn->connectpath,
2774 sharepath,
2775 fsp->fnum,
2776 fsp_str_dbg(fsp),
2777 smb_fname_str_dbg(smb_fname)));
2780 out:
2781 TALLOC_FREE(smb_fname);
2782 return;
2786 * If a main file is opened for delete, all streams need to be checked for
2787 * !FILE_SHARE_DELETE. Do this by opening with DELETE_ACCESS.
2788 * If that works, delete them all by setting the delete on close and close.
2791 NTSTATUS open_streams_for_delete(connection_struct *conn,
2792 const char *fname)
2794 struct stream_struct *stream_info;
2795 files_struct **streams;
2796 int i;
2797 unsigned int num_streams;
2798 TALLOC_CTX *frame = talloc_stackframe();
2799 NTSTATUS status;
2801 status = SMB_VFS_STREAMINFO(conn, NULL, fname, talloc_tos(),
2802 &num_streams, &stream_info);
2804 if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_IMPLEMENTED)
2805 || NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
2806 DEBUG(10, ("no streams around\n"));
2807 TALLOC_FREE(frame);
2808 return NT_STATUS_OK;
2811 if (!NT_STATUS_IS_OK(status)) {
2812 DEBUG(10, ("SMB_VFS_STREAMINFO failed: %s\n",
2813 nt_errstr(status)));
2814 goto fail;
2817 DEBUG(10, ("open_streams_for_delete found %d streams\n",
2818 num_streams));
2820 if (num_streams == 0) {
2821 TALLOC_FREE(frame);
2822 return NT_STATUS_OK;
2825 streams = TALLOC_ARRAY(talloc_tos(), files_struct *, num_streams);
2826 if (streams == NULL) {
2827 DEBUG(0, ("talloc failed\n"));
2828 status = NT_STATUS_NO_MEMORY;
2829 goto fail;
2832 for (i=0; i<num_streams; i++) {
2833 struct smb_filename *smb_fname = NULL;
2835 if (strequal(stream_info[i].name, "::$DATA")) {
2836 streams[i] = NULL;
2837 continue;
2840 status = create_synthetic_smb_fname(talloc_tos(), fname,
2841 stream_info[i].name,
2842 NULL, &smb_fname);
2843 if (!NT_STATUS_IS_OK(status)) {
2844 goto fail;
2847 if (SMB_VFS_STAT(conn, smb_fname) == -1) {
2848 DEBUG(10, ("Unable to stat stream: %s\n",
2849 smb_fname_str_dbg(smb_fname)));
2852 status = SMB_VFS_CREATE_FILE(
2853 conn, /* conn */
2854 NULL, /* req */
2855 0, /* root_dir_fid */
2856 smb_fname, /* fname */
2857 DELETE_ACCESS, /* access_mask */
2858 (FILE_SHARE_READ | /* share_access */
2859 FILE_SHARE_WRITE | FILE_SHARE_DELETE),
2860 FILE_OPEN, /* create_disposition*/
2861 0, /* create_options */
2862 FILE_ATTRIBUTE_NORMAL, /* file_attributes */
2863 0, /* oplock_request */
2864 0, /* allocation_size */
2865 NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE, /* private_flags */
2866 NULL, /* sd */
2867 NULL, /* ea_list */
2868 &streams[i], /* result */
2869 NULL); /* pinfo */
2871 if (!NT_STATUS_IS_OK(status)) {
2872 DEBUG(10, ("Could not open stream %s: %s\n",
2873 smb_fname_str_dbg(smb_fname),
2874 nt_errstr(status)));
2876 TALLOC_FREE(smb_fname);
2877 break;
2879 TALLOC_FREE(smb_fname);
2883 * don't touch the variable "status" beyond this point :-)
2886 for (i -= 1 ; i >= 0; i--) {
2887 if (streams[i] == NULL) {
2888 continue;
2891 DEBUG(10, ("Closing stream # %d, %s\n", i,
2892 fsp_str_dbg(streams[i])));
2893 close_file(NULL, streams[i], NORMAL_CLOSE);
2896 fail:
2897 TALLOC_FREE(frame);
2898 return status;
2902 * Wrapper around open_file_ntcreate and open_directory
2905 static NTSTATUS create_file_unixpath(connection_struct *conn,
2906 struct smb_request *req,
2907 struct smb_filename *smb_fname,
2908 uint32_t access_mask,
2909 uint32_t share_access,
2910 uint32_t create_disposition,
2911 uint32_t create_options,
2912 uint32_t file_attributes,
2913 uint32_t oplock_request,
2914 uint64_t allocation_size,
2915 uint32_t private_flags,
2916 struct security_descriptor *sd,
2917 struct ea_list *ea_list,
2919 files_struct **result,
2920 int *pinfo)
2922 int info = FILE_WAS_OPENED;
2923 files_struct *base_fsp = NULL;
2924 files_struct *fsp = NULL;
2925 NTSTATUS status;
2927 DEBUG(10,("create_file_unixpath: access_mask = 0x%x "
2928 "file_attributes = 0x%x, share_access = 0x%x, "
2929 "create_disposition = 0x%x create_options = 0x%x "
2930 "oplock_request = 0x%x private_flags = 0x%x "
2931 "ea_list = 0x%p, sd = 0x%p, "
2932 "fname = %s\n",
2933 (unsigned int)access_mask,
2934 (unsigned int)file_attributes,
2935 (unsigned int)share_access,
2936 (unsigned int)create_disposition,
2937 (unsigned int)create_options,
2938 (unsigned int)oplock_request,
2939 (unsigned int)private_flags,
2940 ea_list, sd, smb_fname_str_dbg(smb_fname)));
2942 if (create_options & FILE_OPEN_BY_FILE_ID) {
2943 status = NT_STATUS_NOT_SUPPORTED;
2944 goto fail;
2947 if (create_options & NTCREATEX_OPTIONS_INVALID_PARAM_MASK) {
2948 status = NT_STATUS_INVALID_PARAMETER;
2949 goto fail;
2952 if (req == NULL) {
2953 oplock_request |= INTERNAL_OPEN_ONLY;
2956 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
2957 && (access_mask & DELETE_ACCESS)
2958 && !is_ntfs_stream_smb_fname(smb_fname)) {
2960 * We can't open a file with DELETE access if any of the
2961 * streams is open without FILE_SHARE_DELETE
2963 status = open_streams_for_delete(conn, smb_fname->base_name);
2965 if (!NT_STATUS_IS_OK(status)) {
2966 goto fail;
2970 /* This is the correct thing to do (check every time) but can_delete
2971 * is expensive (it may have to read the parent directory
2972 * permissions). So for now we're not doing it unless we have a strong
2973 * hint the client is really going to delete this file. If the client
2974 * is forcing FILE_CREATE let the filesystem take care of the
2975 * permissions. */
2977 /* Setting FILE_SHARE_DELETE is the hint. */
2979 if (lp_acl_check_permissions(SNUM(conn))
2980 && (create_disposition != FILE_CREATE)
2981 && (share_access & FILE_SHARE_DELETE)
2982 && (access_mask & DELETE_ACCESS)
2983 && (!(can_delete_file_in_directory(conn, smb_fname) ||
2984 can_access_file_acl(conn, smb_fname, DELETE_ACCESS)))) {
2985 status = NT_STATUS_ACCESS_DENIED;
2986 DEBUG(10,("create_file_unixpath: open file %s "
2987 "for delete ACCESS_DENIED\n",
2988 smb_fname_str_dbg(smb_fname)));
2989 goto fail;
2992 #if 0
2993 /* We need to support SeSecurityPrivilege for this. */
2994 if ((access_mask & SEC_FLAG_SYSTEM_SECURITY) &&
2995 !user_has_privileges(current_user.nt_user_token,
2996 &se_security)) {
2997 status = NT_STATUS_PRIVILEGE_NOT_HELD;
2998 goto fail;
3000 #else
3001 /* We need to support SeSecurityPrivilege for this. */
3002 if (access_mask & SEC_FLAG_SYSTEM_SECURITY) {
3003 status = NT_STATUS_PRIVILEGE_NOT_HELD;
3004 goto fail;
3006 /* Don't allow a SACL set from an NTtrans create until we
3007 * support SeSecurityPrivilege. */
3008 if (!VALID_STAT(smb_fname->st) &&
3009 lp_nt_acl_support(SNUM(conn)) &&
3010 sd && (sd->sacl != NULL)) {
3011 status = NT_STATUS_PRIVILEGE_NOT_HELD;
3012 goto fail;
3014 #endif
3016 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
3017 && is_ntfs_stream_smb_fname(smb_fname)
3018 && (!(private_flags & NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE))) {
3019 uint32 base_create_disposition;
3020 struct smb_filename *smb_fname_base = NULL;
3022 if (create_options & FILE_DIRECTORY_FILE) {
3023 status = NT_STATUS_NOT_A_DIRECTORY;
3024 goto fail;
3027 switch (create_disposition) {
3028 case FILE_OPEN:
3029 base_create_disposition = FILE_OPEN;
3030 break;
3031 default:
3032 base_create_disposition = FILE_OPEN_IF;
3033 break;
3036 /* Create an smb_filename with stream_name == NULL. */
3037 status = create_synthetic_smb_fname(talloc_tos(),
3038 smb_fname->base_name,
3039 NULL, NULL,
3040 &smb_fname_base);
3041 if (!NT_STATUS_IS_OK(status)) {
3042 goto fail;
3045 if (SMB_VFS_STAT(conn, smb_fname_base) == -1) {
3046 DEBUG(10, ("Unable to stat stream: %s\n",
3047 smb_fname_str_dbg(smb_fname_base)));
3050 /* Open the base file. */
3051 status = create_file_unixpath(conn, NULL, smb_fname_base, 0,
3052 FILE_SHARE_READ
3053 | FILE_SHARE_WRITE
3054 | FILE_SHARE_DELETE,
3055 base_create_disposition,
3056 0, 0, 0, 0, 0, NULL, NULL,
3057 &base_fsp, NULL);
3058 TALLOC_FREE(smb_fname_base);
3060 if (!NT_STATUS_IS_OK(status)) {
3061 DEBUG(10, ("create_file_unixpath for base %s failed: "
3062 "%s\n", smb_fname->base_name,
3063 nt_errstr(status)));
3064 goto fail;
3066 /* we don't need to low level fd */
3067 fd_close(base_fsp);
3071 * If it's a request for a directory open, deal with it separately.
3074 if (create_options & FILE_DIRECTORY_FILE) {
3076 if (create_options & FILE_NON_DIRECTORY_FILE) {
3077 status = NT_STATUS_INVALID_PARAMETER;
3078 goto fail;
3081 /* Can't open a temp directory. IFS kit test. */
3082 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
3083 (file_attributes & FILE_ATTRIBUTE_TEMPORARY)) {
3084 status = NT_STATUS_INVALID_PARAMETER;
3085 goto fail;
3089 * We will get a create directory here if the Win32
3090 * app specified a security descriptor in the
3091 * CreateDirectory() call.
3094 oplock_request = 0;
3095 status = open_directory(
3096 conn, req, smb_fname, access_mask, share_access,
3097 create_disposition, create_options, file_attributes,
3098 &info, &fsp);
3099 } else {
3102 * Ordinary file case.
3105 status = file_new(req, conn, &fsp);
3106 if(!NT_STATUS_IS_OK(status)) {
3107 goto fail;
3110 status = fsp_set_smb_fname(fsp, smb_fname);
3111 if (!NT_STATUS_IS_OK(status)) {
3112 goto fail;
3116 * We're opening the stream element of a base_fsp
3117 * we already opened. Set up the base_fsp pointer.
3119 if (base_fsp) {
3120 fsp->base_fsp = base_fsp;
3123 status = open_file_ntcreate(conn,
3124 req,
3125 access_mask,
3126 share_access,
3127 create_disposition,
3128 create_options,
3129 file_attributes,
3130 oplock_request,
3131 private_flags,
3132 &info,
3133 fsp);
3135 if(!NT_STATUS_IS_OK(status)) {
3136 file_free(req, fsp);
3137 fsp = NULL;
3140 if (NT_STATUS_EQUAL(status, NT_STATUS_FILE_IS_A_DIRECTORY)) {
3142 /* A stream open never opens a directory */
3144 if (base_fsp) {
3145 status = NT_STATUS_FILE_IS_A_DIRECTORY;
3146 goto fail;
3150 * Fail the open if it was explicitly a non-directory
3151 * file.
3154 if (create_options & FILE_NON_DIRECTORY_FILE) {
3155 status = NT_STATUS_FILE_IS_A_DIRECTORY;
3156 goto fail;
3159 oplock_request = 0;
3160 status = open_directory(
3161 conn, req, smb_fname, access_mask,
3162 share_access, create_disposition,
3163 create_options, file_attributes,
3164 &info, &fsp);
3168 if (!NT_STATUS_IS_OK(status)) {
3169 goto fail;
3172 fsp->base_fsp = base_fsp;
3175 * According to the MS documentation, the only time the security
3176 * descriptor is applied to the opened file is iff we *created* the
3177 * file; an existing file stays the same.
3179 * Also, it seems (from observation) that you can open the file with
3180 * any access mask but you can still write the sd. We need to override
3181 * the granted access before we call set_sd
3182 * Patch for bug #2242 from Tom Lackemann <cessnatomny@yahoo.com>.
3185 if ((sd != NULL) && (info == FILE_WAS_CREATED)
3186 && lp_nt_acl_support(SNUM(conn))) {
3188 uint32_t sec_info_sent;
3189 uint32_t saved_access_mask = fsp->access_mask;
3191 sec_info_sent = get_sec_info(sd);
3193 fsp->access_mask = FILE_GENERIC_ALL;
3195 /* Convert all the generic bits. */
3196 security_acl_map_generic(sd->dacl, &file_generic_mapping);
3197 security_acl_map_generic(sd->sacl, &file_generic_mapping);
3199 if (sec_info_sent & (OWNER_SECURITY_INFORMATION|
3200 GROUP_SECURITY_INFORMATION|
3201 DACL_SECURITY_INFORMATION|
3202 SACL_SECURITY_INFORMATION)) {
3203 status = SMB_VFS_FSET_NT_ACL(fsp, sec_info_sent, sd);
3206 fsp->access_mask = saved_access_mask;
3208 if (!NT_STATUS_IS_OK(status)) {
3209 goto fail;
3213 if ((ea_list != NULL) &&
3214 ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN))) {
3215 status = set_ea(conn, fsp, fsp->fsp_name, ea_list);
3216 if (!NT_STATUS_IS_OK(status)) {
3217 goto fail;
3221 if (!fsp->is_directory && S_ISDIR(fsp->fsp_name->st.st_ex_mode)) {
3222 status = NT_STATUS_ACCESS_DENIED;
3223 goto fail;
3226 /* Save the requested allocation size. */
3227 if ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN)) {
3228 if (allocation_size
3229 && (allocation_size > fsp->fsp_name->st.st_ex_size)) {
3230 fsp->initial_allocation_size = smb_roundup(
3231 fsp->conn, allocation_size);
3232 if (fsp->is_directory) {
3233 /* Can't set allocation size on a directory. */
3234 status = NT_STATUS_ACCESS_DENIED;
3235 goto fail;
3237 if (vfs_allocate_file_space(
3238 fsp, fsp->initial_allocation_size) == -1) {
3239 status = NT_STATUS_DISK_FULL;
3240 goto fail;
3242 } else {
3243 fsp->initial_allocation_size = smb_roundup(
3244 fsp->conn, (uint64_t)fsp->fsp_name->st.st_ex_size);
3248 DEBUG(10, ("create_file_unixpath: info=%d\n", info));
3250 *result = fsp;
3251 if (pinfo != NULL) {
3252 *pinfo = info;
3255 smb_fname->st = fsp->fsp_name->st;
3257 return NT_STATUS_OK;
3259 fail:
3260 DEBUG(10, ("create_file_unixpath: %s\n", nt_errstr(status)));
3262 if (fsp != NULL) {
3263 if (base_fsp && fsp->base_fsp == base_fsp) {
3265 * The close_file below will close
3266 * fsp->base_fsp.
3268 base_fsp = NULL;
3270 close_file(req, fsp, ERROR_CLOSE);
3271 fsp = NULL;
3273 if (base_fsp != NULL) {
3274 close_file(req, base_fsp, ERROR_CLOSE);
3275 base_fsp = NULL;
3277 return status;
3281 * Calculate the full path name given a relative fid.
3283 NTSTATUS get_relative_fid_filename(connection_struct *conn,
3284 struct smb_request *req,
3285 uint16_t root_dir_fid,
3286 struct smb_filename *smb_fname)
3288 files_struct *dir_fsp;
3289 char *parent_fname = NULL;
3290 char *new_base_name = NULL;
3291 NTSTATUS status;
3293 if (root_dir_fid == 0 || !smb_fname) {
3294 status = NT_STATUS_INTERNAL_ERROR;
3295 goto out;
3298 dir_fsp = file_fsp(req, root_dir_fid);
3300 if (dir_fsp == NULL) {
3301 status = NT_STATUS_INVALID_HANDLE;
3302 goto out;
3305 if (is_ntfs_stream_smb_fname(dir_fsp->fsp_name)) {
3306 status = NT_STATUS_INVALID_HANDLE;
3307 goto out;
3310 if (!dir_fsp->is_directory) {
3313 * Check to see if this is a mac fork of some kind.
3316 if ((conn->fs_capabilities & FILE_NAMED_STREAMS) &&
3317 is_ntfs_stream_smb_fname(smb_fname)) {
3318 status = NT_STATUS_OBJECT_PATH_NOT_FOUND;
3319 goto out;
3323 we need to handle the case when we get a
3324 relative open relative to a file and the
3325 pathname is blank - this is a reopen!
3326 (hint from demyn plantenberg)
3329 status = NT_STATUS_INVALID_HANDLE;
3330 goto out;
3333 if (ISDOT(dir_fsp->fsp_name->base_name)) {
3335 * We're at the toplevel dir, the final file name
3336 * must not contain ./, as this is filtered out
3337 * normally by srvstr_get_path and unix_convert
3338 * explicitly rejects paths containing ./.
3340 parent_fname = talloc_strdup(talloc_tos(), "");
3341 if (parent_fname == NULL) {
3342 status = NT_STATUS_NO_MEMORY;
3343 goto out;
3345 } else {
3346 size_t dir_name_len = strlen(dir_fsp->fsp_name->base_name);
3349 * Copy in the base directory name.
3352 parent_fname = TALLOC_ARRAY(talloc_tos(), char,
3353 dir_name_len+2);
3354 if (parent_fname == NULL) {
3355 status = NT_STATUS_NO_MEMORY;
3356 goto out;
3358 memcpy(parent_fname, dir_fsp->fsp_name->base_name,
3359 dir_name_len+1);
3362 * Ensure it ends in a '/'.
3363 * We used TALLOC_SIZE +2 to add space for the '/'.
3366 if(dir_name_len
3367 && (parent_fname[dir_name_len-1] != '\\')
3368 && (parent_fname[dir_name_len-1] != '/')) {
3369 parent_fname[dir_name_len] = '/';
3370 parent_fname[dir_name_len+1] = '\0';
3374 new_base_name = talloc_asprintf(smb_fname, "%s%s", parent_fname,
3375 smb_fname->base_name);
3376 if (new_base_name == NULL) {
3377 status = NT_STATUS_NO_MEMORY;
3378 goto out;
3381 TALLOC_FREE(smb_fname->base_name);
3382 smb_fname->base_name = new_base_name;
3383 status = NT_STATUS_OK;
3385 out:
3386 TALLOC_FREE(parent_fname);
3387 return status;
3390 NTSTATUS create_file_default(connection_struct *conn,
3391 struct smb_request *req,
3392 uint16_t root_dir_fid,
3393 struct smb_filename *smb_fname,
3394 uint32_t access_mask,
3395 uint32_t share_access,
3396 uint32_t create_disposition,
3397 uint32_t create_options,
3398 uint32_t file_attributes,
3399 uint32_t oplock_request,
3400 uint64_t allocation_size,
3401 uint32_t private_flags,
3402 struct security_descriptor *sd,
3403 struct ea_list *ea_list,
3404 files_struct **result,
3405 int *pinfo)
3407 int info = FILE_WAS_OPENED;
3408 files_struct *fsp = NULL;
3409 NTSTATUS status;
3411 DEBUG(10,("create_file: access_mask = 0x%x "
3412 "file_attributes = 0x%x, share_access = 0x%x, "
3413 "create_disposition = 0x%x create_options = 0x%x "
3414 "oplock_request = 0x%x "
3415 "private_flags = 0x%x "
3416 "root_dir_fid = 0x%x, ea_list = 0x%p, sd = 0x%p, "
3417 "fname = %s\n",
3418 (unsigned int)access_mask,
3419 (unsigned int)file_attributes,
3420 (unsigned int)share_access,
3421 (unsigned int)create_disposition,
3422 (unsigned int)create_options,
3423 (unsigned int)oplock_request,
3424 (unsigned int)private_flags,
3425 (unsigned int)root_dir_fid,
3426 ea_list, sd, smb_fname_str_dbg(smb_fname)));
3429 * Calculate the filename from the root_dir_if if necessary.
3432 if (root_dir_fid != 0) {
3433 status = get_relative_fid_filename(conn, req, root_dir_fid,
3434 smb_fname);
3435 if (!NT_STATUS_IS_OK(status)) {
3436 goto fail;
3441 * Check to see if this is a mac fork of some kind.
3444 if (is_ntfs_stream_smb_fname(smb_fname)) {
3445 enum FAKE_FILE_TYPE fake_file_type;
3447 fake_file_type = is_fake_file(smb_fname);
3449 if (fake_file_type != FAKE_FILE_TYPE_NONE) {
3452 * Here we go! support for changing the disk quotas
3453 * --metze
3455 * We need to fake up to open this MAGIC QUOTA file
3456 * and return a valid FID.
3458 * w2k close this file directly after openening xp
3459 * also tries a QUERY_FILE_INFO on the file and then
3460 * close it
3462 status = open_fake_file(req, conn, req->vuid,
3463 fake_file_type, smb_fname,
3464 access_mask, &fsp);
3465 if (!NT_STATUS_IS_OK(status)) {
3466 goto fail;
3469 ZERO_STRUCT(smb_fname->st);
3470 goto done;
3473 if (!(conn->fs_capabilities & FILE_NAMED_STREAMS)) {
3474 status = NT_STATUS_OBJECT_NAME_NOT_FOUND;
3475 goto fail;
3479 /* All file access must go through check_name() */
3481 status = check_name(conn, smb_fname->base_name);
3482 if (!NT_STATUS_IS_OK(status)) {
3483 goto fail;
3486 status = create_file_unixpath(
3487 conn, req, smb_fname, access_mask, share_access,
3488 create_disposition, create_options, file_attributes,
3489 oplock_request, allocation_size, private_flags,
3490 sd, ea_list,
3491 &fsp, &info);
3493 if (!NT_STATUS_IS_OK(status)) {
3494 goto fail;
3497 done:
3498 DEBUG(10, ("create_file: info=%d\n", info));
3500 *result = fsp;
3501 if (pinfo != NULL) {
3502 *pinfo = info;
3504 return NT_STATUS_OK;
3506 fail:
3507 DEBUG(10, ("create_file: %s\n", nt_errstr(status)));
3509 if (fsp != NULL) {
3510 close_file(req, fsp, ERROR_CLOSE);
3511 fsp = NULL;
3513 return status;