s3-lanman: remove defines now provided by IDL.
[Samba/ekacnet.git] / source3 / smbd / open.c
blobce69157df5741063400a8d6dfafac21e9ded7750
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"
24 #include "librpc/gen_ndr/messaging.h"
26 extern const struct generic_mapping file_generic_mapping;
28 struct deferred_open_record {
29 bool delayed_for_oplocks;
30 struct file_id id;
33 static NTSTATUS create_file_unixpath(connection_struct *conn,
34 struct smb_request *req,
35 struct smb_filename *smb_fname,
36 uint32_t access_mask,
37 uint32_t share_access,
38 uint32_t create_disposition,
39 uint32_t create_options,
40 uint32_t file_attributes,
41 uint32_t oplock_request,
42 uint64_t allocation_size,
43 uint32_t private_flags,
44 struct security_descriptor *sd,
45 struct ea_list *ea_list,
47 files_struct **result,
48 int *pinfo);
50 /****************************************************************************
51 SMB1 file varient of se_access_check. Never test FILE_READ_ATTRIBUTES.
52 ****************************************************************************/
54 NTSTATUS smb1_file_se_access_check(struct connection_struct *conn,
55 const struct security_descriptor *sd,
56 const NT_USER_TOKEN *token,
57 uint32_t access_desired,
58 uint32_t *access_granted)
60 *access_granted = 0;
62 if (get_current_uid(conn) == (uid_t)0) {
63 /* I'm sorry sir, I didn't know you were root... */
64 *access_granted = access_desired;
65 if (access_desired & SEC_FLAG_MAXIMUM_ALLOWED) {
66 *access_granted |= FILE_GENERIC_ALL;
68 return NT_STATUS_OK;
71 return se_access_check(sd,
72 token,
73 (access_desired & ~FILE_READ_ATTRIBUTES),
74 access_granted);
77 /****************************************************************************
78 Check if we have open rights.
79 ****************************************************************************/
81 NTSTATUS smbd_check_open_rights(struct connection_struct *conn,
82 const struct smb_filename *smb_fname,
83 uint32_t access_mask,
84 uint32_t *access_granted)
86 /* Check if we have rights to open. */
87 NTSTATUS status;
88 struct security_descriptor *sd = NULL;
90 status = SMB_VFS_GET_NT_ACL(conn, smb_fname->base_name,
91 (OWNER_SECURITY_INFORMATION |
92 GROUP_SECURITY_INFORMATION |
93 DACL_SECURITY_INFORMATION),&sd);
95 if (!NT_STATUS_IS_OK(status)) {
96 DEBUG(10, ("smbd_check_open_rights: Could not get acl "
97 "on %s: %s\n",
98 smb_fname_str_dbg(smb_fname),
99 nt_errstr(status)));
100 return status;
103 status = smb1_file_se_access_check(conn,
105 get_current_nttok(conn),
106 access_mask,
107 access_granted);
109 DEBUG(10,("smbd_check_open_rights: file %s requesting "
110 "0x%x returning 0x%x (%s)\n",
111 smb_fname_str_dbg(smb_fname),
112 (unsigned int)access_mask,
113 (unsigned int)*access_granted,
114 nt_errstr(status) ));
116 if (!NT_STATUS_IS_OK(status)) {
117 if (DEBUGLEVEL >= 10) {
118 DEBUG(10,("smbd_check_open_rights: acl for %s is:\n",
119 smb_fname_str_dbg(smb_fname) ));
120 NDR_PRINT_DEBUG(security_descriptor, sd);
124 TALLOC_FREE(sd);
126 return status;
129 /****************************************************************************
130 fd support routines - attempt to do a dos_open.
131 ****************************************************************************/
133 static NTSTATUS fd_open(struct connection_struct *conn,
134 files_struct *fsp,
135 int flags,
136 mode_t mode)
138 struct smb_filename *smb_fname = fsp->fsp_name;
139 NTSTATUS status = NT_STATUS_OK;
141 #ifdef O_NOFOLLOW
143 * Never follow symlinks on a POSIX client. The
144 * client should be doing this.
147 if (fsp->posix_open || !lp_symlinks(SNUM(conn))) {
148 flags |= O_NOFOLLOW;
150 #endif
152 fsp->fh->fd = SMB_VFS_OPEN(conn, smb_fname, fsp, flags, mode);
153 if (fsp->fh->fd == -1) {
154 status = map_nt_error_from_unix(errno);
155 if (errno == EMFILE) {
156 static time_t last_warned = 0L;
158 if (time((time_t *) NULL) > last_warned) {
159 DEBUG(0,("Too many open files, unable "
160 "to open more! smbd's max "
161 "open files = %d\n",
162 lp_max_open_files()));
163 last_warned = time((time_t *) NULL);
169 DEBUG(10,("fd_open: name %s, flags = 0%o mode = 0%o, fd = %d. %s\n",
170 smb_fname_str_dbg(smb_fname), flags, (int)mode, fsp->fh->fd,
171 (fsp->fh->fd == -1) ? strerror(errno) : "" ));
173 return status;
176 /****************************************************************************
177 Close the file associated with a fsp.
178 ****************************************************************************/
180 NTSTATUS fd_close(files_struct *fsp)
182 int ret;
184 if (fsp->fh->fd == -1) {
185 return NT_STATUS_OK; /* What we used to call a stat open. */
187 if (fsp->fh->ref_count > 1) {
188 return NT_STATUS_OK; /* Shared handle. Only close last reference. */
191 ret = SMB_VFS_CLOSE(fsp);
192 fsp->fh->fd = -1;
193 if (ret == -1) {
194 return map_nt_error_from_unix(errno);
196 return NT_STATUS_OK;
199 /****************************************************************************
200 Change the ownership of a file to that of the parent directory.
201 Do this by fd if possible.
202 ****************************************************************************/
204 void change_file_owner_to_parent(connection_struct *conn,
205 const char *inherit_from_dir,
206 files_struct *fsp)
208 struct smb_filename *smb_fname_parent = NULL;
209 NTSTATUS status;
210 int ret;
212 status = create_synthetic_smb_fname(talloc_tos(), inherit_from_dir,
213 NULL, NULL, &smb_fname_parent);
214 if (!NT_STATUS_IS_OK(status)) {
215 return;
218 ret = SMB_VFS_STAT(conn, smb_fname_parent);
219 if (ret == -1) {
220 DEBUG(0,("change_file_owner_to_parent: failed to stat parent "
221 "directory %s. Error was %s\n",
222 smb_fname_str_dbg(smb_fname_parent),
223 strerror(errno)));
224 return;
227 become_root();
228 ret = SMB_VFS_FCHOWN(fsp, smb_fname_parent->st.st_ex_uid, (gid_t)-1);
229 unbecome_root();
230 if (ret == -1) {
231 DEBUG(0,("change_file_owner_to_parent: failed to fchown "
232 "file %s to parent directory uid %u. Error "
233 "was %s\n", fsp_str_dbg(fsp),
234 (unsigned int)smb_fname_parent->st.st_ex_uid,
235 strerror(errno) ));
238 DEBUG(10,("change_file_owner_to_parent: changed new file %s to "
239 "parent directory uid %u.\n", fsp_str_dbg(fsp),
240 (unsigned int)smb_fname_parent->st.st_ex_uid));
242 TALLOC_FREE(smb_fname_parent);
245 NTSTATUS change_dir_owner_to_parent(connection_struct *conn,
246 const char *inherit_from_dir,
247 const char *fname,
248 SMB_STRUCT_STAT *psbuf)
250 struct smb_filename *smb_fname_parent = NULL;
251 struct smb_filename *smb_fname_cwd = NULL;
252 char *saved_dir = NULL;
253 TALLOC_CTX *ctx = talloc_tos();
254 NTSTATUS status = NT_STATUS_OK;
255 int ret;
257 status = create_synthetic_smb_fname(ctx, inherit_from_dir, NULL, NULL,
258 &smb_fname_parent);
259 if (!NT_STATUS_IS_OK(status)) {
260 return status;
263 ret = SMB_VFS_STAT(conn, smb_fname_parent);
264 if (ret == -1) {
265 status = map_nt_error_from_unix(errno);
266 DEBUG(0,("change_dir_owner_to_parent: failed to stat parent "
267 "directory %s. Error was %s\n",
268 smb_fname_str_dbg(smb_fname_parent),
269 strerror(errno)));
270 goto out;
273 /* We've already done an lstat into psbuf, and we know it's a
274 directory. If we can cd into the directory and the dev/ino
275 are the same then we can safely chown without races as
276 we're locking the directory in place by being in it. This
277 should work on any UNIX (thanks tridge :-). JRA.
280 saved_dir = vfs_GetWd(ctx,conn);
281 if (!saved_dir) {
282 status = map_nt_error_from_unix(errno);
283 DEBUG(0,("change_dir_owner_to_parent: failed to get "
284 "current working directory. Error was %s\n",
285 strerror(errno)));
286 goto out;
289 /* Chdir into the new path. */
290 if (vfs_ChDir(conn, fname) == -1) {
291 status = map_nt_error_from_unix(errno);
292 DEBUG(0,("change_dir_owner_to_parent: failed to change "
293 "current working directory to %s. Error "
294 "was %s\n", fname, strerror(errno) ));
295 goto chdir;
298 status = create_synthetic_smb_fname(ctx, ".", NULL, NULL,
299 &smb_fname_cwd);
300 if (!NT_STATUS_IS_OK(status)) {
301 return status;
304 ret = SMB_VFS_STAT(conn, smb_fname_cwd);
305 if (ret == -1) {
306 status = map_nt_error_from_unix(errno);
307 DEBUG(0,("change_dir_owner_to_parent: failed to stat "
308 "directory '.' (%s) Error was %s\n",
309 fname, strerror(errno)));
310 goto chdir;
313 /* Ensure we're pointing at the same place. */
314 if (smb_fname_cwd->st.st_ex_dev != psbuf->st_ex_dev ||
315 smb_fname_cwd->st.st_ex_ino != psbuf->st_ex_ino ||
316 smb_fname_cwd->st.st_ex_mode != psbuf->st_ex_mode ) {
317 DEBUG(0,("change_dir_owner_to_parent: "
318 "device/inode/mode on directory %s changed. "
319 "Refusing to chown !\n", fname ));
320 status = NT_STATUS_ACCESS_DENIED;
321 goto chdir;
324 become_root();
325 ret = SMB_VFS_CHOWN(conn, ".", smb_fname_parent->st.st_ex_uid,
326 (gid_t)-1);
327 unbecome_root();
328 if (ret == -1) {
329 status = map_nt_error_from_unix(errno);
330 DEBUG(10,("change_dir_owner_to_parent: failed to chown "
331 "directory %s to parent directory uid %u. "
332 "Error was %s\n", fname,
333 (unsigned int)smb_fname_parent->st.st_ex_uid,
334 strerror(errno) ));
335 goto chdir;
338 DEBUG(10,("change_dir_owner_to_parent: changed ownership of new "
339 "directory %s to parent directory uid %u.\n",
340 fname, (unsigned int)smb_fname_parent->st.st_ex_uid ));
342 chdir:
343 vfs_ChDir(conn,saved_dir);
344 out:
345 TALLOC_FREE(smb_fname_parent);
346 TALLOC_FREE(smb_fname_cwd);
347 return status;
350 /****************************************************************************
351 Open a file.
352 ****************************************************************************/
354 static NTSTATUS open_file(files_struct *fsp,
355 connection_struct *conn,
356 struct smb_request *req,
357 const char *parent_dir,
358 int flags,
359 mode_t unx_mode,
360 uint32 access_mask, /* client requested access mask. */
361 uint32 open_access_mask) /* what we're actually using in the open. */
363 struct smb_filename *smb_fname = fsp->fsp_name;
364 NTSTATUS status = NT_STATUS_OK;
365 int accmode = (flags & O_ACCMODE);
366 int local_flags = flags;
367 bool file_existed = VALID_STAT(fsp->fsp_name->st);
369 fsp->fh->fd = -1;
370 errno = EPERM;
372 /* Check permissions */
375 * This code was changed after seeing a client open request
376 * containing the open mode of (DENY_WRITE/read-only) with
377 * the 'create if not exist' bit set. The previous code
378 * would fail to open the file read only on a read-only share
379 * as it was checking the flags parameter directly against O_RDONLY,
380 * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
381 * JRA.
384 if (!CAN_WRITE(conn)) {
385 /* It's a read-only share - fail if we wanted to write. */
386 if(accmode != O_RDONLY || (flags & O_TRUNC) || (flags & O_APPEND)) {
387 DEBUG(3,("Permission denied opening %s\n",
388 smb_fname_str_dbg(smb_fname)));
389 return NT_STATUS_ACCESS_DENIED;
390 } else if(flags & O_CREAT) {
391 /* We don't want to write - but we must make sure that
392 O_CREAT doesn't create the file if we have write
393 access into the directory.
395 flags &= ~(O_CREAT|O_EXCL);
396 local_flags &= ~(O_CREAT|O_EXCL);
401 * This little piece of insanity is inspired by the
402 * fact that an NT client can open a file for O_RDONLY,
403 * but set the create disposition to FILE_EXISTS_TRUNCATE.
404 * If the client *can* write to the file, then it expects to
405 * truncate the file, even though it is opening for readonly.
406 * Quicken uses this stupid trick in backup file creation...
407 * Thanks *greatly* to "David W. Chapman Jr." <dwcjr@inethouston.net>
408 * for helping track this one down. It didn't bite us in 2.0.x
409 * as we always opened files read-write in that release. JRA.
412 if ((accmode == O_RDONLY) && ((flags & O_TRUNC) == O_TRUNC)) {
413 DEBUG(10,("open_file: truncate requested on read-only open "
414 "for file %s\n", smb_fname_str_dbg(smb_fname)));
415 local_flags = (flags & ~O_ACCMODE)|O_RDWR;
418 if ((open_access_mask & (FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA|FILE_EXECUTE)) ||
419 (!file_existed && (local_flags & O_CREAT)) ||
420 ((local_flags & O_TRUNC) == O_TRUNC) ) {
421 const char *wild;
424 * We can't actually truncate here as the file may be locked.
425 * open_file_ntcreate will take care of the truncate later. JRA.
428 local_flags &= ~O_TRUNC;
430 #if defined(O_NONBLOCK) && defined(S_ISFIFO)
432 * We would block on opening a FIFO with no one else on the
433 * other end. Do what we used to do and add O_NONBLOCK to the
434 * open flags. JRA.
437 if (file_existed && S_ISFIFO(smb_fname->st.st_ex_mode)) {
438 local_flags |= O_NONBLOCK;
440 #endif
442 /* Don't create files with Microsoft wildcard characters. */
443 if (fsp->base_fsp) {
445 * wildcard characters are allowed in stream names
446 * only test the basefilename
448 wild = fsp->base_fsp->fsp_name->base_name;
449 } else {
450 wild = smb_fname->base_name;
452 if ((local_flags & O_CREAT) && !file_existed &&
453 ms_has_wild(wild)) {
454 return NT_STATUS_OBJECT_NAME_INVALID;
457 /* Actually do the open */
458 status = fd_open(conn, fsp, local_flags, unx_mode);
459 if (!NT_STATUS_IS_OK(status)) {
460 DEBUG(3,("Error opening file %s (%s) (local_flags=%d) "
461 "(flags=%d)\n", smb_fname_str_dbg(smb_fname),
462 nt_errstr(status),local_flags,flags));
463 return status;
466 if ((local_flags & O_CREAT) && !file_existed) {
468 /* Inherit the ACL if required */
469 if (lp_inherit_perms(SNUM(conn))) {
470 inherit_access_posix_acl(conn, parent_dir,
471 smb_fname->base_name,
472 unx_mode);
475 /* Change the owner if required. */
476 if (lp_inherit_owner(SNUM(conn))) {
477 change_file_owner_to_parent(conn, parent_dir,
478 fsp);
481 notify_fname(conn, NOTIFY_ACTION_ADDED,
482 FILE_NOTIFY_CHANGE_FILE_NAME,
483 smb_fname->base_name);
486 } else {
487 fsp->fh->fd = -1; /* What we used to call a stat open. */
488 if (file_existed) {
489 uint32_t access_granted = 0;
491 status = smbd_check_open_rights(conn,
492 smb_fname,
493 access_mask,
494 &access_granted);
495 if (!NT_STATUS_IS_OK(status)) {
496 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
498 * On NT_STATUS_ACCESS_DENIED, access_granted
499 * contains the denied bits.
502 if ((access_mask & FILE_WRITE_ATTRIBUTES) &&
503 (access_granted & FILE_WRITE_ATTRIBUTES) &&
504 (lp_map_readonly(SNUM(conn)) ||
505 lp_map_archive(SNUM(conn)) ||
506 lp_map_hidden(SNUM(conn)) ||
507 lp_map_system(SNUM(conn)))) {
508 access_granted &= ~FILE_WRITE_ATTRIBUTES;
510 DEBUG(10,("open_file: "
511 "overrode "
512 "FILE_WRITE_"
513 "ATTRIBUTES "
514 "on file %s\n",
515 smb_fname_str_dbg(
516 smb_fname)));
519 if ((access_mask & DELETE_ACCESS) &&
520 (access_granted & DELETE_ACCESS) &&
521 can_delete_file_in_directory(conn,
522 smb_fname)) {
523 /* Were we trying to do a stat open
524 * for delete and didn't get DELETE
525 * access (only) ? Check if the
526 * directory allows DELETE_CHILD.
527 * See here:
528 * http://blogs.msdn.com/oldnewthing/archive/2004/06/04/148426.aspx
529 * for details. */
531 access_granted &= ~DELETE_ACCESS;
533 DEBUG(10,("open_file: "
534 "overrode "
535 "DELETE_ACCESS on "
536 "file %s\n",
537 smb_fname_str_dbg(
538 smb_fname)));
541 if (access_granted != 0) {
542 DEBUG(10,("open_file: Access "
543 "denied on file "
544 "%s\n",
545 smb_fname_str_dbg(
546 smb_fname)));
547 return status;
549 } else if (NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND) &&
550 fsp->posix_open &&
551 S_ISLNK(smb_fname->st.st_ex_mode)) {
552 /* This is a POSIX stat open for delete
553 * or rename on a symlink that points
554 * nowhere. Allow. */
555 DEBUG(10,("open_file: allowing POSIX "
556 "open on bad symlink %s\n",
557 smb_fname_str_dbg(
558 smb_fname)));
559 } else {
560 DEBUG(10,("open_file: "
561 "smbd_check_open_rights on file "
562 "%s returned %s\n",
563 smb_fname_str_dbg(smb_fname),
564 nt_errstr(status) ));
565 return status;
571 if (!file_existed) {
572 int ret;
574 if (fsp->fh->fd == -1) {
575 ret = SMB_VFS_STAT(conn, smb_fname);
576 } else {
577 ret = SMB_VFS_FSTAT(fsp, &smb_fname->st);
578 /* If we have an fd, this stat should succeed. */
579 if (ret == -1) {
580 DEBUG(0,("Error doing fstat on open file %s "
581 "(%s)\n",
582 smb_fname_str_dbg(smb_fname),
583 strerror(errno) ));
587 /* For a non-io open, this stat failing means file not found. JRA */
588 if (ret == -1) {
589 status = map_nt_error_from_unix(errno);
590 fd_close(fsp);
591 return status;
596 * POSIX allows read-only opens of directories. We don't
597 * want to do this (we use a different code path for this)
598 * so catch a directory open and return an EISDIR. JRA.
601 if(S_ISDIR(smb_fname->st.st_ex_mode)) {
602 fd_close(fsp);
603 errno = EISDIR;
604 return NT_STATUS_FILE_IS_A_DIRECTORY;
607 fsp->mode = smb_fname->st.st_ex_mode;
608 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
609 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
610 fsp->file_pid = req ? req->smbpid : 0;
611 fsp->can_lock = True;
612 fsp->can_read = (access_mask & (FILE_READ_DATA)) ? True : False;
613 if (!CAN_WRITE(conn)) {
614 fsp->can_write = False;
615 } else {
616 fsp->can_write = (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ?
617 True : False;
619 fsp->print_file = NULL;
620 fsp->modified = False;
621 fsp->sent_oplock_break = NO_BREAK_SENT;
622 fsp->is_directory = False;
623 if (conn->aio_write_behind_list &&
624 is_in_path(smb_fname->base_name, conn->aio_write_behind_list,
625 conn->case_sensitive)) {
626 fsp->aio_write_behind = True;
629 fsp->wcp = NULL; /* Write cache pointer. */
631 DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
632 conn->server_info->unix_name,
633 smb_fname_str_dbg(smb_fname),
634 BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
635 conn->num_files_open));
637 errno = 0;
638 return NT_STATUS_OK;
641 /*******************************************************************
642 Return True if the filename is one of the special executable types.
643 ********************************************************************/
645 bool is_executable(const char *fname)
647 if ((fname = strrchr_m(fname,'.'))) {
648 if (strequal(fname,".com") ||
649 strequal(fname,".dll") ||
650 strequal(fname,".exe") ||
651 strequal(fname,".sym")) {
652 return True;
655 return False;
658 /****************************************************************************
659 Check if we can open a file with a share mode.
660 Returns True if conflict, False if not.
661 ****************************************************************************/
663 static bool share_conflict(struct share_mode_entry *entry,
664 uint32 access_mask,
665 uint32 share_access)
667 DEBUG(10,("share_conflict: entry->access_mask = 0x%x, "
668 "entry->share_access = 0x%x, "
669 "entry->private_options = 0x%x\n",
670 (unsigned int)entry->access_mask,
671 (unsigned int)entry->share_access,
672 (unsigned int)entry->private_options));
674 DEBUG(10,("share_conflict: access_mask = 0x%x, share_access = 0x%x\n",
675 (unsigned int)access_mask, (unsigned int)share_access));
677 if ((entry->access_mask & (FILE_WRITE_DATA|
678 FILE_APPEND_DATA|
679 FILE_READ_DATA|
680 FILE_EXECUTE|
681 DELETE_ACCESS)) == 0) {
682 DEBUG(10,("share_conflict: No conflict due to "
683 "entry->access_mask = 0x%x\n",
684 (unsigned int)entry->access_mask ));
685 return False;
688 if ((access_mask & (FILE_WRITE_DATA|
689 FILE_APPEND_DATA|
690 FILE_READ_DATA|
691 FILE_EXECUTE|
692 DELETE_ACCESS)) == 0) {
693 DEBUG(10,("share_conflict: No conflict due to "
694 "access_mask = 0x%x\n",
695 (unsigned int)access_mask ));
696 return False;
699 #if 1 /* JRA TEST - Superdebug. */
700 #define CHECK_MASK(num, am, right, sa, share) \
701 DEBUG(10,("share_conflict: [%d] am (0x%x) & right (0x%x) = 0x%x\n", \
702 (unsigned int)(num), (unsigned int)(am), \
703 (unsigned int)(right), (unsigned int)(am)&(right) )); \
704 DEBUG(10,("share_conflict: [%d] sa (0x%x) & share (0x%x) = 0x%x\n", \
705 (unsigned int)(num), (unsigned int)(sa), \
706 (unsigned int)(share), (unsigned int)(sa)&(share) )); \
707 if (((am) & (right)) && !((sa) & (share))) { \
708 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
709 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
710 (unsigned int)(share) )); \
711 return True; \
713 #else
714 #define CHECK_MASK(num, am, right, sa, share) \
715 if (((am) & (right)) && !((sa) & (share))) { \
716 DEBUG(10,("share_conflict: check %d conflict am = 0x%x, right = 0x%x, \
717 sa = 0x%x, share = 0x%x\n", (num), (unsigned int)(am), (unsigned int)(right), (unsigned int)(sa), \
718 (unsigned int)(share) )); \
719 return True; \
721 #endif
723 CHECK_MASK(1, entry->access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
724 share_access, FILE_SHARE_WRITE);
725 CHECK_MASK(2, access_mask, FILE_WRITE_DATA | FILE_APPEND_DATA,
726 entry->share_access, FILE_SHARE_WRITE);
728 CHECK_MASK(3, entry->access_mask, FILE_READ_DATA | FILE_EXECUTE,
729 share_access, FILE_SHARE_READ);
730 CHECK_MASK(4, access_mask, FILE_READ_DATA | FILE_EXECUTE,
731 entry->share_access, FILE_SHARE_READ);
733 CHECK_MASK(5, entry->access_mask, DELETE_ACCESS,
734 share_access, FILE_SHARE_DELETE);
735 CHECK_MASK(6, access_mask, DELETE_ACCESS,
736 entry->share_access, FILE_SHARE_DELETE);
738 DEBUG(10,("share_conflict: No conflict.\n"));
739 return False;
742 #if defined(DEVELOPER)
743 static void validate_my_share_entries(int num,
744 struct share_mode_entry *share_entry)
746 files_struct *fsp;
748 if (!procid_is_me(&share_entry->pid)) {
749 return;
752 if (is_deferred_open_entry(share_entry) &&
753 !open_was_deferred(share_entry->op_mid)) {
754 char *str = talloc_asprintf(talloc_tos(),
755 "Got a deferred entry without a request: "
756 "PANIC: %s\n",
757 share_mode_str(talloc_tos(), num, share_entry));
758 smb_panic(str);
761 if (!is_valid_share_mode_entry(share_entry)) {
762 return;
765 fsp = file_find_dif(share_entry->id,
766 share_entry->share_file_id);
767 if (!fsp) {
768 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
769 share_mode_str(talloc_tos(), num, share_entry) ));
770 smb_panic("validate_my_share_entries: Cannot match a "
771 "share entry with an open file\n");
774 if (is_deferred_open_entry(share_entry) ||
775 is_unused_share_mode_entry(share_entry)) {
776 goto panic;
779 if ((share_entry->op_type == NO_OPLOCK) &&
780 (fsp->oplock_type == FAKE_LEVEL_II_OPLOCK)) {
781 /* Someone has already written to it, but I haven't yet
782 * noticed */
783 return;
786 if (((uint16)fsp->oplock_type) != share_entry->op_type) {
787 goto panic;
790 return;
792 panic:
794 char *str;
795 DEBUG(0,("validate_my_share_entries: PANIC : %s\n",
796 share_mode_str(talloc_tos(), num, share_entry) ));
797 str = talloc_asprintf(talloc_tos(),
798 "validate_my_share_entries: "
799 "file %s, oplock_type = 0x%x, op_type = 0x%x\n",
800 fsp->fsp_name->base_name,
801 (unsigned int)fsp->oplock_type,
802 (unsigned int)share_entry->op_type );
803 smb_panic(str);
806 #endif
808 bool is_stat_open(uint32 access_mask)
810 return (access_mask &&
811 ((access_mask & ~(SYNCHRONIZE_ACCESS| FILE_READ_ATTRIBUTES|
812 FILE_WRITE_ATTRIBUTES))==0) &&
813 ((access_mask & (SYNCHRONIZE_ACCESS|FILE_READ_ATTRIBUTES|
814 FILE_WRITE_ATTRIBUTES)) != 0));
817 /****************************************************************************
818 Deal with share modes
819 Invarient: Share mode must be locked on entry and exit.
820 Returns -1 on error, or number of share modes on success (may be zero).
821 ****************************************************************************/
823 static NTSTATUS open_mode_check(connection_struct *conn,
824 struct share_mode_lock *lck,
825 uint32 access_mask,
826 uint32 share_access,
827 uint32 create_options,
828 bool *file_existed)
830 int i;
832 if(lck->num_share_modes == 0) {
833 return NT_STATUS_OK;
836 *file_existed = True;
838 /* A delete on close prohibits everything */
840 if (lck->delete_on_close) {
841 return NT_STATUS_DELETE_PENDING;
844 if (is_stat_open(access_mask)) {
845 /* Stat open that doesn't trigger oplock breaks or share mode
846 * checks... ! JRA. */
847 return NT_STATUS_OK;
851 * Check if the share modes will give us access.
854 #if defined(DEVELOPER)
855 for(i = 0; i < lck->num_share_modes; i++) {
856 validate_my_share_entries(i, &lck->share_modes[i]);
858 #endif
860 if (!lp_share_modes(SNUM(conn))) {
861 return NT_STATUS_OK;
864 /* Now we check the share modes, after any oplock breaks. */
865 for(i = 0; i < lck->num_share_modes; i++) {
867 if (!is_valid_share_mode_entry(&lck->share_modes[i])) {
868 continue;
871 /* someone else has a share lock on it, check to see if we can
872 * too */
873 if (share_conflict(&lck->share_modes[i],
874 access_mask, share_access)) {
875 return NT_STATUS_SHARING_VIOLATION;
879 return NT_STATUS_OK;
882 static bool is_delete_request(files_struct *fsp) {
883 return ((fsp->access_mask == DELETE_ACCESS) &&
884 (fsp->oplock_type == NO_OPLOCK));
888 * Send a break message to the oplock holder and delay the open for
889 * our client.
892 static NTSTATUS send_break_message(files_struct *fsp,
893 struct share_mode_entry *exclusive,
894 uint64_t mid,
895 int oplock_request)
897 NTSTATUS status;
898 char msg[MSG_SMB_SHARE_MODE_ENTRY_SIZE];
900 DEBUG(10, ("Sending break request to PID %s\n",
901 procid_str_static(&exclusive->pid)));
902 exclusive->op_mid = mid;
904 /* Create the message. */
905 share_mode_entry_to_message(msg, exclusive);
907 /* Add in the FORCE_OPLOCK_BREAK_TO_NONE bit in the message if set. We
908 don't want this set in the share mode struct pointed to by lck. */
910 if (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE) {
911 SSVAL(msg,OP_BREAK_MSG_OP_TYPE_OFFSET,
912 exclusive->op_type | FORCE_OPLOCK_BREAK_TO_NONE);
915 status = messaging_send_buf(smbd_messaging_context(), exclusive->pid,
916 MSG_SMB_BREAK_REQUEST,
917 (uint8 *)msg,
918 MSG_SMB_SHARE_MODE_ENTRY_SIZE);
919 if (!NT_STATUS_IS_OK(status)) {
920 DEBUG(3, ("Could not send oplock break message: %s\n",
921 nt_errstr(status)));
924 return status;
928 * 1) No files open at all or internal open: Grant whatever the client wants.
930 * 2) Exclusive (or batch) oplock around: If the requested access is a delete
931 * request, break if the oplock around is a batch oplock. If it's another
932 * requested access type, break.
934 * 3) Only level2 around: Grant level2 and do nothing else.
937 static bool delay_for_oplocks(struct share_mode_lock *lck,
938 files_struct *fsp,
939 uint64_t mid,
940 int pass_number,
941 int oplock_request)
943 int i;
944 struct share_mode_entry *exclusive = NULL;
945 bool valid_entry = false;
946 bool have_level2 = false;
947 bool have_a_none_oplock = false;
948 bool allow_level2 = (global_client_caps & CAP_LEVEL_II_OPLOCKS) &&
949 lp_level2_oplocks(SNUM(fsp->conn));
951 if (oplock_request & INTERNAL_OPEN_ONLY) {
952 fsp->oplock_type = NO_OPLOCK;
955 if ((oplock_request & INTERNAL_OPEN_ONLY) || is_stat_open(fsp->access_mask)) {
956 return false;
959 for (i=0; i<lck->num_share_modes; i++) {
961 if (!is_valid_share_mode_entry(&lck->share_modes[i])) {
962 continue;
965 /* At least one entry is not an invalid or deferred entry. */
966 valid_entry = true;
968 if (pass_number == 1) {
969 if (BATCH_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
970 SMB_ASSERT(exclusive == NULL);
971 exclusive = &lck->share_modes[i];
973 } else {
974 if (EXCLUSIVE_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
975 SMB_ASSERT(exclusive == NULL);
976 exclusive = &lck->share_modes[i];
980 if (LEVEL_II_OPLOCK_TYPE(lck->share_modes[i].op_type)) {
981 SMB_ASSERT(exclusive == NULL);
982 have_level2 = true;
985 if (lck->share_modes[i].op_type == NO_OPLOCK) {
986 have_a_none_oplock = true;
990 if (exclusive != NULL) { /* Found an exclusive oplock */
991 bool delay_it = is_delete_request(fsp) ?
992 BATCH_OPLOCK_TYPE(exclusive->op_type) : true;
993 SMB_ASSERT(!have_level2);
994 if (delay_it) {
995 send_break_message(fsp, exclusive, mid, oplock_request);
996 return true;
1001 * Match what was requested (fsp->oplock_type) with
1002 * what was found in the existing share modes.
1005 if (!valid_entry) {
1006 /* All entries are placeholders or deferred.
1007 * Directly grant whatever the client wants. */
1008 if (fsp->oplock_type == NO_OPLOCK) {
1009 /* Store a level2 oplock, but don't tell the client */
1010 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1012 } else if (have_a_none_oplock) {
1013 fsp->oplock_type = NO_OPLOCK;
1014 } else if (have_level2) {
1015 if (fsp->oplock_type == NO_OPLOCK ||
1016 fsp->oplock_type == FAKE_LEVEL_II_OPLOCK) {
1017 /* Store a level2 oplock, but don't tell the client */
1018 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1019 } else {
1020 fsp->oplock_type = LEVEL_II_OPLOCK;
1022 } else {
1023 /* This case can never happen. */
1024 SMB_ASSERT(1);
1028 * Don't grant level2 to clients that don't want them
1029 * or if we've turned them off.
1031 if (fsp->oplock_type == LEVEL_II_OPLOCK && !allow_level2) {
1032 fsp->oplock_type = FAKE_LEVEL_II_OPLOCK;
1035 DEBUG(10,("delay_for_oplocks: oplock type 0x%x on file %s\n",
1036 fsp->oplock_type, fsp_str_dbg(fsp)));
1038 /* No delay. */
1039 return false;
1042 bool request_timed_out(struct timeval request_time,
1043 struct timeval timeout)
1045 struct timeval now, end_time;
1046 GetTimeOfDay(&now);
1047 end_time = timeval_sum(&request_time, &timeout);
1048 return (timeval_compare(&end_time, &now) < 0);
1051 /****************************************************************************
1052 Handle the 1 second delay in returning a SHARING_VIOLATION error.
1053 ****************************************************************************/
1055 static void defer_open(struct share_mode_lock *lck,
1056 struct timeval request_time,
1057 struct timeval timeout,
1058 struct smb_request *req,
1059 struct deferred_open_record *state)
1061 int i;
1063 /* Paranoia check */
1065 for (i=0; i<lck->num_share_modes; i++) {
1066 struct share_mode_entry *e = &lck->share_modes[i];
1068 if (!is_deferred_open_entry(e)) {
1069 continue;
1072 if (procid_is_me(&e->pid) && (e->op_mid == req->mid)) {
1073 DEBUG(0, ("Trying to defer an already deferred "
1074 "request: mid=%llu, exiting\n",
1075 (unsigned long long)req->mid));
1076 exit_server("attempt to defer a deferred request");
1080 /* End paranoia check */
1082 DEBUG(10,("defer_open_sharing_error: time [%u.%06u] adding deferred "
1083 "open entry for mid %llu\n",
1084 (unsigned int)request_time.tv_sec,
1085 (unsigned int)request_time.tv_usec,
1086 (unsigned long long)req->mid));
1088 if (!push_deferred_open_message_smb(req, request_time, timeout,
1089 state->id, (char *)state, sizeof(*state))) {
1090 exit_server("push_deferred_open_message_smb failed");
1092 add_deferred_open(lck, req->mid, request_time, state->id);
1096 /****************************************************************************
1097 On overwrite open ensure that the attributes match.
1098 ****************************************************************************/
1100 bool open_match_attributes(connection_struct *conn,
1101 uint32 old_dos_attr,
1102 uint32 new_dos_attr,
1103 mode_t existing_unx_mode,
1104 mode_t new_unx_mode,
1105 mode_t *returned_unx_mode)
1107 uint32 noarch_old_dos_attr, noarch_new_dos_attr;
1109 noarch_old_dos_attr = (old_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
1110 noarch_new_dos_attr = (new_dos_attr & ~FILE_ATTRIBUTE_ARCHIVE);
1112 if((noarch_old_dos_attr == 0 && noarch_new_dos_attr != 0) ||
1113 (noarch_old_dos_attr != 0 && ((noarch_old_dos_attr & noarch_new_dos_attr) == noarch_old_dos_attr))) {
1114 *returned_unx_mode = new_unx_mode;
1115 } else {
1116 *returned_unx_mode = (mode_t)0;
1119 DEBUG(10,("open_match_attributes: old_dos_attr = 0x%x, "
1120 "existing_unx_mode = 0%o, new_dos_attr = 0x%x "
1121 "returned_unx_mode = 0%o\n",
1122 (unsigned int)old_dos_attr,
1123 (unsigned int)existing_unx_mode,
1124 (unsigned int)new_dos_attr,
1125 (unsigned int)*returned_unx_mode ));
1127 /* If we're mapping SYSTEM and HIDDEN ensure they match. */
1128 if (lp_map_system(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
1129 if ((old_dos_attr & FILE_ATTRIBUTE_SYSTEM) &&
1130 !(new_dos_attr & FILE_ATTRIBUTE_SYSTEM)) {
1131 return False;
1134 if (lp_map_hidden(SNUM(conn)) || lp_store_dos_attributes(SNUM(conn))) {
1135 if ((old_dos_attr & FILE_ATTRIBUTE_HIDDEN) &&
1136 !(new_dos_attr & FILE_ATTRIBUTE_HIDDEN)) {
1137 return False;
1140 return True;
1143 /****************************************************************************
1144 Special FCB or DOS processing in the case of a sharing violation.
1145 Try and find a duplicated file handle.
1146 ****************************************************************************/
1148 NTSTATUS fcb_or_dos_open(struct smb_request *req,
1149 connection_struct *conn,
1150 files_struct *fsp_to_dup_into,
1151 const struct smb_filename *smb_fname,
1152 struct file_id id,
1153 uint16 file_pid,
1154 uint16 vuid,
1155 uint32 access_mask,
1156 uint32 share_access,
1157 uint32 create_options)
1159 files_struct *fsp;
1161 DEBUG(5,("fcb_or_dos_open: attempting old open semantics for "
1162 "file %s.\n", smb_fname_str_dbg(smb_fname)));
1164 for(fsp = file_find_di_first(id); fsp;
1165 fsp = file_find_di_next(fsp)) {
1167 DEBUG(10,("fcb_or_dos_open: checking file %s, fd = %d, "
1168 "vuid = %u, file_pid = %u, private_options = 0x%x "
1169 "access_mask = 0x%x\n", fsp_str_dbg(fsp),
1170 fsp->fh->fd, (unsigned int)fsp->vuid,
1171 (unsigned int)fsp->file_pid,
1172 (unsigned int)fsp->fh->private_options,
1173 (unsigned int)fsp->access_mask ));
1175 if (fsp->fh->fd != -1 &&
1176 fsp->vuid == vuid &&
1177 fsp->file_pid == file_pid &&
1178 (fsp->fh->private_options & (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS |
1179 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) &&
1180 (fsp->access_mask & FILE_WRITE_DATA) &&
1181 strequal(fsp->fsp_name->base_name, smb_fname->base_name) &&
1182 strequal(fsp->fsp_name->stream_name,
1183 smb_fname->stream_name)) {
1184 DEBUG(10,("fcb_or_dos_open: file match\n"));
1185 break;
1189 if (!fsp) {
1190 return NT_STATUS_NOT_FOUND;
1193 /* quite an insane set of semantics ... */
1194 if (is_executable(smb_fname->base_name) &&
1195 (fsp->fh->private_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS)) {
1196 DEBUG(10,("fcb_or_dos_open: file fail due to is_executable.\n"));
1197 return NT_STATUS_INVALID_PARAMETER;
1200 /* We need to duplicate this fsp. */
1201 return dup_file_fsp(req, fsp, access_mask, share_access,
1202 create_options, fsp_to_dup_into);
1205 /****************************************************************************
1206 Open a file with a share mode - old openX method - map into NTCreate.
1207 ****************************************************************************/
1209 bool map_open_params_to_ntcreate(const struct smb_filename *smb_fname,
1210 int deny_mode, int open_func,
1211 uint32 *paccess_mask,
1212 uint32 *pshare_mode,
1213 uint32 *pcreate_disposition,
1214 uint32 *pcreate_options,
1215 uint32_t *pprivate_flags)
1217 uint32 access_mask;
1218 uint32 share_mode;
1219 uint32 create_disposition;
1220 uint32 create_options = FILE_NON_DIRECTORY_FILE;
1221 uint32_t private_flags = 0;
1223 DEBUG(10,("map_open_params_to_ntcreate: fname = %s, deny_mode = 0x%x, "
1224 "open_func = 0x%x\n",
1225 smb_fname_str_dbg(smb_fname), (unsigned int)deny_mode,
1226 (unsigned int)open_func ));
1228 /* Create the NT compatible access_mask. */
1229 switch (GET_OPENX_MODE(deny_mode)) {
1230 case DOS_OPEN_EXEC: /* Implies read-only - used to be FILE_READ_DATA */
1231 case DOS_OPEN_RDONLY:
1232 access_mask = FILE_GENERIC_READ;
1233 break;
1234 case DOS_OPEN_WRONLY:
1235 access_mask = FILE_GENERIC_WRITE;
1236 break;
1237 case DOS_OPEN_RDWR:
1238 case DOS_OPEN_FCB:
1239 access_mask = FILE_GENERIC_READ|FILE_GENERIC_WRITE;
1240 break;
1241 default:
1242 DEBUG(10,("map_open_params_to_ntcreate: bad open mode = 0x%x\n",
1243 (unsigned int)GET_OPENX_MODE(deny_mode)));
1244 return False;
1247 /* Create the NT compatible create_disposition. */
1248 switch (open_func) {
1249 case OPENX_FILE_EXISTS_FAIL|OPENX_FILE_CREATE_IF_NOT_EXIST:
1250 create_disposition = FILE_CREATE;
1251 break;
1253 case OPENX_FILE_EXISTS_OPEN:
1254 create_disposition = FILE_OPEN;
1255 break;
1257 case OPENX_FILE_EXISTS_OPEN|OPENX_FILE_CREATE_IF_NOT_EXIST:
1258 create_disposition = FILE_OPEN_IF;
1259 break;
1261 case OPENX_FILE_EXISTS_TRUNCATE:
1262 create_disposition = FILE_OVERWRITE;
1263 break;
1265 case OPENX_FILE_EXISTS_TRUNCATE|OPENX_FILE_CREATE_IF_NOT_EXIST:
1266 create_disposition = FILE_OVERWRITE_IF;
1267 break;
1269 default:
1270 /* From samba4 - to be confirmed. */
1271 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_EXEC) {
1272 create_disposition = FILE_CREATE;
1273 break;
1275 DEBUG(10,("map_open_params_to_ntcreate: bad "
1276 "open_func 0x%x\n", (unsigned int)open_func));
1277 return False;
1280 /* Create the NT compatible share modes. */
1281 switch (GET_DENY_MODE(deny_mode)) {
1282 case DENY_ALL:
1283 share_mode = FILE_SHARE_NONE;
1284 break;
1286 case DENY_WRITE:
1287 share_mode = FILE_SHARE_READ;
1288 break;
1290 case DENY_READ:
1291 share_mode = FILE_SHARE_WRITE;
1292 break;
1294 case DENY_NONE:
1295 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1296 break;
1298 case DENY_DOS:
1299 private_flags |= NTCREATEX_OPTIONS_PRIVATE_DENY_DOS;
1300 if (is_executable(smb_fname->base_name)) {
1301 share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
1302 } else {
1303 if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_RDONLY) {
1304 share_mode = FILE_SHARE_READ;
1305 } else {
1306 share_mode = FILE_SHARE_NONE;
1309 break;
1311 case DENY_FCB:
1312 private_flags |= NTCREATEX_OPTIONS_PRIVATE_DENY_FCB;
1313 share_mode = FILE_SHARE_NONE;
1314 break;
1316 default:
1317 DEBUG(10,("map_open_params_to_ntcreate: bad deny_mode 0x%x\n",
1318 (unsigned int)GET_DENY_MODE(deny_mode) ));
1319 return False;
1322 DEBUG(10,("map_open_params_to_ntcreate: file %s, access_mask = 0x%x, "
1323 "share_mode = 0x%x, create_disposition = 0x%x, "
1324 "create_options = 0x%x private_flags = 0x%x\n",
1325 smb_fname_str_dbg(smb_fname),
1326 (unsigned int)access_mask,
1327 (unsigned int)share_mode,
1328 (unsigned int)create_disposition,
1329 (unsigned int)create_options,
1330 (unsigned int)private_flags));
1332 if (paccess_mask) {
1333 *paccess_mask = access_mask;
1335 if (pshare_mode) {
1336 *pshare_mode = share_mode;
1338 if (pcreate_disposition) {
1339 *pcreate_disposition = create_disposition;
1341 if (pcreate_options) {
1342 *pcreate_options = create_options;
1344 if (pprivate_flags) {
1345 *pprivate_flags = private_flags;
1348 return True;
1352 static void schedule_defer_open(struct share_mode_lock *lck,
1353 struct timeval request_time,
1354 struct smb_request *req)
1356 struct deferred_open_record state;
1358 /* This is a relative time, added to the absolute
1359 request_time value to get the absolute timeout time.
1360 Note that if this is the second or greater time we enter
1361 this codepath for this particular request mid then
1362 request_time is left as the absolute time of the *first*
1363 time this request mid was processed. This is what allows
1364 the request to eventually time out. */
1366 struct timeval timeout;
1368 /* Normally the smbd we asked should respond within
1369 * OPLOCK_BREAK_TIMEOUT seconds regardless of whether
1370 * the client did, give twice the timeout as a safety
1371 * measure here in case the other smbd is stuck
1372 * somewhere else. */
1374 timeout = timeval_set(OPLOCK_BREAK_TIMEOUT*2, 0);
1376 /* Nothing actually uses state.delayed_for_oplocks
1377 but it's handy to differentiate in debug messages
1378 between a 30 second delay due to oplock break, and
1379 a 1 second delay for share mode conflicts. */
1381 state.delayed_for_oplocks = True;
1382 state.id = lck->id;
1384 if (!request_timed_out(request_time, timeout)) {
1385 defer_open(lck, request_time, timeout, req, &state);
1389 /****************************************************************************
1390 Work out what access_mask to use from what the client sent us.
1391 ****************************************************************************/
1393 static NTSTATUS calculate_access_mask(connection_struct *conn,
1394 const struct smb_filename *smb_fname,
1395 bool file_existed,
1396 uint32_t access_mask,
1397 uint32_t *access_mask_out)
1399 NTSTATUS status;
1402 * Convert GENERIC bits to specific bits.
1405 se_map_generic(&access_mask, &file_generic_mapping);
1407 /* Calculate MAXIMUM_ALLOWED_ACCESS if requested. */
1408 if (access_mask & MAXIMUM_ALLOWED_ACCESS) {
1409 if (file_existed) {
1411 struct security_descriptor *sd;
1412 uint32_t access_granted = 0;
1414 status = SMB_VFS_GET_NT_ACL(conn, smb_fname->base_name,
1415 (OWNER_SECURITY_INFORMATION |
1416 GROUP_SECURITY_INFORMATION |
1417 DACL_SECURITY_INFORMATION),&sd);
1419 if (!NT_STATUS_IS_OK(status)) {
1420 DEBUG(10, ("calculate_access_mask: Could not get acl "
1421 "on file %s: %s\n",
1422 smb_fname_str_dbg(smb_fname),
1423 nt_errstr(status)));
1424 return NT_STATUS_ACCESS_DENIED;
1427 status = smb1_file_se_access_check(conn,
1429 get_current_nttok(conn),
1430 access_mask,
1431 &access_granted);
1433 TALLOC_FREE(sd);
1435 if (!NT_STATUS_IS_OK(status)) {
1436 DEBUG(10, ("calculate_access_mask: Access denied on "
1437 "file %s: when calculating maximum access\n",
1438 smb_fname_str_dbg(smb_fname)));
1439 return NT_STATUS_ACCESS_DENIED;
1442 access_mask = access_granted;
1443 } else {
1444 access_mask = FILE_GENERIC_ALL;
1448 *access_mask_out = access_mask;
1449 return NT_STATUS_OK;
1452 /****************************************************************************
1453 Remove the deferred open entry under lock.
1454 ****************************************************************************/
1456 void remove_deferred_open_entry(struct file_id id, uint64_t mid)
1458 struct share_mode_lock *lck = get_share_mode_lock(talloc_tos(), id,
1459 NULL, NULL, NULL);
1460 if (lck == NULL) {
1461 DEBUG(0, ("could not get share mode lock\n"));
1462 } else {
1463 del_deferred_open_entry(lck, mid);
1464 TALLOC_FREE(lck);
1468 /****************************************************************************
1469 Open a file with a share mode. Passed in an already created files_struct *.
1470 ****************************************************************************/
1472 static NTSTATUS open_file_ntcreate(connection_struct *conn,
1473 struct smb_request *req,
1474 uint32 access_mask, /* access bits (FILE_READ_DATA etc.) */
1475 uint32 share_access, /* share constants (FILE_SHARE_READ etc) */
1476 uint32 create_disposition, /* FILE_OPEN_IF etc. */
1477 uint32 create_options, /* options such as delete on close. */
1478 uint32 new_dos_attributes, /* attributes used for new file. */
1479 int oplock_request, /* internal Samba oplock codes. */
1480 /* Information (FILE_EXISTS etc.) */
1481 uint32_t private_flags, /* Samba specific flags. */
1482 int *pinfo,
1483 files_struct *fsp)
1485 struct smb_filename *smb_fname = fsp->fsp_name;
1486 int flags=0;
1487 int flags2=0;
1488 bool file_existed = VALID_STAT(smb_fname->st);
1489 bool def_acl = False;
1490 bool posix_open = False;
1491 bool new_file_created = False;
1492 bool clear_ads = false;
1493 struct file_id id;
1494 NTSTATUS fsp_open = NT_STATUS_ACCESS_DENIED;
1495 mode_t new_unx_mode = (mode_t)0;
1496 mode_t unx_mode = (mode_t)0;
1497 int info;
1498 uint32 existing_dos_attributes = 0;
1499 struct timeval request_time = timeval_zero();
1500 struct share_mode_lock *lck = NULL;
1501 uint32 open_access_mask = access_mask;
1502 NTSTATUS status;
1503 char *parent_dir;
1505 ZERO_STRUCT(id);
1507 if (conn->printer) {
1509 * Printers are handled completely differently.
1510 * Most of the passed parameters are ignored.
1513 if (pinfo) {
1514 *pinfo = FILE_WAS_CREATED;
1517 DEBUG(10, ("open_file_ntcreate: printer open fname=%s\n",
1518 smb_fname_str_dbg(smb_fname)));
1520 if (!req) {
1521 DEBUG(0,("open_file_ntcreate: printer open without "
1522 "an SMB request!\n"));
1523 return NT_STATUS_INTERNAL_ERROR;
1526 return print_fsp_open(req, conn, smb_fname->base_name,
1527 req->vuid, fsp);
1530 if (!parent_dirname(talloc_tos(), smb_fname->base_name, &parent_dir,
1531 NULL)) {
1532 return NT_STATUS_NO_MEMORY;
1535 if (new_dos_attributes & FILE_FLAG_POSIX_SEMANTICS) {
1536 posix_open = True;
1537 unx_mode = (mode_t)(new_dos_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
1538 new_dos_attributes = 0;
1539 } else {
1540 /* We add aARCH to this as this mode is only used if the file is
1541 * created new. */
1542 unx_mode = unix_mode(conn, new_dos_attributes | aARCH,
1543 smb_fname, parent_dir);
1546 DEBUG(10, ("open_file_ntcreate: fname=%s, dos_attrs=0x%x "
1547 "access_mask=0x%x share_access=0x%x "
1548 "create_disposition = 0x%x create_options=0x%x "
1549 "unix mode=0%o oplock_request=%d private_flags = 0x%x\n",
1550 smb_fname_str_dbg(smb_fname), new_dos_attributes,
1551 access_mask, share_access, create_disposition,
1552 create_options, (unsigned int)unx_mode, oplock_request,
1553 (unsigned int)private_flags));
1555 if ((req == NULL) && ((oplock_request & INTERNAL_OPEN_ONLY) == 0)) {
1556 DEBUG(0, ("No smb request but not an internal only open!\n"));
1557 return NT_STATUS_INTERNAL_ERROR;
1561 * Only non-internal opens can be deferred at all
1564 if (req) {
1565 void *ptr;
1566 if (get_deferred_open_message_state(req,
1567 &request_time,
1568 &ptr)) {
1570 struct deferred_open_record *state = (struct deferred_open_record *)ptr;
1571 /* Remember the absolute time of the original
1572 request with this mid. We'll use it later to
1573 see if this has timed out. */
1575 /* Remove the deferred open entry under lock. */
1576 remove_deferred_open_entry(state->id, req->mid);
1578 /* Ensure we don't reprocess this message. */
1579 remove_deferred_open_message_smb(req->mid);
1583 status = check_name(conn, smb_fname->base_name);
1584 if (!NT_STATUS_IS_OK(status)) {
1585 return status;
1588 if (!posix_open) {
1589 new_dos_attributes &= SAMBA_ATTRIBUTES_MASK;
1590 if (file_existed) {
1591 existing_dos_attributes = dos_mode(conn, smb_fname);
1595 /* ignore any oplock requests if oplocks are disabled */
1596 if (!lp_oplocks(SNUM(conn)) ||
1597 IS_VETO_OPLOCK_PATH(conn, smb_fname->base_name)) {
1598 /* Mask off everything except the private Samba bits. */
1599 oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
1602 /* this is for OS/2 long file names - say we don't support them */
1603 if (!lp_posix_pathnames() && strstr(smb_fname->base_name,".+,;=[].")) {
1604 /* OS/2 Workplace shell fix may be main code stream in a later
1605 * release. */
1606 DEBUG(5,("open_file_ntcreate: OS/2 long filenames are not "
1607 "supported.\n"));
1608 if (use_nt_status()) {
1609 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1611 return NT_STATUS_DOS(ERRDOS, ERRcannotopen);
1614 switch( create_disposition ) {
1616 * Currently we're using FILE_SUPERSEDE as the same as
1617 * FILE_OVERWRITE_IF but they really are
1618 * different. FILE_SUPERSEDE deletes an existing file
1619 * (requiring delete access) then recreates it.
1621 case FILE_SUPERSEDE:
1622 /* If file exists replace/overwrite. If file doesn't
1623 * exist create. */
1624 flags2 |= (O_CREAT | O_TRUNC);
1625 clear_ads = true;
1626 break;
1628 case FILE_OVERWRITE_IF:
1629 /* If file exists replace/overwrite. If file doesn't
1630 * exist create. */
1631 flags2 |= (O_CREAT | O_TRUNC);
1632 clear_ads = true;
1633 break;
1635 case FILE_OPEN:
1636 /* If file exists open. If file doesn't exist error. */
1637 if (!file_existed) {
1638 DEBUG(5,("open_file_ntcreate: FILE_OPEN "
1639 "requested for file %s and file "
1640 "doesn't exist.\n",
1641 smb_fname_str_dbg(smb_fname)));
1642 errno = ENOENT;
1643 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1645 break;
1647 case FILE_OVERWRITE:
1648 /* If file exists overwrite. If file doesn't exist
1649 * error. */
1650 if (!file_existed) {
1651 DEBUG(5,("open_file_ntcreate: FILE_OVERWRITE "
1652 "requested for file %s and file "
1653 "doesn't exist.\n",
1654 smb_fname_str_dbg(smb_fname) ));
1655 errno = ENOENT;
1656 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1658 flags2 |= O_TRUNC;
1659 clear_ads = true;
1660 break;
1662 case FILE_CREATE:
1663 /* If file exists error. If file doesn't exist
1664 * create. */
1665 if (file_existed) {
1666 DEBUG(5,("open_file_ntcreate: FILE_CREATE "
1667 "requested for file %s and file "
1668 "already exists.\n",
1669 smb_fname_str_dbg(smb_fname)));
1670 if (S_ISDIR(smb_fname->st.st_ex_mode)) {
1671 errno = EISDIR;
1672 } else {
1673 errno = EEXIST;
1675 return map_nt_error_from_unix(errno);
1677 flags2 |= (O_CREAT|O_EXCL);
1678 break;
1680 case FILE_OPEN_IF:
1681 /* If file exists open. If file doesn't exist
1682 * create. */
1683 flags2 |= O_CREAT;
1684 break;
1686 default:
1687 return NT_STATUS_INVALID_PARAMETER;
1690 /* We only care about matching attributes on file exists and
1691 * overwrite. */
1693 if (!posix_open && file_existed && ((create_disposition == FILE_OVERWRITE) ||
1694 (create_disposition == FILE_OVERWRITE_IF))) {
1695 if (!open_match_attributes(conn, existing_dos_attributes,
1696 new_dos_attributes,
1697 smb_fname->st.st_ex_mode,
1698 unx_mode, &new_unx_mode)) {
1699 DEBUG(5,("open_file_ntcreate: attributes missmatch "
1700 "for file %s (%x %x) (0%o, 0%o)\n",
1701 smb_fname_str_dbg(smb_fname),
1702 existing_dos_attributes,
1703 new_dos_attributes,
1704 (unsigned int)smb_fname->st.st_ex_mode,
1705 (unsigned int)unx_mode ));
1706 errno = EACCES;
1707 return NT_STATUS_ACCESS_DENIED;
1711 status = calculate_access_mask(conn, smb_fname, file_existed,
1712 access_mask,
1713 &access_mask);
1714 if (!NT_STATUS_IS_OK(status)) {
1715 DEBUG(10, ("open_file_ntcreate: calculate_access_mask "
1716 "on file %s returned %s\n",
1717 smb_fname_str_dbg(smb_fname), nt_errstr(status)));
1718 return status;
1721 open_access_mask = access_mask;
1723 if ((flags2 & O_TRUNC) || (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
1724 open_access_mask |= FILE_WRITE_DATA; /* This will cause oplock breaks. */
1727 DEBUG(10, ("open_file_ntcreate: fname=%s, after mapping "
1728 "access_mask=0x%x\n", smb_fname_str_dbg(smb_fname),
1729 access_mask));
1732 * Note that we ignore the append flag as append does not
1733 * mean the same thing under DOS and Unix.
1736 if ((access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ||
1737 (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
1738 /* DENY_DOS opens are always underlying read-write on the
1739 file handle, no matter what the requested access mask
1740 says. */
1741 if ((private_flags & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS) ||
1742 access_mask & (FILE_READ_ATTRIBUTES|FILE_READ_DATA|FILE_READ_EA|FILE_EXECUTE)) {
1743 flags = O_RDWR;
1744 } else {
1745 flags = O_WRONLY;
1747 } else {
1748 flags = O_RDONLY;
1752 * Currently we only look at FILE_WRITE_THROUGH for create options.
1755 #if defined(O_SYNC)
1756 if ((create_options & FILE_WRITE_THROUGH) && lp_strict_sync(SNUM(conn))) {
1757 flags2 |= O_SYNC;
1759 #endif /* O_SYNC */
1761 if (posix_open && (access_mask & FILE_APPEND_DATA)) {
1762 flags2 |= O_APPEND;
1765 if (!posix_open && !CAN_WRITE(conn)) {
1767 * We should really return a permission denied error if either
1768 * O_CREAT or O_TRUNC are set, but for compatibility with
1769 * older versions of Samba we just AND them out.
1771 flags2 &= ~(O_CREAT|O_TRUNC);
1775 * Ensure we can't write on a read-only share or file.
1778 if (flags != O_RDONLY && file_existed &&
1779 (!CAN_WRITE(conn) || IS_DOS_READONLY(existing_dos_attributes))) {
1780 DEBUG(5,("open_file_ntcreate: write access requested for "
1781 "file %s on read only %s\n",
1782 smb_fname_str_dbg(smb_fname),
1783 !CAN_WRITE(conn) ? "share" : "file" ));
1784 errno = EACCES;
1785 return NT_STATUS_ACCESS_DENIED;
1788 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
1789 fsp->share_access = share_access;
1790 fsp->fh->private_options = private_flags;
1791 fsp->access_mask = open_access_mask; /* We change this to the
1792 * requested access_mask after
1793 * the open is done. */
1794 fsp->posix_open = posix_open;
1796 /* Ensure no SAMBA_PRIVATE bits can be set. */
1797 fsp->oplock_type = (oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK);
1799 if (timeval_is_zero(&request_time)) {
1800 request_time = fsp->open_time;
1803 if (file_existed) {
1804 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
1805 id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
1807 lck = get_share_mode_lock(talloc_tos(), id,
1808 conn->connectpath,
1809 smb_fname, &old_write_time);
1811 if (lck == NULL) {
1812 DEBUG(0, ("Could not get share mode lock\n"));
1813 return NT_STATUS_SHARING_VIOLATION;
1816 /* First pass - send break only on batch oplocks. */
1817 if ((req != NULL)
1818 && delay_for_oplocks(lck, fsp, req->mid, 1,
1819 oplock_request)) {
1820 schedule_defer_open(lck, request_time, req);
1821 TALLOC_FREE(lck);
1822 return NT_STATUS_SHARING_VIOLATION;
1825 /* Use the client requested access mask here, not the one we
1826 * open with. */
1827 status = open_mode_check(conn, lck, access_mask, share_access,
1828 create_options, &file_existed);
1830 if (NT_STATUS_IS_OK(status)) {
1831 /* We might be going to allow this open. Check oplock
1832 * status again. */
1833 /* Second pass - send break for both batch or
1834 * exclusive oplocks. */
1835 if ((req != NULL)
1836 && delay_for_oplocks(lck, fsp, req->mid, 2,
1837 oplock_request)) {
1838 schedule_defer_open(lck, request_time, req);
1839 TALLOC_FREE(lck);
1840 return NT_STATUS_SHARING_VIOLATION;
1844 if (NT_STATUS_EQUAL(status, NT_STATUS_DELETE_PENDING)) {
1845 /* DELETE_PENDING is not deferred for a second */
1846 TALLOC_FREE(lck);
1847 return status;
1850 if (!NT_STATUS_IS_OK(status)) {
1851 uint32 can_access_mask;
1852 bool can_access = True;
1854 SMB_ASSERT(NT_STATUS_EQUAL(status, NT_STATUS_SHARING_VIOLATION));
1856 /* Check if this can be done with the deny_dos and fcb
1857 * calls. */
1858 if (private_flags &
1859 (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
1860 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
1861 if (req == NULL) {
1862 DEBUG(0, ("DOS open without an SMB "
1863 "request!\n"));
1864 TALLOC_FREE(lck);
1865 return NT_STATUS_INTERNAL_ERROR;
1868 /* Use the client requested access mask here,
1869 * not the one we open with. */
1870 status = fcb_or_dos_open(req,
1871 conn,
1872 fsp,
1873 smb_fname,
1875 req->smbpid,
1876 req->vuid,
1877 access_mask,
1878 share_access,
1879 create_options);
1881 if (NT_STATUS_IS_OK(status)) {
1882 TALLOC_FREE(lck);
1883 if (pinfo) {
1884 *pinfo = FILE_WAS_OPENED;
1886 return NT_STATUS_OK;
1891 * This next line is a subtlety we need for
1892 * MS-Access. If a file open will fail due to share
1893 * permissions and also for security (access) reasons,
1894 * we need to return the access failed error, not the
1895 * share error. We can't open the file due to kernel
1896 * oplock deadlock (it's possible we failed above on
1897 * the open_mode_check()) so use a userspace check.
1900 if (flags & O_RDWR) {
1901 can_access_mask = FILE_READ_DATA|FILE_WRITE_DATA;
1902 } else if (flags & O_WRONLY) {
1903 can_access_mask = FILE_WRITE_DATA;
1904 } else {
1905 can_access_mask = FILE_READ_DATA;
1908 if (((can_access_mask & FILE_WRITE_DATA) &&
1909 !CAN_WRITE(conn)) ||
1910 !can_access_file_data(conn, smb_fname,
1911 can_access_mask)) {
1912 can_access = False;
1916 * If we're returning a share violation, ensure we
1917 * cope with the braindead 1 second delay.
1920 if (!(oplock_request & INTERNAL_OPEN_ONLY) &&
1921 lp_defer_sharing_violations()) {
1922 struct timeval timeout;
1923 struct deferred_open_record state;
1924 int timeout_usecs;
1926 /* this is a hack to speed up torture tests
1927 in 'make test' */
1928 timeout_usecs = lp_parm_int(SNUM(conn),
1929 "smbd","sharedelay",
1930 SHARING_VIOLATION_USEC_WAIT);
1932 /* This is a relative time, added to the absolute
1933 request_time value to get the absolute timeout time.
1934 Note that if this is the second or greater time we enter
1935 this codepath for this particular request mid then
1936 request_time is left as the absolute time of the *first*
1937 time this request mid was processed. This is what allows
1938 the request to eventually time out. */
1940 timeout = timeval_set(0, timeout_usecs);
1942 /* Nothing actually uses state.delayed_for_oplocks
1943 but it's handy to differentiate in debug messages
1944 between a 30 second delay due to oplock break, and
1945 a 1 second delay for share mode conflicts. */
1947 state.delayed_for_oplocks = False;
1948 state.id = id;
1950 if ((req != NULL)
1951 && !request_timed_out(request_time,
1952 timeout)) {
1953 defer_open(lck, request_time, timeout,
1954 req, &state);
1958 TALLOC_FREE(lck);
1959 if (can_access) {
1961 * We have detected a sharing violation here
1962 * so return the correct error code
1964 status = NT_STATUS_SHARING_VIOLATION;
1965 } else {
1966 status = NT_STATUS_ACCESS_DENIED;
1968 return status;
1972 * We exit this block with the share entry *locked*.....
1976 SMB_ASSERT(!file_existed || (lck != NULL));
1979 * Ensure we pay attention to default ACLs on directories if required.
1982 if ((flags2 & O_CREAT) && lp_inherit_acls(SNUM(conn)) &&
1983 (def_acl = directory_has_default_acl(conn, parent_dir))) {
1984 unx_mode = 0777;
1987 DEBUG(4,("calling open_file with flags=0x%X flags2=0x%X mode=0%o, "
1988 "access_mask = 0x%x, open_access_mask = 0x%x\n",
1989 (unsigned int)flags, (unsigned int)flags2,
1990 (unsigned int)unx_mode, (unsigned int)access_mask,
1991 (unsigned int)open_access_mask));
1994 * open_file strips any O_TRUNC flags itself.
1997 fsp_open = open_file(fsp, conn, req, parent_dir,
1998 flags|flags2, unx_mode, access_mask,
1999 open_access_mask);
2001 if (!NT_STATUS_IS_OK(fsp_open)) {
2002 if (lck != NULL) {
2003 TALLOC_FREE(lck);
2005 return fsp_open;
2008 if (!file_existed) {
2009 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
2011 * Deal with the race condition where two smbd's detect the
2012 * file doesn't exist and do the create at the same time. One
2013 * of them will win and set a share mode, the other (ie. this
2014 * one) should check if the requested share mode for this
2015 * create is allowed.
2019 * Now the file exists and fsp is successfully opened,
2020 * fsp->dev and fsp->inode are valid and should replace the
2021 * dev=0,inode=0 from a non existent file. Spotted by
2022 * Nadav Danieli <nadavd@exanet.com>. JRA.
2025 id = fsp->file_id;
2027 lck = get_share_mode_lock(talloc_tos(), id,
2028 conn->connectpath,
2029 smb_fname, &old_write_time);
2031 if (lck == NULL) {
2032 DEBUG(0, ("open_file_ntcreate: Could not get share "
2033 "mode lock for %s\n",
2034 smb_fname_str_dbg(smb_fname)));
2035 fd_close(fsp);
2036 return NT_STATUS_SHARING_VIOLATION;
2039 /* First pass - send break only on batch oplocks. */
2040 if ((req != NULL)
2041 && delay_for_oplocks(lck, fsp, req->mid, 1,
2042 oplock_request)) {
2043 schedule_defer_open(lck, request_time, req);
2044 TALLOC_FREE(lck);
2045 fd_close(fsp);
2046 return NT_STATUS_SHARING_VIOLATION;
2049 status = open_mode_check(conn, lck, access_mask, share_access,
2050 create_options, &file_existed);
2052 if (NT_STATUS_IS_OK(status)) {
2053 /* We might be going to allow this open. Check oplock
2054 * status again. */
2055 /* Second pass - send break for both batch or
2056 * exclusive oplocks. */
2057 if ((req != NULL)
2058 && delay_for_oplocks(lck, fsp, req->mid, 2,
2059 oplock_request)) {
2060 schedule_defer_open(lck, request_time, req);
2061 TALLOC_FREE(lck);
2062 fd_close(fsp);
2063 return NT_STATUS_SHARING_VIOLATION;
2067 if (!NT_STATUS_IS_OK(status)) {
2068 struct deferred_open_record state;
2070 fd_close(fsp);
2072 state.delayed_for_oplocks = False;
2073 state.id = id;
2075 /* Do it all over again immediately. In the second
2076 * round we will find that the file existed and handle
2077 * the DELETE_PENDING and FCB cases correctly. No need
2078 * to duplicate the code here. Essentially this is a
2079 * "goto top of this function", but don't tell
2080 * anybody... */
2082 if (req != NULL) {
2083 defer_open(lck, request_time, timeval_zero(),
2084 req, &state);
2086 TALLOC_FREE(lck);
2087 return status;
2091 * We exit this block with the share entry *locked*.....
2096 SMB_ASSERT(lck != NULL);
2098 /* Delete streams if create_disposition requires it */
2099 if (file_existed && clear_ads &&
2100 !is_ntfs_stream_smb_fname(smb_fname)) {
2101 status = delete_all_streams(conn, smb_fname->base_name);
2102 if (!NT_STATUS_IS_OK(status)) {
2103 TALLOC_FREE(lck);
2104 fd_close(fsp);
2105 return status;
2109 /* note that we ignore failure for the following. It is
2110 basically a hack for NFS, and NFS will never set one of
2111 these only read them. Nobody but Samba can ever set a deny
2112 mode and we have already checked our more authoritative
2113 locking database for permission to set this deny mode. If
2114 the kernel refuses the operations then the kernel is wrong.
2115 note that GPFS supports it as well - jmcd */
2117 if (fsp->fh->fd != -1) {
2118 int ret_flock;
2119 ret_flock = SMB_VFS_KERNEL_FLOCK(fsp, share_access, access_mask);
2120 if(ret_flock == -1 ){
2122 TALLOC_FREE(lck);
2123 fd_close(fsp);
2125 return NT_STATUS_SHARING_VIOLATION;
2130 * At this point onwards, we can guarentee that the share entry
2131 * is locked, whether we created the file or not, and that the
2132 * deny mode is compatible with all current opens.
2136 * If requested, truncate the file.
2139 if (flags2&O_TRUNC) {
2141 * We are modifing the file after open - update the stat
2142 * struct..
2144 if ((SMB_VFS_FTRUNCATE(fsp, 0) == -1) ||
2145 (SMB_VFS_FSTAT(fsp, &smb_fname->st)==-1)) {
2146 status = map_nt_error_from_unix(errno);
2147 TALLOC_FREE(lck);
2148 fd_close(fsp);
2149 return status;
2154 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
2156 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
2158 if (file_existed) {
2159 /* stat opens on existing files don't get oplocks. */
2160 if (is_stat_open(open_access_mask)) {
2161 fsp->oplock_type = NO_OPLOCK;
2164 if (!(flags2 & O_TRUNC)) {
2165 info = FILE_WAS_OPENED;
2166 } else {
2167 info = FILE_WAS_OVERWRITTEN;
2169 } else {
2170 info = FILE_WAS_CREATED;
2173 if (pinfo) {
2174 *pinfo = info;
2178 * Setup the oplock info in both the shared memory and
2179 * file structs.
2182 if (!set_file_oplock(fsp, fsp->oplock_type)) {
2183 /* Could not get the kernel oplock */
2184 fsp->oplock_type = NO_OPLOCK;
2187 if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED || info == FILE_WAS_SUPERSEDED) {
2188 new_file_created = True;
2191 set_share_mode(lck, fsp, get_current_uid(conn), 0,
2192 fsp->oplock_type);
2194 /* Handle strange delete on close create semantics. */
2195 if (create_options & FILE_DELETE_ON_CLOSE) {
2197 status = can_set_delete_on_close(fsp, new_dos_attributes);
2199 if (!NT_STATUS_IS_OK(status)) {
2200 /* Remember to delete the mode we just added. */
2201 del_share_mode(lck, fsp);
2202 TALLOC_FREE(lck);
2203 fd_close(fsp);
2204 return status;
2206 /* Note that here we set the *inital* delete on close flag,
2207 not the regular one. The magic gets handled in close. */
2208 fsp->initial_delete_on_close = True;
2211 if (new_file_created) {
2212 /* Files should be initially set as archive */
2213 if (lp_map_archive(SNUM(conn)) ||
2214 lp_store_dos_attributes(SNUM(conn))) {
2215 if (!posix_open) {
2216 if (file_set_dosmode(conn, smb_fname,
2217 new_dos_attributes | aARCH,
2218 parent_dir, true) == 0) {
2219 unx_mode = smb_fname->st.st_ex_mode;
2226 * Take care of inherited ACLs on created files - if default ACL not
2227 * selected.
2230 if (!posix_open && !file_existed && !def_acl) {
2232 int saved_errno = errno; /* We might get ENOSYS in the next
2233 * call.. */
2235 if (SMB_VFS_FCHMOD_ACL(fsp, unx_mode) == -1 &&
2236 errno == ENOSYS) {
2237 errno = saved_errno; /* Ignore ENOSYS */
2240 } else if (new_unx_mode) {
2242 int ret = -1;
2244 /* Attributes need changing. File already existed. */
2247 int saved_errno = errno; /* We might get ENOSYS in the
2248 * next call.. */
2249 ret = SMB_VFS_FCHMOD_ACL(fsp, new_unx_mode);
2251 if (ret == -1 && errno == ENOSYS) {
2252 errno = saved_errno; /* Ignore ENOSYS */
2253 } else {
2254 DEBUG(5, ("open_file_ntcreate: reset "
2255 "attributes of file %s to 0%o\n",
2256 smb_fname_str_dbg(smb_fname),
2257 (unsigned int)new_unx_mode));
2258 ret = 0; /* Don't do the fchmod below. */
2262 if ((ret == -1) &&
2263 (SMB_VFS_FCHMOD(fsp, new_unx_mode) == -1))
2264 DEBUG(5, ("open_file_ntcreate: failed to reset "
2265 "attributes of file %s to 0%o\n",
2266 smb_fname_str_dbg(smb_fname),
2267 (unsigned int)new_unx_mode));
2270 /* If this is a successful open, we must remove any deferred open
2271 * records. */
2272 if (req != NULL) {
2273 del_deferred_open_entry(lck, req->mid);
2275 TALLOC_FREE(lck);
2277 return NT_STATUS_OK;
2281 /****************************************************************************
2282 Open a file for for write to ensure that we can fchmod it.
2283 ****************************************************************************/
2285 NTSTATUS open_file_fchmod(struct smb_request *req, connection_struct *conn,
2286 struct smb_filename *smb_fname,
2287 files_struct **result)
2289 files_struct *fsp = NULL;
2290 NTSTATUS status;
2292 if (!VALID_STAT(smb_fname->st)) {
2293 return NT_STATUS_INVALID_PARAMETER;
2296 status = file_new(req, conn, &fsp);
2297 if(!NT_STATUS_IS_OK(status)) {
2298 return status;
2301 status = SMB_VFS_CREATE_FILE(
2302 conn, /* conn */
2303 NULL, /* req */
2304 0, /* root_dir_fid */
2305 smb_fname, /* fname */
2306 FILE_WRITE_DATA, /* access_mask */
2307 (FILE_SHARE_READ | FILE_SHARE_WRITE | /* share_access */
2308 FILE_SHARE_DELETE),
2309 FILE_OPEN, /* create_disposition*/
2310 0, /* create_options */
2311 0, /* file_attributes */
2312 0, /* oplock_request */
2313 0, /* allocation_size */
2314 0, /* private_flags */
2315 NULL, /* sd */
2316 NULL, /* ea_list */
2317 &fsp, /* result */
2318 NULL); /* pinfo */
2321 * This is not a user visible file open.
2322 * Don't set a share mode.
2325 if (!NT_STATUS_IS_OK(status)) {
2326 file_free(req, fsp);
2327 return status;
2330 *result = fsp;
2331 return NT_STATUS_OK;
2334 /****************************************************************************
2335 Close the fchmod file fd - ensure no locks are lost.
2336 ****************************************************************************/
2338 NTSTATUS close_file_fchmod(struct smb_request *req, files_struct *fsp)
2340 NTSTATUS status = fd_close(fsp);
2341 file_free(req, fsp);
2342 return status;
2345 static NTSTATUS mkdir_internal(connection_struct *conn,
2346 struct smb_filename *smb_dname,
2347 uint32 file_attributes)
2349 mode_t mode;
2350 char *parent_dir;
2351 NTSTATUS status;
2352 bool posix_open = false;
2354 if(!CAN_WRITE(conn)) {
2355 DEBUG(5,("mkdir_internal: failing create on read-only share "
2356 "%s\n", lp_servicename(SNUM(conn))));
2357 return NT_STATUS_ACCESS_DENIED;
2360 status = check_name(conn, smb_dname->base_name);
2361 if (!NT_STATUS_IS_OK(status)) {
2362 return status;
2365 if (!parent_dirname(talloc_tos(), smb_dname->base_name, &parent_dir,
2366 NULL)) {
2367 return NT_STATUS_NO_MEMORY;
2370 if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
2371 posix_open = true;
2372 mode = (mode_t)(file_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
2373 } else {
2374 mode = unix_mode(conn, aDIR, smb_dname, parent_dir);
2377 if (SMB_VFS_MKDIR(conn, smb_dname->base_name, mode) != 0) {
2378 return map_nt_error_from_unix(errno);
2381 /* Ensure we're checking for a symlink here.... */
2382 /* We don't want to get caught by a symlink racer. */
2384 if (SMB_VFS_LSTAT(conn, smb_dname) == -1) {
2385 DEBUG(2, ("Could not stat directory '%s' just created: %s\n",
2386 smb_fname_str_dbg(smb_dname), strerror(errno)));
2387 return map_nt_error_from_unix(errno);
2390 if (!S_ISDIR(smb_dname->st.st_ex_mode)) {
2391 DEBUG(0, ("Directory just '%s' created is not a directory\n",
2392 smb_fname_str_dbg(smb_dname)));
2393 return NT_STATUS_ACCESS_DENIED;
2396 if (lp_store_dos_attributes(SNUM(conn))) {
2397 if (!posix_open) {
2398 file_set_dosmode(conn, smb_dname,
2399 file_attributes | aDIR,
2400 parent_dir, true);
2404 if (lp_inherit_perms(SNUM(conn))) {
2405 inherit_access_posix_acl(conn, parent_dir,
2406 smb_dname->base_name, mode);
2409 if (!posix_open) {
2411 * Check if high bits should have been set,
2412 * then (if bits are missing): add them.
2413 * Consider bits automagically set by UNIX, i.e. SGID bit from parent
2414 * dir.
2416 if ((mode & ~(S_IRWXU|S_IRWXG|S_IRWXO)) &&
2417 (mode & ~smb_dname->st.st_ex_mode)) {
2418 SMB_VFS_CHMOD(conn, smb_dname->base_name,
2419 (smb_dname->st.st_ex_mode |
2420 (mode & ~smb_dname->st.st_ex_mode)));
2424 /* Change the owner if required. */
2425 if (lp_inherit_owner(SNUM(conn))) {
2426 change_dir_owner_to_parent(conn, parent_dir,
2427 smb_dname->base_name,
2428 &smb_dname->st);
2431 notify_fname(conn, NOTIFY_ACTION_ADDED, FILE_NOTIFY_CHANGE_DIR_NAME,
2432 smb_dname->base_name);
2434 return NT_STATUS_OK;
2437 /****************************************************************************
2438 Open a directory from an NT SMB call.
2439 ****************************************************************************/
2441 static NTSTATUS open_directory(connection_struct *conn,
2442 struct smb_request *req,
2443 struct smb_filename *smb_dname,
2444 uint32 access_mask,
2445 uint32 share_access,
2446 uint32 create_disposition,
2447 uint32 create_options,
2448 uint32 file_attributes,
2449 int *pinfo,
2450 files_struct **result)
2452 files_struct *fsp = NULL;
2453 bool dir_existed = VALID_STAT(smb_dname->st) ? True : False;
2454 struct share_mode_lock *lck = NULL;
2455 NTSTATUS status;
2456 struct timespec mtimespec;
2457 int info = 0;
2459 SMB_ASSERT(!is_ntfs_stream_smb_fname(smb_dname));
2461 DEBUG(5,("open_directory: opening directory %s, access_mask = 0x%x, "
2462 "share_access = 0x%x create_options = 0x%x, "
2463 "create_disposition = 0x%x, file_attributes = 0x%x\n",
2464 smb_fname_str_dbg(smb_dname),
2465 (unsigned int)access_mask,
2466 (unsigned int)share_access,
2467 (unsigned int)create_options,
2468 (unsigned int)create_disposition,
2469 (unsigned int)file_attributes));
2471 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
2472 (conn->fs_capabilities & FILE_NAMED_STREAMS) &&
2473 is_ntfs_stream_smb_fname(smb_dname)) {
2474 DEBUG(2, ("open_directory: %s is a stream name!\n",
2475 smb_fname_str_dbg(smb_dname)));
2476 return NT_STATUS_NOT_A_DIRECTORY;
2479 status = calculate_access_mask(conn, smb_dname, dir_existed,
2480 access_mask, &access_mask);
2481 if (!NT_STATUS_IS_OK(status)) {
2482 DEBUG(10, ("open_directory: calculate_access_mask "
2483 "on file %s returned %s\n",
2484 smb_fname_str_dbg(smb_dname),
2485 nt_errstr(status)));
2486 return status;
2489 /* We need to support SeSecurityPrivilege for this. */
2490 if (access_mask & SEC_FLAG_SYSTEM_SECURITY) {
2491 DEBUG(10, ("open_directory: open on %s "
2492 "failed - SEC_FLAG_SYSTEM_SECURITY denied.\n",
2493 smb_fname_str_dbg(smb_dname)));
2494 return NT_STATUS_PRIVILEGE_NOT_HELD;
2497 switch( create_disposition ) {
2498 case FILE_OPEN:
2500 info = FILE_WAS_OPENED;
2503 * We want to follow symlinks here.
2506 if (SMB_VFS_STAT(conn, smb_dname) != 0) {
2507 return map_nt_error_from_unix(errno);
2510 break;
2512 case FILE_CREATE:
2514 /* If directory exists error. If directory doesn't
2515 * exist create. */
2517 status = mkdir_internal(conn, smb_dname,
2518 file_attributes);
2520 if (!NT_STATUS_IS_OK(status)) {
2521 DEBUG(2, ("open_directory: unable to create "
2522 "%s. Error was %s\n",
2523 smb_fname_str_dbg(smb_dname),
2524 nt_errstr(status)));
2525 return status;
2528 info = FILE_WAS_CREATED;
2529 break;
2531 case FILE_OPEN_IF:
2533 * If directory exists open. If directory doesn't
2534 * exist create.
2537 status = mkdir_internal(conn, smb_dname,
2538 file_attributes);
2540 if (NT_STATUS_IS_OK(status)) {
2541 info = FILE_WAS_CREATED;
2544 if (NT_STATUS_EQUAL(status,
2545 NT_STATUS_OBJECT_NAME_COLLISION)) {
2546 info = FILE_WAS_OPENED;
2547 status = NT_STATUS_OK;
2550 break;
2552 case FILE_SUPERSEDE:
2553 case FILE_OVERWRITE:
2554 case FILE_OVERWRITE_IF:
2555 default:
2556 DEBUG(5,("open_directory: invalid create_disposition "
2557 "0x%x for directory %s\n",
2558 (unsigned int)create_disposition,
2559 smb_fname_str_dbg(smb_dname)));
2560 return NT_STATUS_INVALID_PARAMETER;
2563 if(!S_ISDIR(smb_dname->st.st_ex_mode)) {
2564 DEBUG(5,("open_directory: %s is not a directory !\n",
2565 smb_fname_str_dbg(smb_dname)));
2566 return NT_STATUS_NOT_A_DIRECTORY;
2569 if (info == FILE_WAS_OPENED) {
2570 uint32_t access_granted = 0;
2571 status = smbd_check_open_rights(conn, smb_dname, access_mask,
2572 &access_granted);
2574 /* Were we trying to do a directory open
2575 * for delete and didn't get DELETE
2576 * access (only) ? Check if the
2577 * directory allows DELETE_CHILD.
2578 * See here:
2579 * http://blogs.msdn.com/oldnewthing/archive/2004/06/04/148426.aspx
2580 * for details. */
2582 if ((NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED) &&
2583 (access_mask & DELETE_ACCESS) &&
2584 (access_granted == DELETE_ACCESS) &&
2585 can_delete_file_in_directory(conn, smb_dname))) {
2586 DEBUG(10,("open_directory: overrode ACCESS_DENIED "
2587 "on directory %s\n",
2588 smb_fname_str_dbg(smb_dname)));
2589 status = NT_STATUS_OK;
2592 if (!NT_STATUS_IS_OK(status)) {
2593 DEBUG(10, ("open_directory: smbd_check_open_rights on "
2594 "file %s failed with %s\n",
2595 smb_fname_str_dbg(smb_dname),
2596 nt_errstr(status)));
2597 return status;
2601 status = file_new(req, conn, &fsp);
2602 if(!NT_STATUS_IS_OK(status)) {
2603 return status;
2607 * Setup the files_struct for it.
2610 fsp->mode = smb_dname->st.st_ex_mode;
2611 fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_dname->st);
2612 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
2613 fsp->file_pid = req ? req->smbpid : 0;
2614 fsp->can_lock = False;
2615 fsp->can_read = False;
2616 fsp->can_write = False;
2618 fsp->share_access = share_access;
2619 fsp->fh->private_options = 0;
2621 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
2623 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
2624 fsp->print_file = NULL;
2625 fsp->modified = False;
2626 fsp->oplock_type = NO_OPLOCK;
2627 fsp->sent_oplock_break = NO_BREAK_SENT;
2628 fsp->is_directory = True;
2629 fsp->posix_open = (file_attributes & FILE_FLAG_POSIX_SEMANTICS) ? True : False;
2630 status = fsp_set_smb_fname(fsp, smb_dname);
2631 if (!NT_STATUS_IS_OK(status)) {
2632 return status;
2635 mtimespec = smb_dname->st.st_ex_mtime;
2637 lck = get_share_mode_lock(talloc_tos(), fsp->file_id,
2638 conn->connectpath, smb_dname, &mtimespec);
2640 if (lck == NULL) {
2641 DEBUG(0, ("open_directory: Could not get share mode lock for "
2642 "%s\n", smb_fname_str_dbg(smb_dname)));
2643 file_free(req, fsp);
2644 return NT_STATUS_SHARING_VIOLATION;
2647 status = open_mode_check(conn, lck, access_mask, share_access,
2648 create_options, &dir_existed);
2650 if (!NT_STATUS_IS_OK(status)) {
2651 TALLOC_FREE(lck);
2652 file_free(req, fsp);
2653 return status;
2656 set_share_mode(lck, fsp, get_current_uid(conn), 0, NO_OPLOCK);
2658 /* For directories the delete on close bit at open time seems
2659 always to be honored on close... See test 19 in Samba4 BASE-DELETE. */
2660 if (create_options & FILE_DELETE_ON_CLOSE) {
2661 status = can_set_delete_on_close(fsp, 0);
2662 if (!NT_STATUS_IS_OK(status) && !NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
2663 TALLOC_FREE(lck);
2664 file_free(req, fsp);
2665 return status;
2668 if (NT_STATUS_IS_OK(status)) {
2669 /* Note that here we set the *inital* delete on close flag,
2670 not the regular one. The magic gets handled in close. */
2671 fsp->initial_delete_on_close = True;
2675 TALLOC_FREE(lck);
2677 if (pinfo) {
2678 *pinfo = info;
2681 *result = fsp;
2682 return NT_STATUS_OK;
2685 NTSTATUS create_directory(connection_struct *conn, struct smb_request *req,
2686 struct smb_filename *smb_dname)
2688 NTSTATUS status;
2689 files_struct *fsp;
2691 status = SMB_VFS_CREATE_FILE(
2692 conn, /* conn */
2693 req, /* req */
2694 0, /* root_dir_fid */
2695 smb_dname, /* fname */
2696 FILE_READ_ATTRIBUTES, /* access_mask */
2697 FILE_SHARE_NONE, /* share_access */
2698 FILE_CREATE, /* create_disposition*/
2699 FILE_DIRECTORY_FILE, /* create_options */
2700 FILE_ATTRIBUTE_DIRECTORY, /* file_attributes */
2701 0, /* oplock_request */
2702 0, /* allocation_size */
2703 0, /* private_flags */
2704 NULL, /* sd */
2705 NULL, /* ea_list */
2706 &fsp, /* result */
2707 NULL); /* pinfo */
2709 if (NT_STATUS_IS_OK(status)) {
2710 close_file(req, fsp, NORMAL_CLOSE);
2713 return status;
2716 /****************************************************************************
2717 Receive notification that one of our open files has been renamed by another
2718 smbd process.
2719 ****************************************************************************/
2721 void msg_file_was_renamed(struct messaging_context *msg,
2722 void *private_data,
2723 uint32_t msg_type,
2724 struct server_id server_id,
2725 DATA_BLOB *data)
2727 files_struct *fsp;
2728 char *frm = (char *)data->data;
2729 struct file_id id;
2730 const char *sharepath;
2731 const char *base_name;
2732 const char *stream_name;
2733 struct smb_filename *smb_fname = NULL;
2734 size_t sp_len, bn_len;
2735 NTSTATUS status;
2737 if (data->data == NULL
2738 || data->length < MSG_FILE_RENAMED_MIN_SIZE + 2) {
2739 DEBUG(0, ("msg_file_was_renamed: Got invalid msg len %d\n",
2740 (int)data->length));
2741 return;
2744 /* Unpack the message. */
2745 pull_file_id_24(frm, &id);
2746 sharepath = &frm[24];
2747 sp_len = strlen(sharepath);
2748 base_name = sharepath + sp_len + 1;
2749 bn_len = strlen(base_name);
2750 stream_name = sharepath + sp_len + 1 + bn_len + 1;
2752 /* stream_name must always be NULL if there is no stream. */
2753 if (stream_name[0] == '\0') {
2754 stream_name = NULL;
2757 status = create_synthetic_smb_fname(talloc_tos(), base_name,
2758 stream_name, NULL, &smb_fname);
2759 if (!NT_STATUS_IS_OK(status)) {
2760 return;
2763 DEBUG(10,("msg_file_was_renamed: Got rename message for sharepath %s, new name %s, "
2764 "file_id %s\n",
2765 sharepath, smb_fname_str_dbg(smb_fname),
2766 file_id_string_tos(&id)));
2768 for(fsp = file_find_di_first(id); fsp; fsp = file_find_di_next(fsp)) {
2769 if (memcmp(fsp->conn->connectpath, sharepath, sp_len) == 0) {
2771 DEBUG(10,("msg_file_was_renamed: renaming file fnum %d from %s -> %s\n",
2772 fsp->fnum, fsp_str_dbg(fsp),
2773 smb_fname_str_dbg(smb_fname)));
2774 status = fsp_set_smb_fname(fsp, smb_fname);
2775 if (!NT_STATUS_IS_OK(status)) {
2776 goto out;
2778 } else {
2779 /* TODO. JRA. */
2780 /* Now we have the complete path we can work out if this is
2781 actually within this share and adjust newname accordingly. */
2782 DEBUG(10,("msg_file_was_renamed: share mismatch (sharepath %s "
2783 "not sharepath %s) "
2784 "fnum %d from %s -> %s\n",
2785 fsp->conn->connectpath,
2786 sharepath,
2787 fsp->fnum,
2788 fsp_str_dbg(fsp),
2789 smb_fname_str_dbg(smb_fname)));
2792 out:
2793 TALLOC_FREE(smb_fname);
2794 return;
2798 * If a main file is opened for delete, all streams need to be checked for
2799 * !FILE_SHARE_DELETE. Do this by opening with DELETE_ACCESS.
2800 * If that works, delete them all by setting the delete on close and close.
2803 NTSTATUS open_streams_for_delete(connection_struct *conn,
2804 const char *fname)
2806 struct stream_struct *stream_info;
2807 files_struct **streams;
2808 int i;
2809 unsigned int num_streams;
2810 TALLOC_CTX *frame = talloc_stackframe();
2811 NTSTATUS status;
2813 status = SMB_VFS_STREAMINFO(conn, NULL, fname, talloc_tos(),
2814 &num_streams, &stream_info);
2816 if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_IMPLEMENTED)
2817 || NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
2818 DEBUG(10, ("no streams around\n"));
2819 TALLOC_FREE(frame);
2820 return NT_STATUS_OK;
2823 if (!NT_STATUS_IS_OK(status)) {
2824 DEBUG(10, ("SMB_VFS_STREAMINFO failed: %s\n",
2825 nt_errstr(status)));
2826 goto fail;
2829 DEBUG(10, ("open_streams_for_delete found %d streams\n",
2830 num_streams));
2832 if (num_streams == 0) {
2833 TALLOC_FREE(frame);
2834 return NT_STATUS_OK;
2837 streams = TALLOC_ARRAY(talloc_tos(), files_struct *, num_streams);
2838 if (streams == NULL) {
2839 DEBUG(0, ("talloc failed\n"));
2840 status = NT_STATUS_NO_MEMORY;
2841 goto fail;
2844 for (i=0; i<num_streams; i++) {
2845 struct smb_filename *smb_fname = NULL;
2847 if (strequal(stream_info[i].name, "::$DATA")) {
2848 streams[i] = NULL;
2849 continue;
2852 status = create_synthetic_smb_fname(talloc_tos(), fname,
2853 stream_info[i].name,
2854 NULL, &smb_fname);
2855 if (!NT_STATUS_IS_OK(status)) {
2856 goto fail;
2859 if (SMB_VFS_STAT(conn, smb_fname) == -1) {
2860 DEBUG(10, ("Unable to stat stream: %s\n",
2861 smb_fname_str_dbg(smb_fname)));
2864 status = SMB_VFS_CREATE_FILE(
2865 conn, /* conn */
2866 NULL, /* req */
2867 0, /* root_dir_fid */
2868 smb_fname, /* fname */
2869 DELETE_ACCESS, /* access_mask */
2870 (FILE_SHARE_READ | /* share_access */
2871 FILE_SHARE_WRITE | FILE_SHARE_DELETE),
2872 FILE_OPEN, /* create_disposition*/
2873 0, /* create_options */
2874 FILE_ATTRIBUTE_NORMAL, /* file_attributes */
2875 0, /* oplock_request */
2876 0, /* allocation_size */
2877 NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE, /* private_flags */
2878 NULL, /* sd */
2879 NULL, /* ea_list */
2880 &streams[i], /* result */
2881 NULL); /* pinfo */
2883 if (!NT_STATUS_IS_OK(status)) {
2884 DEBUG(10, ("Could not open stream %s: %s\n",
2885 smb_fname_str_dbg(smb_fname),
2886 nt_errstr(status)));
2888 TALLOC_FREE(smb_fname);
2889 break;
2891 TALLOC_FREE(smb_fname);
2895 * don't touch the variable "status" beyond this point :-)
2898 for (i -= 1 ; i >= 0; i--) {
2899 if (streams[i] == NULL) {
2900 continue;
2903 DEBUG(10, ("Closing stream # %d, %s\n", i,
2904 fsp_str_dbg(streams[i])));
2905 close_file(NULL, streams[i], NORMAL_CLOSE);
2908 fail:
2909 TALLOC_FREE(frame);
2910 return status;
2914 * Wrapper around open_file_ntcreate and open_directory
2917 static NTSTATUS create_file_unixpath(connection_struct *conn,
2918 struct smb_request *req,
2919 struct smb_filename *smb_fname,
2920 uint32_t access_mask,
2921 uint32_t share_access,
2922 uint32_t create_disposition,
2923 uint32_t create_options,
2924 uint32_t file_attributes,
2925 uint32_t oplock_request,
2926 uint64_t allocation_size,
2927 uint32_t private_flags,
2928 struct security_descriptor *sd,
2929 struct ea_list *ea_list,
2931 files_struct **result,
2932 int *pinfo)
2934 int info = FILE_WAS_OPENED;
2935 files_struct *base_fsp = NULL;
2936 files_struct *fsp = NULL;
2937 NTSTATUS status;
2939 DEBUG(10,("create_file_unixpath: access_mask = 0x%x "
2940 "file_attributes = 0x%x, share_access = 0x%x, "
2941 "create_disposition = 0x%x create_options = 0x%x "
2942 "oplock_request = 0x%x private_flags = 0x%x "
2943 "ea_list = 0x%p, sd = 0x%p, "
2944 "fname = %s\n",
2945 (unsigned int)access_mask,
2946 (unsigned int)file_attributes,
2947 (unsigned int)share_access,
2948 (unsigned int)create_disposition,
2949 (unsigned int)create_options,
2950 (unsigned int)oplock_request,
2951 (unsigned int)private_flags,
2952 ea_list, sd, smb_fname_str_dbg(smb_fname)));
2954 if (create_options & FILE_OPEN_BY_FILE_ID) {
2955 status = NT_STATUS_NOT_SUPPORTED;
2956 goto fail;
2959 if (create_options & NTCREATEX_OPTIONS_INVALID_PARAM_MASK) {
2960 status = NT_STATUS_INVALID_PARAMETER;
2961 goto fail;
2964 if (req == NULL) {
2965 oplock_request |= INTERNAL_OPEN_ONLY;
2968 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
2969 && (access_mask & DELETE_ACCESS)
2970 && !is_ntfs_stream_smb_fname(smb_fname)) {
2972 * We can't open a file with DELETE access if any of the
2973 * streams is open without FILE_SHARE_DELETE
2975 status = open_streams_for_delete(conn, smb_fname->base_name);
2977 if (!NT_STATUS_IS_OK(status)) {
2978 goto fail;
2982 /* This is the correct thing to do (check every time) but can_delete
2983 * is expensive (it may have to read the parent directory
2984 * permissions). So for now we're not doing it unless we have a strong
2985 * hint the client is really going to delete this file. If the client
2986 * is forcing FILE_CREATE let the filesystem take care of the
2987 * permissions. */
2989 /* Setting FILE_SHARE_DELETE is the hint. */
2991 if (lp_acl_check_permissions(SNUM(conn))
2992 && (create_disposition != FILE_CREATE)
2993 && (share_access & FILE_SHARE_DELETE)
2994 && (access_mask & DELETE_ACCESS)
2995 && (!(can_delete_file_in_directory(conn, smb_fname) ||
2996 can_access_file_acl(conn, smb_fname, DELETE_ACCESS)))) {
2997 status = NT_STATUS_ACCESS_DENIED;
2998 DEBUG(10,("create_file_unixpath: open file %s "
2999 "for delete ACCESS_DENIED\n",
3000 smb_fname_str_dbg(smb_fname)));
3001 goto fail;
3004 #if 0
3005 /* We need to support SeSecurityPrivilege for this. */
3006 if ((access_mask & SEC_FLAG_SYSTEM_SECURITY) &&
3007 !user_has_privileges(current_user.nt_user_token,
3008 &se_security)) {
3009 status = NT_STATUS_PRIVILEGE_NOT_HELD;
3010 goto fail;
3012 #else
3013 /* We need to support SeSecurityPrivilege for this. */
3014 if (access_mask & SEC_FLAG_SYSTEM_SECURITY) {
3015 status = NT_STATUS_PRIVILEGE_NOT_HELD;
3016 goto fail;
3018 /* Don't allow a SACL set from an NTtrans create until we
3019 * support SeSecurityPrivilege. */
3020 if (!VALID_STAT(smb_fname->st) &&
3021 lp_nt_acl_support(SNUM(conn)) &&
3022 sd && (sd->sacl != NULL)) {
3023 status = NT_STATUS_PRIVILEGE_NOT_HELD;
3024 goto fail;
3026 #endif
3028 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
3029 && is_ntfs_stream_smb_fname(smb_fname)
3030 && (!(private_flags & NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE))) {
3031 uint32 base_create_disposition;
3032 struct smb_filename *smb_fname_base = NULL;
3034 if (create_options & FILE_DIRECTORY_FILE) {
3035 status = NT_STATUS_NOT_A_DIRECTORY;
3036 goto fail;
3039 switch (create_disposition) {
3040 case FILE_OPEN:
3041 base_create_disposition = FILE_OPEN;
3042 break;
3043 default:
3044 base_create_disposition = FILE_OPEN_IF;
3045 break;
3048 /* Create an smb_filename with stream_name == NULL. */
3049 status = create_synthetic_smb_fname(talloc_tos(),
3050 smb_fname->base_name,
3051 NULL, NULL,
3052 &smb_fname_base);
3053 if (!NT_STATUS_IS_OK(status)) {
3054 goto fail;
3057 if (SMB_VFS_STAT(conn, smb_fname_base) == -1) {
3058 DEBUG(10, ("Unable to stat stream: %s\n",
3059 smb_fname_str_dbg(smb_fname_base)));
3062 /* Open the base file. */
3063 status = create_file_unixpath(conn, NULL, smb_fname_base, 0,
3064 FILE_SHARE_READ
3065 | FILE_SHARE_WRITE
3066 | FILE_SHARE_DELETE,
3067 base_create_disposition,
3068 0, 0, 0, 0, 0, NULL, NULL,
3069 &base_fsp, NULL);
3070 TALLOC_FREE(smb_fname_base);
3072 if (!NT_STATUS_IS_OK(status)) {
3073 DEBUG(10, ("create_file_unixpath for base %s failed: "
3074 "%s\n", smb_fname->base_name,
3075 nt_errstr(status)));
3076 goto fail;
3078 /* we don't need to low level fd */
3079 fd_close(base_fsp);
3083 * If it's a request for a directory open, deal with it separately.
3086 if (create_options & FILE_DIRECTORY_FILE) {
3088 if (create_options & FILE_NON_DIRECTORY_FILE) {
3089 status = NT_STATUS_INVALID_PARAMETER;
3090 goto fail;
3093 /* Can't open a temp directory. IFS kit test. */
3094 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
3095 (file_attributes & FILE_ATTRIBUTE_TEMPORARY)) {
3096 status = NT_STATUS_INVALID_PARAMETER;
3097 goto fail;
3101 * We will get a create directory here if the Win32
3102 * app specified a security descriptor in the
3103 * CreateDirectory() call.
3106 oplock_request = 0;
3107 status = open_directory(
3108 conn, req, smb_fname, access_mask, share_access,
3109 create_disposition, create_options, file_attributes,
3110 &info, &fsp);
3111 } else {
3114 * Ordinary file case.
3117 status = file_new(req, conn, &fsp);
3118 if(!NT_STATUS_IS_OK(status)) {
3119 goto fail;
3122 status = fsp_set_smb_fname(fsp, smb_fname);
3123 if (!NT_STATUS_IS_OK(status)) {
3124 goto fail;
3128 * We're opening the stream element of a base_fsp
3129 * we already opened. Set up the base_fsp pointer.
3131 if (base_fsp) {
3132 fsp->base_fsp = base_fsp;
3135 status = open_file_ntcreate(conn,
3136 req,
3137 access_mask,
3138 share_access,
3139 create_disposition,
3140 create_options,
3141 file_attributes,
3142 oplock_request,
3143 private_flags,
3144 &info,
3145 fsp);
3147 if(!NT_STATUS_IS_OK(status)) {
3148 file_free(req, fsp);
3149 fsp = NULL;
3152 if (NT_STATUS_EQUAL(status, NT_STATUS_FILE_IS_A_DIRECTORY)) {
3154 /* A stream open never opens a directory */
3156 if (base_fsp) {
3157 status = NT_STATUS_FILE_IS_A_DIRECTORY;
3158 goto fail;
3162 * Fail the open if it was explicitly a non-directory
3163 * file.
3166 if (create_options & FILE_NON_DIRECTORY_FILE) {
3167 status = NT_STATUS_FILE_IS_A_DIRECTORY;
3168 goto fail;
3171 oplock_request = 0;
3172 status = open_directory(
3173 conn, req, smb_fname, access_mask,
3174 share_access, create_disposition,
3175 create_options, file_attributes,
3176 &info, &fsp);
3180 if (!NT_STATUS_IS_OK(status)) {
3181 goto fail;
3184 fsp->base_fsp = base_fsp;
3187 * According to the MS documentation, the only time the security
3188 * descriptor is applied to the opened file is iff we *created* the
3189 * file; an existing file stays the same.
3191 * Also, it seems (from observation) that you can open the file with
3192 * any access mask but you can still write the sd. We need to override
3193 * the granted access before we call set_sd
3194 * Patch for bug #2242 from Tom Lackemann <cessnatomny@yahoo.com>.
3197 if ((sd != NULL) && (info == FILE_WAS_CREATED)
3198 && lp_nt_acl_support(SNUM(conn))) {
3200 uint32_t sec_info_sent;
3201 uint32_t saved_access_mask = fsp->access_mask;
3203 sec_info_sent = get_sec_info(sd);
3205 fsp->access_mask = FILE_GENERIC_ALL;
3207 /* Convert all the generic bits. */
3208 security_acl_map_generic(sd->dacl, &file_generic_mapping);
3209 security_acl_map_generic(sd->sacl, &file_generic_mapping);
3211 if (sec_info_sent & (OWNER_SECURITY_INFORMATION|
3212 GROUP_SECURITY_INFORMATION|
3213 DACL_SECURITY_INFORMATION|
3214 SACL_SECURITY_INFORMATION)) {
3215 status = SMB_VFS_FSET_NT_ACL(fsp, sec_info_sent, sd);
3218 fsp->access_mask = saved_access_mask;
3220 if (!NT_STATUS_IS_OK(status)) {
3221 goto fail;
3225 if ((ea_list != NULL) &&
3226 ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN))) {
3227 status = set_ea(conn, fsp, fsp->fsp_name, ea_list);
3228 if (!NT_STATUS_IS_OK(status)) {
3229 goto fail;
3233 if (!fsp->is_directory && S_ISDIR(fsp->fsp_name->st.st_ex_mode)) {
3234 status = NT_STATUS_ACCESS_DENIED;
3235 goto fail;
3238 /* Save the requested allocation size. */
3239 if ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN)) {
3240 if (allocation_size
3241 && (allocation_size > fsp->fsp_name->st.st_ex_size)) {
3242 fsp->initial_allocation_size = smb_roundup(
3243 fsp->conn, allocation_size);
3244 if (fsp->is_directory) {
3245 /* Can't set allocation size on a directory. */
3246 status = NT_STATUS_ACCESS_DENIED;
3247 goto fail;
3249 if (vfs_allocate_file_space(
3250 fsp, fsp->initial_allocation_size) == -1) {
3251 status = NT_STATUS_DISK_FULL;
3252 goto fail;
3254 } else {
3255 fsp->initial_allocation_size = smb_roundup(
3256 fsp->conn, (uint64_t)fsp->fsp_name->st.st_ex_size);
3260 DEBUG(10, ("create_file_unixpath: info=%d\n", info));
3262 *result = fsp;
3263 if (pinfo != NULL) {
3264 *pinfo = info;
3267 smb_fname->st = fsp->fsp_name->st;
3269 return NT_STATUS_OK;
3271 fail:
3272 DEBUG(10, ("create_file_unixpath: %s\n", nt_errstr(status)));
3274 if (fsp != NULL) {
3275 if (base_fsp && fsp->base_fsp == base_fsp) {
3277 * The close_file below will close
3278 * fsp->base_fsp.
3280 base_fsp = NULL;
3282 close_file(req, fsp, ERROR_CLOSE);
3283 fsp = NULL;
3285 if (base_fsp != NULL) {
3286 close_file(req, base_fsp, ERROR_CLOSE);
3287 base_fsp = NULL;
3289 return status;
3293 * Calculate the full path name given a relative fid.
3295 NTSTATUS get_relative_fid_filename(connection_struct *conn,
3296 struct smb_request *req,
3297 uint16_t root_dir_fid,
3298 struct smb_filename *smb_fname)
3300 files_struct *dir_fsp;
3301 char *parent_fname = NULL;
3302 char *new_base_name = NULL;
3303 NTSTATUS status;
3305 if (root_dir_fid == 0 || !smb_fname) {
3306 status = NT_STATUS_INTERNAL_ERROR;
3307 goto out;
3310 dir_fsp = file_fsp(req, root_dir_fid);
3312 if (dir_fsp == NULL) {
3313 status = NT_STATUS_INVALID_HANDLE;
3314 goto out;
3317 if (is_ntfs_stream_smb_fname(dir_fsp->fsp_name)) {
3318 status = NT_STATUS_INVALID_HANDLE;
3319 goto out;
3322 if (!dir_fsp->is_directory) {
3325 * Check to see if this is a mac fork of some kind.
3328 if ((conn->fs_capabilities & FILE_NAMED_STREAMS) &&
3329 is_ntfs_stream_smb_fname(smb_fname)) {
3330 status = NT_STATUS_OBJECT_PATH_NOT_FOUND;
3331 goto out;
3335 we need to handle the case when we get a
3336 relative open relative to a file and the
3337 pathname is blank - this is a reopen!
3338 (hint from demyn plantenberg)
3341 status = NT_STATUS_INVALID_HANDLE;
3342 goto out;
3345 if (ISDOT(dir_fsp->fsp_name->base_name)) {
3347 * We're at the toplevel dir, the final file name
3348 * must not contain ./, as this is filtered out
3349 * normally by srvstr_get_path and unix_convert
3350 * explicitly rejects paths containing ./.
3352 parent_fname = talloc_strdup(talloc_tos(), "");
3353 if (parent_fname == NULL) {
3354 status = NT_STATUS_NO_MEMORY;
3355 goto out;
3357 } else {
3358 size_t dir_name_len = strlen(dir_fsp->fsp_name->base_name);
3361 * Copy in the base directory name.
3364 parent_fname = TALLOC_ARRAY(talloc_tos(), char,
3365 dir_name_len+2);
3366 if (parent_fname == NULL) {
3367 status = NT_STATUS_NO_MEMORY;
3368 goto out;
3370 memcpy(parent_fname, dir_fsp->fsp_name->base_name,
3371 dir_name_len+1);
3374 * Ensure it ends in a '/'.
3375 * We used TALLOC_SIZE +2 to add space for the '/'.
3378 if(dir_name_len
3379 && (parent_fname[dir_name_len-1] != '\\')
3380 && (parent_fname[dir_name_len-1] != '/')) {
3381 parent_fname[dir_name_len] = '/';
3382 parent_fname[dir_name_len+1] = '\0';
3386 new_base_name = talloc_asprintf(smb_fname, "%s%s", parent_fname,
3387 smb_fname->base_name);
3388 if (new_base_name == NULL) {
3389 status = NT_STATUS_NO_MEMORY;
3390 goto out;
3393 TALLOC_FREE(smb_fname->base_name);
3394 smb_fname->base_name = new_base_name;
3395 status = NT_STATUS_OK;
3397 out:
3398 TALLOC_FREE(parent_fname);
3399 return status;
3402 NTSTATUS create_file_default(connection_struct *conn,
3403 struct smb_request *req,
3404 uint16_t root_dir_fid,
3405 struct smb_filename *smb_fname,
3406 uint32_t access_mask,
3407 uint32_t share_access,
3408 uint32_t create_disposition,
3409 uint32_t create_options,
3410 uint32_t file_attributes,
3411 uint32_t oplock_request,
3412 uint64_t allocation_size,
3413 uint32_t private_flags,
3414 struct security_descriptor *sd,
3415 struct ea_list *ea_list,
3416 files_struct **result,
3417 int *pinfo)
3419 int info = FILE_WAS_OPENED;
3420 files_struct *fsp = NULL;
3421 NTSTATUS status;
3422 bool stream_name = false;
3424 DEBUG(10,("create_file: access_mask = 0x%x "
3425 "file_attributes = 0x%x, share_access = 0x%x, "
3426 "create_disposition = 0x%x create_options = 0x%x "
3427 "oplock_request = 0x%x "
3428 "private_flags = 0x%x "
3429 "root_dir_fid = 0x%x, ea_list = 0x%p, sd = 0x%p, "
3430 "fname = %s\n",
3431 (unsigned int)access_mask,
3432 (unsigned int)file_attributes,
3433 (unsigned int)share_access,
3434 (unsigned int)create_disposition,
3435 (unsigned int)create_options,
3436 (unsigned int)oplock_request,
3437 (unsigned int)private_flags,
3438 (unsigned int)root_dir_fid,
3439 ea_list, sd, smb_fname_str_dbg(smb_fname)));
3442 * Calculate the filename from the root_dir_if if necessary.
3445 if (root_dir_fid != 0) {
3446 status = get_relative_fid_filename(conn, req, root_dir_fid,
3447 smb_fname);
3448 if (!NT_STATUS_IS_OK(status)) {
3449 goto fail;
3454 * Check to see if this is a mac fork of some kind.
3457 stream_name = is_ntfs_stream_smb_fname(smb_fname);
3458 if (stream_name) {
3459 enum FAKE_FILE_TYPE fake_file_type;
3461 fake_file_type = is_fake_file(smb_fname);
3463 if (fake_file_type != FAKE_FILE_TYPE_NONE) {
3466 * Here we go! support for changing the disk quotas
3467 * --metze
3469 * We need to fake up to open this MAGIC QUOTA file
3470 * and return a valid FID.
3472 * w2k close this file directly after openening xp
3473 * also tries a QUERY_FILE_INFO on the file and then
3474 * close it
3476 status = open_fake_file(req, conn, req->vuid,
3477 fake_file_type, smb_fname,
3478 access_mask, &fsp);
3479 if (!NT_STATUS_IS_OK(status)) {
3480 goto fail;
3483 ZERO_STRUCT(smb_fname->st);
3484 goto done;
3487 if (!(conn->fs_capabilities & FILE_NAMED_STREAMS)) {
3488 status = NT_STATUS_OBJECT_NAME_NOT_FOUND;
3489 goto fail;
3493 /* All file access must go through check_name() */
3495 status = check_name(conn, smb_fname->base_name);
3496 if (!NT_STATUS_IS_OK(status)) {
3497 goto fail;
3500 if (stream_name && is_ntfs_default_stream_smb_fname(smb_fname)) {
3501 int ret;
3502 smb_fname->stream_name = NULL;
3503 /* We have to handle this error here. */
3504 if (create_options & FILE_DIRECTORY_FILE) {
3505 status = NT_STATUS_NOT_A_DIRECTORY;
3506 goto fail;
3508 if (lp_posix_pathnames()) {
3509 ret = SMB_VFS_LSTAT(conn, smb_fname);
3510 } else {
3511 ret = SMB_VFS_STAT(conn, smb_fname);
3514 if (ret == 0 && VALID_STAT_OF_DIR(smb_fname->st)) {
3515 status = NT_STATUS_FILE_IS_A_DIRECTORY;
3516 goto fail;
3520 status = create_file_unixpath(
3521 conn, req, smb_fname, access_mask, share_access,
3522 create_disposition, create_options, file_attributes,
3523 oplock_request, allocation_size, private_flags,
3524 sd, ea_list,
3525 &fsp, &info);
3527 if (!NT_STATUS_IS_OK(status)) {
3528 goto fail;
3531 done:
3532 DEBUG(10, ("create_file: info=%d\n", info));
3534 *result = fsp;
3535 if (pinfo != NULL) {
3536 *pinfo = info;
3538 return NT_STATUS_OK;
3540 fail:
3541 DEBUG(10, ("create_file: %s\n", nt_errstr(status)));
3543 if (fsp != NULL) {
3544 close_file(req, fsp, ERROR_CLOSE);
3545 fsp = NULL;
3547 return status;