2 * Unix SMB/CIFS implementation.
4 * This file began with some code from source3/smbd/open.c and has been
5 * modified it work with ifs_createfile.
7 * ifs_createfile is a CIFS-specific syscall for opening/files and
8 * directories. It adds support for:
9 * - Full in-kernel access checks using a windows access_mask
10 * - Cluster-coherent share mode locks
11 * - Cluster-coherent oplocks
13 * - Setting security descriptors at create time
14 * - Setting dos_attributes at create time
16 * Copyright (C) Andrew Tridgell 1992-1998
17 * Copyright (C) Jeremy Allison 2001-2004
18 * Copyright (C) Volker Lendecke 2005
19 * Copyright (C) Tim Prouty, 2008
21 * This program is free software; you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation; either version 3 of the License, or
24 * (at your option) any later version.
26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
29 * GNU General Public License for more details.
31 * You should have received a copy of the GNU General Public License
32 * along with this program; if not, see <http://www.gnu.org/licenses/>.
37 extern const struct generic_mapping file_generic_mapping;
38 extern bool global_client_failed_oplock_break;
40 struct deferred_open_record {
41 bool delayed_for_oplocks;
42 bool failed; /* added for onefs_oplocks */
46 static NTSTATUS onefs_create_file_unixpath(connection_struct *conn,
47 struct smb_request *req,
50 uint32_t share_access,
51 uint32_t create_disposition,
52 uint32_t create_options,
53 uint32_t file_attributes,
54 uint32_t oplock_request,
55 uint64_t allocation_size,
56 struct security_descriptor *sd,
57 struct ea_list *ea_list,
59 files_struct **result,
61 SMB_STRUCT_STAT *psbuf);
63 /****************************************************************************
65 ****************************************************************************/
67 static NTSTATUS onefs_open_file(files_struct *fsp,
68 connection_struct *conn,
69 struct smb_request *req,
70 const char *parent_dir,
73 SMB_STRUCT_STAT *psbuf,
77 uint32 open_access_mask,
81 uint32 create_options,
82 uint32_t new_dos_attributes,
83 struct security_descriptor *sd,
86 NTSTATUS status = NT_STATUS_OK;
87 int accmode = (flags & O_ACCMODE);
88 int local_flags = flags;
89 bool file_existed = VALID_STAT(*psbuf);
95 /* Check permissions */
98 * This code was changed after seeing a client open request
99 * containing the open mode of (DENY_WRITE/read-only) with
100 * the 'create if not exist' bit set. The previous code
101 * would fail to open the file read only on a read-only share
102 * as it was checking the flags parameter directly against O_RDONLY,
103 * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
107 if (!CAN_WRITE(conn)) {
108 /* It's a read-only share - fail if we wanted to write. */
109 if(accmode != O_RDONLY) {
110 DEBUG(3,("Permission denied opening %s\n", path));
111 return NT_STATUS_ACCESS_DENIED;
112 } else if(flags & O_CREAT) {
113 /* We don't want to write - but we must make sure that
114 O_CREAT doesn't create the file if we have write
115 access into the directory.
118 local_flags &= ~O_CREAT;
123 * This little piece of insanity is inspired by the
124 * fact that an NT client can open a file for O_RDONLY,
125 * but set the create disposition to FILE_EXISTS_TRUNCATE.
126 * If the client *can* write to the file, then it expects to
127 * truncate the file, even though it is opening for readonly.
128 * Quicken uses this stupid trick in backup file creation...
129 * Thanks *greatly* to "David W. Chapman Jr." <dwcjr@inethouston.net>
130 * for helping track this one down. It didn't bite us in 2.0.x
131 * as we always opened files read-write in that release. JRA.
134 if ((accmode == O_RDONLY) && ((flags & O_TRUNC) == O_TRUNC)) {
135 DEBUG(10,("onefs_open_file: truncate requested on read-only "
136 "open for file %s\n", path));
137 local_flags = (flags & ~O_ACCMODE)|O_RDWR;
140 #if defined(O_NONBLOCK) && defined(S_ISFIFO)
142 * We would block on opening a FIFO with no one else on the
143 * other end. Do what we used to do and add O_NONBLOCK to the
147 if (file_existed && S_ISFIFO(psbuf->st_mode)) {
148 local_flags |= O_NONBLOCK;
152 /* Don't create files with Microsoft wildcard characters. */
155 * wildcard characters are allowed in stream names
156 * only test the basefilename
158 wild = fsp->base_fsp->fsp_name;
162 if ((local_flags & O_CREAT) && !file_existed &&
165 * XXX: may need to remvoe this return...
167 * We dont think this check needs to exist. All it does is
168 * block creating files with Microsoft wildcards, which is
169 * fine if the creation originated from NFS or locally and
170 * then was copied via Samba.
172 DEBUG(1, ("onefs_open_file: creating file with wildcard: %s\n",
174 return NT_STATUS_OBJECT_NAME_INVALID;
177 /* Actually do the open */
181 * Never follow symlinks on a POSIX client. The
182 * client should be doing this.
185 if (fsp->posix_open || !lp_symlinks(SNUM(conn))) {
189 /* Don't request an oplock if oplocks are turned off for the
191 if (!lp_oplocks(SNUM(conn)))
194 fsp->fh->fd = onefs_sys_create_file(conn,
209 if (fsp->fh->fd == -1) {
210 if (errno == EMFILE) {
211 static time_t last_warned = 0L;
213 if (time((time_t *) NULL) > last_warned) {
214 DEBUG(0, ("Too many open files, unable "
215 "to open more! smbd's max "
216 "open files = %d, also check "
217 "sysctl kern.maxfiles and "
218 "sysctl kern.maxfilesperproc\n",
219 lp_max_open_files()));
220 last_warned = time((time_t *) NULL);
224 status = map_nt_error_from_unix(errno);
225 DEBUG(3,("Error opening file %s (%s) (local_flags=%d) "
227 path,nt_errstr(status),local_flags,flags));
231 if ((local_flags & O_CREAT) && !file_existed) {
233 /* Inherit the ACL if required */
234 if (lp_inherit_perms(SNUM(conn))) {
235 inherit_access_posix_acl(conn, parent_dir, path,
239 /* Change the owner if required. */
240 if (lp_inherit_owner(SNUM(conn))) {
241 change_file_owner_to_parent(conn, parent_dir,
245 notify_fname(conn, NOTIFY_ACTION_ADDED,
246 FILE_NOTIFY_CHANGE_FILE_NAME, path);
252 if (fsp->fh->fd == -1) {
253 ret = SMB_VFS_STAT(conn, path, psbuf);
255 ret = SMB_VFS_FSTAT(fsp, psbuf);
256 /* If we have an fd, this stat should succeed. */
258 DEBUG(0,("Error doing fstat on open file %s "
259 "(%s)\n", path,strerror(errno) ));
263 /* For a non-io open, this stat failing means file not found. JRA */
265 status = map_nt_error_from_unix(errno);
272 * POSIX allows read-only opens of directories. We don't
273 * want to do this (we use a different code path for this)
274 * so catch a directory open and return an EISDIR. JRA.
277 if(S_ISDIR(psbuf->st_mode)) {
280 return NT_STATUS_FILE_IS_A_DIRECTORY;
283 fsp->mode = psbuf->st_mode;
284 fsp->file_id = vfs_file_id_from_sbuf(conn, psbuf);
285 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
286 fsp->file_pid = req ? req->smbpid : 0;
287 fsp->can_lock = True;
288 fsp->can_read = (access_mask & (FILE_READ_DATA)) ? True : False;
289 if (!CAN_WRITE(conn)) {
290 fsp->can_write = False;
292 fsp->can_write = (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ?
295 fsp->print_file = False;
296 fsp->modified = False;
297 fsp->sent_oplock_break = NO_BREAK_SENT;
298 fsp->is_directory = False;
299 if (conn->aio_write_behind_list &&
300 is_in_path(path, conn->aio_write_behind_list, conn->case_sensitive)) {
301 fsp->aio_write_behind = True;
304 string_set(&fsp->fsp_name, path);
305 fsp->wcp = NULL; /* Write cache pointer. */
307 DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
308 conn->server_info->unix_name,
310 BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
311 conn->num_files_open));
317 /****************************************************************************
318 Handle the 1 second delay in returning a SHARING_VIOLATION error.
319 ****************************************************************************/
321 static void defer_open(struct share_mode_lock *lck,
322 struct timeval request_time,
323 struct timeval timeout,
324 struct smb_request *req,
325 struct deferred_open_record *state)
331 for (i=0; i<lck->num_share_modes; i++) {
332 struct share_mode_entry *e = &lck->share_modes[i];
334 if (!is_deferred_open_entry(e)) {
338 if (procid_is_me(&e->pid) && (e->op_mid == req->mid)) {
339 DEBUG(0, ("Trying to defer an already deferred "
340 "request: mid=%d, exiting\n", req->mid));
341 exit_server("attempt to defer a deferred request");
345 /* End paranoia check */
347 DEBUG(10,("defer_open_sharing_error: time [%u.%06u] adding deferred "
348 "open entry for mid %u\n",
349 (unsigned int)request_time.tv_sec,
350 (unsigned int)request_time.tv_usec,
351 (unsigned int)req->mid));
353 if (!push_deferred_smb_message(req, request_time, timeout,
354 (char *)state, sizeof(*state))) {
355 exit_server("push_deferred_smb_message failed");
357 add_deferred_open(lck, req->mid, request_time, state->id);
360 * Push the MID of this packet on the signing queue.
361 * We only do this once, the first time we push the packet
362 * onto the deferred open queue, as this has a side effect
363 * of incrementing the response sequence number.
366 srv_defer_sign_response(req->mid);
369 static void schedule_defer_open(struct share_mode_lock *lck,
370 struct timeval request_time,
371 struct smb_request *req)
373 struct deferred_open_record state;
375 /* This is a relative time, added to the absolute
376 request_time value to get the absolute timeout time.
377 Note that if this is the second or greater time we enter
378 this codepath for this particular request mid then
379 request_time is left as the absolute time of the *first*
380 time this request mid was processed. This is what allows
381 the request to eventually time out. */
383 struct timeval timeout;
385 /* Normally the smbd we asked should respond within
386 * OPLOCK_BREAK_TIMEOUT seconds regardless of whether
387 * the client did, give twice the timeout as a safety
388 * measure here in case the other smbd is stuck
391 timeout = timeval_set(OPLOCK_BREAK_TIMEOUT*2, 0);
393 /* Nothing actually uses state.delayed_for_oplocks
394 but it's handy to differentiate in debug messages
395 between a 30 second delay due to oplock break, and
396 a 1 second delay for share mode conflicts. */
398 state.delayed_for_oplocks = True;
399 state.failed = False;
402 if (!request_timed_out(request_time, timeout)) {
403 defer_open(lck, request_time, timeout, req, &state);
407 /****************************************************************************
408 Open a file with a share mode. Passed in an already created files_struct.
409 ****************************************************************************/
410 NTSTATUS onefs_open_file_ntcreate(connection_struct *conn,
411 struct smb_request *req,
415 uint32 create_disposition,
416 uint32 create_options,
417 uint32 new_dos_attributes,
419 struct security_descriptor *sd,
422 SMB_STRUCT_STAT *psbuf)
426 bool file_existed = VALID_STAT(*psbuf);
427 bool def_acl = False;
428 bool posix_open = False;
429 bool new_file_created = False;
431 mode_t new_unx_mode = (mode_t)0;
432 mode_t unx_mode = (mode_t)0;
434 uint32 existing_dos_attributes = 0;
435 struct pending_message_list *pml = NULL;
436 struct timeval request_time = timeval_zero();
437 struct share_mode_lock *lck = NULL;
438 uint32 open_access_mask = access_mask;
444 uint64 oplock_waiter;
445 uint32 createfile_attributes = 0;
451 * Printers are handled completely differently.
452 * Most of the passed parameters are ignored.
456 *pinfo = FILE_WAS_CREATED;
459 DEBUG(10, ("onefs_open_file_ntcreate: printer open fname=%s\n",
462 return print_fsp_open(req, conn, fname, req->vuid, fsp, psbuf);
465 if (!parent_dirname(talloc_tos(), fname, &parent_dir, &newname)) {
466 return NT_STATUS_NO_MEMORY;
469 if (new_dos_attributes & FILE_FLAG_POSIX_SEMANTICS) {
471 unx_mode = (mode_t)(new_dos_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
472 new_dos_attributes = 0;
474 /* We add aARCH to this as this mode is only used if the file is
476 unx_mode = unix_mode(conn, new_dos_attributes | aARCH, fname,
480 DEBUG(10,("onefs_open_file_ntcreate: fname=%s, dos_attrs=0x%x "
481 "access_mask=0x%x share_access=0x%x "
482 "create_disposition = 0x%x create_options=0x%x "
483 "unix mode=0%o oplock_request=0x%x\n",
484 fname, new_dos_attributes, access_mask, share_access,
485 create_disposition, create_options, unx_mode,
488 if ((req == NULL) && ((oplock_request & INTERNAL_OPEN_ONLY) == 0)) {
489 DEBUG(0, ("No smb request but not an internal only open!\n"));
490 return NT_STATUS_INTERNAL_ERROR;
494 * Only non-internal opens can be deferred at all
498 && ((pml = get_open_deferred_message(req->mid)) != NULL)) {
499 struct deferred_open_record *state =
500 (struct deferred_open_record *)pml->private_data.data;
502 /* Remember the absolute time of the original
503 request with this mid. We'll use it later to
504 see if this has timed out. */
506 request_time = pml->request_time;
508 /* Remove the deferred open entry under lock. */
509 lck = get_share_mode_lock(talloc_tos(), state->id, NULL, NULL,
512 DEBUG(0, ("could not get share mode lock\n"));
514 del_deferred_open_entry(lck, req->mid);
518 /* Ensure we don't reprocess this message. */
519 remove_deferred_open_smb_message(req->mid);
522 * When receiving a semlock_async_failure message, the
523 * deferred open will be marked as "failed". Returning
527 DEBUG(0, ("onefs_open_file_ntcreate: "
528 "semlock_async_failure detected!\n"));
529 return NT_STATUS_INTERNAL_ERROR;
533 status = check_name(conn, fname);
534 if (!NT_STATUS_IS_OK(status)) {
539 new_dos_attributes &= SAMBA_ATTRIBUTES_MASK;
541 existing_dos_attributes = dos_mode(conn, fname, psbuf);
545 /* Setup dos_attributes to be set by ifs_createfile */
546 if (lp_store_dos_attributes(SNUM(conn))) {
547 createfile_attributes = (new_dos_attributes | aARCH) &
548 ~(FILE_ATTRIBUTE_NONINDEXED | FILE_ATTRIBUTE_COMPRESSED);
551 /* Ignore oplock requests if oplocks are disabled. */
552 if (!lp_oplocks(SNUM(conn)) || global_client_failed_oplock_break ||
553 IS_VETO_OPLOCK_PATH(conn, fname)) {
554 /* Mask off everything except the private Samba bits. */
555 oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
558 /* this is for OS/2 long file names - say we don't support them */
559 if (!lp_posix_pathnames() && strstr(fname,".+,;=[].")) {
560 /* OS/2 Workplace shell fix may be main code stream in a later
562 DEBUG(5,("onefs_open_file_ntcreate: OS/2 long filenames are "
563 "not supported.\n"));
564 if (use_nt_status()) {
565 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
567 return NT_STATUS_DOS(ERRDOS, ERRcannotopen);
570 switch( create_disposition ) {
572 * Currently we're using FILE_SUPERSEDE as the same as
573 * FILE_OVERWRITE_IF but they really are
574 * different. FILE_SUPERSEDE deletes an existing file
575 * (requiring delete access) then recreates it.
579 * @todo: Clear all file attributes?
580 * http://www.osronline.com/article.cfm?article=302
581 * create if not exist, trunc if exist
583 * If file exists replace/overwrite. If file doesn't
586 flags2 |= (O_CREAT | O_TRUNC);
589 case FILE_OVERWRITE_IF:
590 /* If file exists replace/overwrite. If file doesn't
592 flags2 |= (O_CREAT | O_TRUNC);
596 /* If file exists open. If file doesn't exist error. */
598 DEBUG(5,("onefs_open_file_ntcreate: FILE_OPEN "
599 "requested for file %s and file "
600 "doesn't exist.\n", fname ));
602 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
607 /* If file exists overwrite. If file doesn't exist
610 DEBUG(5, ("onefs_open_file_ntcreate: "
611 "FILE_OVERWRITE requested for file "
612 "%s and file doesn't exist.\n",
615 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
621 /* If file exists error. If file doesn't exist
624 DEBUG(5, ("onefs_open_file_ntcreate: "
625 "FILE_CREATE requested for file %s "
626 "and file already exists.\n",
628 if (S_ISDIR(psbuf->st_mode)) {
633 return map_nt_error_from_unix(errno);
635 flags2 |= (O_CREAT|O_EXCL);
639 /* If file exists open. If file doesn't exist
645 return NT_STATUS_INVALID_PARAMETER;
648 /* Match attributes on file exists and overwrite. */
649 if (!posix_open && file_existed &&
650 ((create_disposition == FILE_OVERWRITE) ||
651 (create_disposition == FILE_OVERWRITE_IF))) {
652 if (!open_match_attributes(conn, fname,
653 existing_dos_attributes,
654 new_dos_attributes, psbuf->st_mode,
655 unx_mode, &new_unx_mode)) {
656 DEBUG(5, ("onefs_open_file_ntcreate: attributes "
657 "missmatch for file %s (%x %x) (0%o, 0%o)\n",
658 fname, existing_dos_attributes,
660 (unsigned int)psbuf->st_mode,
661 (unsigned int)unx_mode ));
663 return NT_STATUS_ACCESS_DENIED;
668 * OneFS understands MAXIMUM_ALLOWED_ACCESS, so only hack the
669 * access_mask, but leave the MAA for the actual open in
672 open_access_mask = access_mask;
673 if (open_access_mask & MAXIMUM_ALLOWED_ACCESS) {
674 access_mask |= FILE_GENERIC_ALL;
677 /* Convert GENERIC bits to specific bits. */
678 se_map_generic(&access_mask, &file_generic_mapping);
679 se_map_generic(&open_access_mask, &file_generic_mapping);
681 if ((flags2 & O_TRUNC) || (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
682 /* This will cause oplock breaks. */
683 open_access_mask |= FILE_WRITE_DATA;
686 DEBUG(10, ("onefs_open_file_ntcreate: fname=%s, after mapping "
687 "open_access_mask=%#x, access_mask=0x%x\n",
688 fname, open_access_mask, access_mask));
691 * Note that we ignore the append flag as append does not
692 * mean the same thing under DOS and Unix.
695 if ((access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ||
696 (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
699 * DENY_DOS opens are always underlying read-write on the
700 * file handle, no matter what the requested access mask
701 * says. Stock samba just sets the flags, but since
702 * ifs_createfile uses the access_mask, it must be updated as
703 * well. This allows BASE-DENY* to pass.
705 if (create_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS) {
707 DEBUG(10,("onefs_open_file_ntcreate: deny_dos: "
708 "Adding O_RDWR to flags "
709 "(0x%x) and some READ bits to "
710 "open_access_mask (0x%x)\n",
711 flags, open_access_mask));
714 open_access_mask |= (FILE_READ_ATTRIBUTES |
715 FILE_READ_DATA | FILE_READ_EA | FILE_EXECUTE);
717 } else if (access_mask & (FILE_READ_ATTRIBUTES |
729 /* Currently we only look at FILE_WRITE_THROUGH for create options. */
731 if ((create_options & FILE_WRITE_THROUGH) &&
732 lp_strict_sync(SNUM(conn))) {
737 if (posix_open && (access_mask & FILE_APPEND_DATA)) {
741 if (!posix_open && !CAN_WRITE(conn)) {
743 * We should really return a permission denied error if either
744 * O_CREAT or O_TRUNC are set, but for compatibility with
745 * older versions of Samba we just AND them out.
747 flags2 &= ~(O_CREAT|O_TRUNC);
749 /* Deny DELETE_ACCESS explicitly if the share is read only. */
750 if (access_mask & DELETE_ACCESS) {
751 return map_nt_error_from_unix(EACCES);
755 /* Ensure we can't write on a read-only share or file. */
756 if (flags != O_RDONLY && file_existed &&
757 (!CAN_WRITE(conn) || IS_DOS_READONLY(existing_dos_attributes))) {
758 DEBUG(5, ("onefs_open_file_ntcreate: write access requested "
759 "for file %s on read only %s\n",
760 fname, !CAN_WRITE(conn) ? "share" : "file" ));
762 return NT_STATUS_ACCESS_DENIED;
765 DEBUG(10, ("fsp = %p\n", fsp));
767 fsp->file_id = vfs_file_id_from_sbuf(conn, psbuf);
768 fsp->share_access = share_access;
769 fsp->fh->private_options = create_options;
770 fsp->access_mask = open_access_mask; /* We change this to the
771 * requested access_mask after
772 * the open is done. */
773 fsp->posix_open = posix_open;
775 /* Ensure no SAMBA_PRIVATE bits can be set. */
776 fsp->oplock_type = (oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK);
778 if (timeval_is_zero(&request_time)) {
779 request_time = fsp->open_time;
783 struct timespec old_write_time = get_mtimespec(psbuf);
784 id = vfs_file_id_from_sbuf(conn, psbuf);
786 lck = get_share_mode_lock(talloc_tos(), id,
788 fname, &old_write_time);
791 DEBUG(0, ("Could not get share mode lock\n"));
792 return NT_STATUS_SHARING_VIOLATION;
795 if (lck->delete_on_close) {
796 /* DELETE_PENDING is not deferred for a second */
798 return NT_STATUS_DELETE_PENDING;
802 SMB_ASSERT(!file_existed || (lck != NULL));
805 * Ensure we pay attention to default ACLs on directories. May be
806 * neccessary depending on ACL policies.
808 if ((flags2 & O_CREAT) && lp_inherit_acls(SNUM(conn)) &&
809 (def_acl = directory_has_default_acl(conn, parent_dir))) {
813 DEBUG(4,("calling onefs_open_file with flags=0x%X flags2=0x%X "
814 "mode=0%o, access_mask = 0x%x, open_access_mask = 0x%x\n",
815 (unsigned int)flags, (unsigned int)flags2,
816 (unsigned int)unx_mode, (unsigned int)access_mask,
817 (unsigned int)open_access_mask));
819 oplock_waiter = 1; //ifs_oplock_wait_record(mid);
821 if (oplock_waiter == 0) {
822 return NT_STATUS_NO_MEMORY;
826 status = onefs_open_file(fsp,
841 createfile_attributes,
845 if (!NT_STATUS_IS_OK(status)) {
847 /* OneFS Oplock Handling */
848 if (errno == EINPROGRESS) {
852 struct deferred_open_record state;
853 struct timespec old_write_time;
855 old_write_time = get_mtimespec(psbuf);
857 DEBUG(3, ("Someone created file %s with an "
858 "oplock after we looked: Retrying\n",
861 * We hit the race that when we did the stat
862 * on the file it did not exist, and someone
863 * has created it in between the stat and the
864 * open_file() call. Just retry immediately.
866 id = vfs_file_id_from_sbuf(conn, psbuf);
867 if (!(lck = get_share_mode_lock(talloc_tos(),
868 id, conn->connectpath, fname,
873 DEBUG(0, ("onefs_open_file_ntcreate: "
874 "Could not get share mode "
875 "lock for %s\n", fname));
876 status = NT_STATUS_SHARING_VIOLATION;
877 goto cleanup_destroy;
880 state.delayed_for_oplocks = False;
884 defer_open(lck, request_time,
885 timeval_zero(), req, &state);
887 goto cleanup_destroy;
889 /* Waiting for an oplock */
891 schedule_defer_open(lck, request_time, req);
895 /* Check for a sharing violation */
896 if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
897 uint32 can_access_mask;
898 bool can_access = True;
900 /* Check if this can be done with the deny_dos and fcb
903 /* Try to find dup fsp if possible. */
905 (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
906 NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
909 DEBUG(0, ("DOS open without an SMB "
911 status = NT_STATUS_INTERNAL_ERROR;
912 goto cleanup_destroy;
915 /* Use the client requested access mask here,
916 * not the one we open with. */
917 status = fcb_or_dos_open(req,
928 if (NT_STATUS_IS_OK(status)) {
931 *pinfo = FILE_WAS_OPENED;
933 status = NT_STATUS_OK;
939 * This next line is a subtlety we need for
940 * MS-Access. If a file open will fail due to share
941 * permissions and also for security (access) reasons,
942 * we need to return the access failed error, not the
943 * share error. We can't open the file due to kernel
944 * oplock deadlock (it's possible we failed above on
945 * the open_mode_check()) so use a userspace check.
948 if (flags & O_RDWR) {
949 can_access_mask = FILE_READ_DATA|FILE_WRITE_DATA;
950 } else if (flags & O_WRONLY) {
951 can_access_mask = FILE_WRITE_DATA;
953 can_access_mask = FILE_READ_DATA;
956 if (((can_access_mask & FILE_WRITE_DATA) && !CAN_WRITE(conn)) ||
957 !can_access_file_data(conn,fname,psbuf,can_access_mask)) {
962 * If we're returning a share violation, ensure we
963 * cope with the braindead 1 second delay.
965 if (!(oplock_request & INTERNAL_OPEN_ONLY) &&
966 lp_defer_sharing_violations()) {
967 struct timeval timeout;
968 struct deferred_open_record state;
971 /* this is a hack to speed up torture tests
973 timeout_usecs = lp_parm_int(SNUM(conn),
975 SHARING_VIOLATION_USEC_WAIT);
977 /* This is a relative time, added to the
978 absolute request_time value to get the
979 absolute timeout time. Note that if this
980 is the second or greater time we enter this
981 codepath for this particular request mid
982 then request_time is left as the absolute
983 time of the *first* time this request mid
984 was processed. This is what allows the
985 request to eventually time out. */
987 timeout = timeval_set(0, timeout_usecs);
989 /* Nothing actually uses
990 state.delayed_for_oplocks but it's handy to
991 differentiate in debug messages between a
992 30 second delay due to oplock break, and a
993 1 second delay for share mode conflicts. */
995 state.delayed_for_oplocks = False;
997 state.failed = false;
1000 && !request_timed_out(request_time,
1002 defer_open(lck, request_time, timeout,
1009 * We have detected a sharing violation here
1010 * so return the correct error code
1012 status = NT_STATUS_SHARING_VIOLATION;
1014 status = NT_STATUS_ACCESS_DENIED;
1017 goto cleanup_destroy;
1021 * Normal error, for example EACCES
1024 //destroy_ifs_callback_record(oplock_waiter);
1030 fsp->oplock_type = granted_oplock;
1032 /* XXX uncomment for oplocks */
1033 //ifs_set_oplock_callback(oplock_waiter, fsp);
1034 //fsp->oplock_callback_id = oplock_waiter;
1036 if (!file_existed) {
1037 struct timespec old_write_time = get_mtimespec(psbuf);
1039 * Deal with the race condition where two smbd's detect the
1040 * file doesn't exist and do the create at the same time. One
1041 * of them will win and set a share mode, the other (ie. this
1042 * one) should check if the requested share mode for this
1043 * create is allowed.
1047 * Now the file exists and fsp is successfully opened,
1048 * fsp->dev and fsp->inode are valid and should replace the
1049 * dev=0,inode=0 from a non existent file. Spotted by
1050 * Nadav Danieli <nadavd@exanet.com>. JRA.
1055 lck = get_share_mode_lock(talloc_tos(), id,
1057 fname, &old_write_time);
1060 DEBUG(0, ("onefs_open_file_ntcreate: Could not get "
1061 "share mode lock for %s\n", fname));
1063 return NT_STATUS_SHARING_VIOLATION;
1066 if (lck->delete_on_close) {
1067 status = NT_STATUS_DELETE_PENDING;
1070 if (!NT_STATUS_IS_OK(status)) {
1071 struct deferred_open_record state;
1075 state.delayed_for_oplocks = False;
1078 /* Do it all over again immediately. In the second
1079 * round we will find that the file existed and handle
1080 * the DELETE_PENDING and FCB cases correctly. No need
1081 * to duplicate the code here. Essentially this is a
1082 * "goto top of this function", but don't tell
1086 defer_open(lck, request_time, timeval_zero(),
1094 * We exit this block with the share entry *locked*.....
1099 SMB_ASSERT(lck != NULL);
1101 /* note that we ignore failure for the following. It is
1102 basically a hack for NFS, and NFS will never set one of
1103 these only read them. Nobody but Samba can ever set a deny
1104 mode and we have already checked our more authoritative
1105 locking database for permission to set this deny mode. If
1106 the kernel refuses the operations then the kernel is wrong.
1107 note that GPFS supports it as well - jmcd */
1109 if (fsp->fh->fd != -1) {
1110 ret_flock = SMB_VFS_KERNEL_FLOCK(fsp, share_access);
1111 if(ret_flock == -1 ){
1115 return NT_STATUS_SHARING_VIOLATION;
1120 * At this point onwards, we can guarentee that the share entry
1121 * is locked, whether we created the file or not, and that the
1122 * deny mode is compatible with all current opens.
1125 /* Record the options we were opened with. */
1126 fsp->share_access = share_access;
1127 fsp->fh->private_options = create_options;
1129 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
1131 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
1134 /* stat opens on existing files don't get oplocks. */
1135 if (is_stat_open(open_access_mask)) {
1136 fsp->oplock_type = NO_OPLOCK;
1139 if (!(flags2 & O_TRUNC)) {
1140 info = FILE_WAS_OPENED;
1142 info = FILE_WAS_OVERWRITTEN;
1145 info = FILE_WAS_CREATED;
1153 * Setup the oplock info in both the shared memory and
1157 if ((fsp->oplock_type != NO_OPLOCK) &&
1158 (fsp->oplock_type != FAKE_LEVEL_II_OPLOCK)) {
1159 if (!set_file_oplock(fsp, fsp->oplock_type)) {
1160 /* Could not get the kernel oplock */
1161 fsp->oplock_type = NO_OPLOCK;
1165 if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED ||
1166 info == FILE_WAS_SUPERSEDED) {
1167 new_file_created = True;
1170 set_share_mode(lck, fsp, conn->server_info->utok.uid, 0,
1173 /* Handle strange delete on close create semantics. */
1174 if (create_options & FILE_DELETE_ON_CLOSE) {
1175 status = can_set_delete_on_close(fsp, True, new_dos_attributes);
1177 if (!NT_STATUS_IS_OK(status)) {
1178 /* Remember to delete the mode we just added. */
1179 del_share_mode(lck, fsp);
1184 /* Note that here we set the *inital* delete on close flag,
1185 not the regular one. The magic gets handled in close. */
1186 fsp->initial_delete_on_close = True;
1190 * Take care of inherited ACLs on created files - if default ACL not
1192 * May be necessary depending on acl policies.
1194 if (!posix_open && !file_existed && !def_acl && !(VALID_STAT(*psbuf)
1195 && (psbuf->st_flags & SF_HASNTFSACL))) {
1197 int saved_errno = errno; /* We might get ENOSYS in the next
1200 if (SMB_VFS_FCHMOD_ACL(fsp, unx_mode) == -1 &&
1202 errno = saved_errno; /* Ignore ENOSYS */
1205 } else if (new_unx_mode) {
1209 /* Attributes need changing. File already existed. */
1212 int saved_errno = errno; /* We might get ENOSYS in the
1214 ret = SMB_VFS_FCHMOD_ACL(fsp, new_unx_mode);
1216 if (ret == -1 && errno == ENOSYS) {
1217 errno = saved_errno; /* Ignore ENOSYS */
1219 DEBUG(5, ("onefs_open_file_ntcreate: reset "
1220 "attributes of file %s to 0%o\n",
1221 fname, (unsigned int)new_unx_mode));
1222 ret = 0; /* Don't do the fchmod below. */
1227 (SMB_VFS_FCHMOD(fsp, new_unx_mode) == -1))
1228 DEBUG(5, ("onefs_open_file_ntcreate: failed to reset "
1229 "attributes of file %s to 0%o\n",
1230 fname, (unsigned int)new_unx_mode));
1233 /* If this is a successful open, we must remove any deferred open
1236 del_deferred_open_entry(lck, req->mid);
1240 return NT_STATUS_OK;
1244 /****************************************************************************
1245 Open a directory from an NT SMB call.
1246 ****************************************************************************/
1247 static NTSTATUS onefs_open_directory(connection_struct *conn,
1248 struct smb_request *req,
1251 uint32 share_access,
1252 uint32 create_disposition,
1253 uint32 create_options,
1254 uint32 file_attributes,
1255 struct security_descriptor *sd,
1256 files_struct **result,
1258 SMB_STRUCT_STAT *psbuf)
1260 files_struct *fsp = NULL;
1261 struct share_mode_lock *lck = NULL;
1263 struct timespec mtimespec;
1266 const char *dirname;
1267 bool posix_open = false;
1268 uint32 create_flags = 0;
1269 uint32 mode = lp_dir_mask(SNUM(conn));
1271 DEBUG(5, ("onefs_open_directory: opening directory %s, "
1272 "access_mask = 0x%x, "
1273 "share_access = 0x%x create_options = 0x%x, "
1274 "create_disposition = 0x%x, file_attributes = 0x%x\n",
1275 fname, (unsigned int)access_mask, (unsigned int)share_access,
1276 (unsigned int)create_options, (unsigned int)create_disposition,
1277 (unsigned int)file_attributes));
1279 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
1280 (conn->fs_capabilities & FILE_NAMED_STREAMS) &&
1281 is_ntfs_stream_name(fname)) {
1282 DEBUG(2, ("onefs_open_directory: %s is a stream name!\n", fname));
1283 return NT_STATUS_NOT_A_DIRECTORY;
1286 switch (create_disposition) {
1288 /* If directory exists open. If directory doesn't
1291 info = FILE_WAS_OPENED;
1294 /* If directory exists error. If directory doesn't
1296 create_flags = O_CREAT | O_EXCL;
1297 info = FILE_WAS_CREATED;
1300 /* If directory exists open. If directory doesn't
1303 /* Note: in order to return whether the directory was
1304 * opened or created, we first try to open and then try
1307 info = FILE_WAS_OPENED;
1309 case FILE_SUPERSEDE:
1310 case FILE_OVERWRITE:
1311 case FILE_OVERWRITE_IF:
1313 DEBUG(5, ("onefs_open_directory: invalid "
1314 "create_disposition 0x%x for directory %s\n",
1315 (unsigned int)create_disposition, fname));
1316 return NT_STATUS_INVALID_PARAMETER;
1320 * Check for write access to the share. Done in mkdir_internal() in
1323 if (!CAN_WRITE(conn) && (create_flags & O_CREAT)) {
1324 return NT_STATUS_ACCESS_DENIED;
1327 /* Get parent dirname */
1328 if (!parent_dirname(talloc_tos(), fname, &parent_dir, &dirname)) {
1329 return NT_STATUS_NO_MEMORY;
1332 if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
1334 mode = (mode_t)(file_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
1335 file_attributes = 0;
1337 mode = unix_mode(conn, aDIR, fname, parent_dir);
1341 * The NONINDEXED and COMPRESSED bits seem to always be cleared on
1342 * directories, no matter if you specify that they should be set.
1345 ~(FILE_ATTRIBUTE_NONINDEXED | FILE_ATTRIBUTE_COMPRESSED);
1347 status = file_new(req, conn, &fsp);
1348 if(!NT_STATUS_IS_OK(status)) {
1353 * Actual open with retry magic to handle FILE_OPEN_IF which is
1354 * unique because the kernel won't tell us if the file was opened or
1358 fsp->fh->fd = onefs_sys_create_file(conn,
1365 create_flags | O_DIRECTORY,
1373 if (fsp->fh->fd == -1) {
1374 DEBUG(3, ("Error opening %s. Errno=%d (%s).\n", fname, errno,
1376 SMB_ASSERT(errno != EINPROGRESS);
1378 if (create_disposition == FILE_OPEN_IF) {
1379 if (errno == ENOENT) {
1380 /* Try again, creating it this time. */
1381 create_flags = O_CREAT | O_EXCL;
1382 info = FILE_WAS_CREATED;
1384 } else if (errno == EEXIST) {
1385 /* Uggh. Try again again. */
1387 info = FILE_WAS_OPENED;
1392 /* Error cases below: */
1393 file_free(req, fsp);
1395 if ((errno == ENOENT) && (create_disposition == FILE_OPEN)) {
1396 DEBUG(5,("onefs_open_directory: FILE_OPEN requested "
1397 "for directory %s and it doesn't "
1398 "exist.\n", fname ));
1399 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1400 } else if ((errno == EEXIST) &&
1401 (create_disposition == FILE_CREATE)) {
1402 DEBUG(5,("onefs_open_directory: FILE_CREATE "
1403 "requested for directory %s and it "
1404 "already exists.\n", fname ));
1405 return NT_STATUS_OBJECT_NAME_COLLISION;
1406 } else if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
1407 /* Catch sharing violations. */
1408 return NT_STATUS_SHARING_VIOLATION;
1411 return map_nt_error_from_unix(errno);
1414 if (info == FILE_WAS_CREATED) {
1416 /* Pulled from mkdir_internal() */
1417 if (SMB_VFS_LSTAT(conn, fname, psbuf) == -1) {
1418 DEBUG(2, ("Could not stat directory '%s' just "
1419 "created: %s\n",fname, strerror(errno)));
1420 return map_nt_error_from_unix(errno);
1423 if (!S_ISDIR(psbuf->st_mode)) {
1424 DEBUG(0, ("Directory just '%s' created is not a "
1425 "directory\n", fname));
1426 return NT_STATUS_ACCESS_DENIED;
1431 * Check if high bits should have been set, then (if
1432 * bits are missing): add them. Consider bits
1433 * automagically set by UNIX, i.e. SGID bit from
1436 if (mode & ~(S_IRWXU|S_IRWXG|S_IRWXO) &&
1437 (mode & ~psbuf->st_mode)) {
1438 SMB_VFS_CHMOD(conn, fname, (psbuf->st_mode |
1439 (mode & ~psbuf->st_mode)));
1443 /* Change the owner if required. */
1444 if (lp_inherit_owner(SNUM(conn))) {
1445 change_dir_owner_to_parent(conn, parent_dir, fname,
1449 notify_fname(conn, NOTIFY_ACTION_ADDED,
1450 FILE_NOTIFY_CHANGE_DIR_NAME, fname);
1453 /* Stat the fd for Samba bookkeeping. */
1454 if(SMB_VFS_FSTAT(fsp, psbuf) != 0) {
1456 file_free(req, fsp);
1457 return map_nt_error_from_unix(errno);
1460 /* Setup the files_struct for it. */
1461 fsp->mode = psbuf->st_mode;
1462 fsp->file_id = vfs_file_id_from_sbuf(conn, psbuf);
1463 fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
1464 fsp->file_pid = req ? req->smbpid : 0;
1465 fsp->can_lock = False;
1466 fsp->can_read = False;
1467 fsp->can_write = False;
1469 fsp->share_access = share_access;
1470 fsp->fh->private_options = create_options;
1472 * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
1474 fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
1475 fsp->print_file = False;
1476 fsp->modified = False;
1477 fsp->oplock_type = NO_OPLOCK;
1478 fsp->sent_oplock_break = NO_BREAK_SENT;
1479 fsp->is_directory = True;
1480 fsp->posix_open = posix_open;
1482 string_set(&fsp->fsp_name,fname);
1484 mtimespec = get_mtimespec(psbuf);
1487 * Still set the samba share mode lock for correct delete-on-close
1488 * semantics and to make smbstatus more useful.
1490 lck = get_share_mode_lock(talloc_tos(), fsp->file_id,
1495 DEBUG(0, ("onefs_open_directory: Could not get share mode "
1496 "lock for %s\n", fname));
1498 file_free(req, fsp);
1499 return NT_STATUS_SHARING_VIOLATION;
1502 if (lck->delete_on_close) {
1505 file_free(req, fsp);
1506 return NT_STATUS_DELETE_PENDING;
1509 set_share_mode(lck, fsp, conn->server_info->utok.uid, 0, NO_OPLOCK);
1512 * For directories the delete on close bit at open time seems
1513 * always to be honored on close... See test 19 in Samba4 BASE-DELETE.
1515 if (create_options & FILE_DELETE_ON_CLOSE) {
1516 status = can_set_delete_on_close(fsp, True, 0);
1517 if (!NT_STATUS_IS_OK(status) &&
1518 !NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
1521 file_free(req, fsp);
1525 if (NT_STATUS_IS_OK(status)) {
1526 /* Note that here we set the *inital* delete on close flag,
1527 not the regular one. The magic gets handled in close. */
1528 fsp->initial_delete_on_close = True;
1539 return NT_STATUS_OK;
1543 * If a main file is opened for delete, all streams need to be checked for
1544 * !FILE_SHARE_DELETE. Do this by opening with DELETE_ACCESS.
1545 * If that works, delete them all by setting the delete on close and close.
1548 static NTSTATUS open_streams_for_delete(connection_struct *conn,
1551 struct stream_struct *stream_info;
1552 files_struct **streams;
1554 unsigned int num_streams;
1555 TALLOC_CTX *frame = talloc_stackframe();
1558 status = SMB_VFS_STREAMINFO(conn, NULL, fname, talloc_tos(),
1559 &num_streams, &stream_info);
1561 if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_IMPLEMENTED)
1562 || NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
1563 DEBUG(10, ("no streams around\n"));
1565 return NT_STATUS_OK;
1568 if (!NT_STATUS_IS_OK(status)) {
1569 DEBUG(10, ("SMB_VFS_STREAMINFO failed: %s\n",
1570 nt_errstr(status)));
1574 DEBUG(10, ("open_streams_for_delete found %d streams\n",
1577 if (num_streams == 0) {
1579 return NT_STATUS_OK;
1582 streams = TALLOC_ARRAY(talloc_tos(), files_struct *, num_streams);
1583 if (streams == NULL) {
1584 DEBUG(0, ("talloc failed\n"));
1585 status = NT_STATUS_NO_MEMORY;
1589 for (i=0; i<num_streams; i++) {
1592 if (strequal(stream_info[i].name, "::$DATA")) {
1597 streamname = talloc_asprintf(talloc_tos(), "%s%s", fname,
1598 stream_info[i].name);
1600 if (streamname == NULL) {
1601 DEBUG(0, ("talloc_aprintf failed\n"));
1602 status = NT_STATUS_NO_MEMORY;
1606 status = onefs_create_file_unixpath
1609 streamname, /* fname */
1610 DELETE_ACCESS, /* access_mask */
1611 FILE_SHARE_READ | FILE_SHARE_WRITE
1612 | FILE_SHARE_DELETE, /* share_access */
1613 FILE_OPEN, /* create_disposition*/
1614 NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE, /* create_options */
1615 FILE_ATTRIBUTE_NORMAL, /* file_attributes */
1616 0, /* oplock_request */
1617 0, /* allocation_size */
1620 &streams[i], /* result */
1624 TALLOC_FREE(streamname);
1626 if (!NT_STATUS_IS_OK(status)) {
1627 DEBUG(10, ("Could not open stream %s: %s\n",
1628 streamname, nt_errstr(status)));
1634 * don't touch the variable "status" beyond this point :-)
1637 for (i -= 1 ; i >= 0; i--) {
1638 if (streams[i] == NULL) {
1642 DEBUG(10, ("Closing stream # %d, %s\n", i,
1643 streams[i]->fsp_name));
1644 close_file(NULL, streams[i], NORMAL_CLOSE);
1653 * Wrapper around onefs_open_file_ntcreate and onefs_open_directory.
1655 static NTSTATUS onefs_create_file_unixpath(connection_struct *conn,
1656 struct smb_request *req,
1658 uint32_t access_mask,
1659 uint32_t share_access,
1660 uint32_t create_disposition,
1661 uint32_t create_options,
1662 uint32_t file_attributes,
1663 uint32_t oplock_request,
1664 uint64_t allocation_size,
1665 struct security_descriptor *sd,
1666 struct ea_list *ea_list,
1667 files_struct **result,
1669 SMB_STRUCT_STAT *psbuf)
1671 SMB_STRUCT_STAT sbuf;
1672 int info = FILE_WAS_OPENED;
1673 files_struct *base_fsp = NULL;
1674 files_struct *fsp = NULL;
1677 DEBUG(10,("onefs_create_file_unixpath: access_mask = 0x%x "
1678 "file_attributes = 0x%x, share_access = 0x%x, "
1679 "create_disposition = 0x%x create_options = 0x%x "
1680 "oplock_request = 0x%x ea_list = 0x%p, sd = 0x%p, "
1682 (unsigned int)access_mask,
1683 (unsigned int)file_attributes,
1684 (unsigned int)share_access,
1685 (unsigned int)create_disposition,
1686 (unsigned int)create_options,
1687 (unsigned int)oplock_request,
1688 ea_list, sd, fname));
1690 if (create_options & FILE_OPEN_BY_FILE_ID) {
1691 status = NT_STATUS_NOT_SUPPORTED;
1695 if (create_options & NTCREATEX_OPTIONS_INVALID_PARAM_MASK) {
1696 status = NT_STATUS_INVALID_PARAMETER;
1701 oplock_request |= INTERNAL_OPEN_ONLY;
1704 if (psbuf != NULL) {
1708 if (SMB_VFS_STAT(conn, fname, &sbuf) == -1) {
1709 SET_STAT_INVALID(sbuf);
1713 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
1714 && (access_mask & DELETE_ACCESS)
1715 && !is_ntfs_stream_name(fname)) {
1717 * We can't open a file with DELETE access if any of the
1718 * streams is open without FILE_SHARE_DELETE
1720 status = open_streams_for_delete(conn, fname);
1722 if (!NT_STATUS_IS_OK(status)) {
1727 if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
1728 && is_ntfs_stream_name(fname)
1729 && (!(create_options & NTCREATEX_OPTIONS_PRIVATE_STREAM_DELETE))) {
1731 uint32 base_create_disposition;
1733 if (create_options & FILE_DIRECTORY_FILE) {
1734 status = NT_STATUS_NOT_A_DIRECTORY;
1738 status = split_ntfs_stream_name(talloc_tos(), fname,
1740 if (!NT_STATUS_IS_OK(status)) {
1741 DEBUG(10, ("onefs_create_file_unixpath: "
1742 "split_ntfs_stream_name failed: %s\n",
1743 nt_errstr(status)));
1747 SMB_ASSERT(!is_ntfs_stream_name(base)); /* paranoia.. */
1749 switch (create_disposition) {
1751 base_create_disposition = FILE_OPEN;
1754 base_create_disposition = FILE_OPEN_IF;
1758 status = onefs_create_file_unixpath(
1762 0, /* access_mask */
1765 FILE_SHARE_DELETE), /* share_access */
1766 base_create_disposition, /* create_disposition*/
1767 0, /* create_options */
1768 0, /* file_attributes */
1769 NO_OPLOCK, /* oplock_request */
1770 0, /* allocation_size */
1773 &base_fsp, /* result */
1777 if (!NT_STATUS_IS_OK(status)) {
1778 DEBUG(10, ("onefs_create_file_unixpath for base %s "
1779 "failed: %s\n", base, nt_errstr(status)));
1783 * we don't need to low level fd: This might conflict with
1789 /* Covert generic bits in the security descriptor. */
1791 security_acl_map_generic(sd->dacl, &file_generic_mapping);
1792 security_acl_map_generic(sd->sacl, &file_generic_mapping);
1796 * If it's a request for a directory open, deal with it separately.
1799 if (create_options & FILE_DIRECTORY_FILE) {
1801 if (create_options & FILE_NON_DIRECTORY_FILE) {
1802 status = NT_STATUS_INVALID_PARAMETER;
1806 /* Can't open a temp directory. IFS kit test. */
1807 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
1808 (file_attributes & FILE_ATTRIBUTE_TEMPORARY)) {
1809 status = NT_STATUS_INVALID_PARAMETER;
1814 * We will get a create directory here if the Win32
1815 * app specified a security descriptor in the
1816 * CreateDirectory() call.
1819 status = onefs_open_directory(
1823 access_mask, /* access_mask */
1824 share_access, /* share_access */
1825 create_disposition, /* create_disposition*/
1826 create_options, /* create_options */
1827 file_attributes, /* file_attributes */
1835 * Ordinary file case.
1838 status = file_new(req, conn, &fsp);
1839 if(!NT_STATUS_IS_OK(status)) {
1844 * We're opening the stream element of a base_fsp
1845 * we already opened. Set up the base_fsp pointer.
1848 fsp->base_fsp = base_fsp;
1851 status = onefs_open_file_ntcreate(
1855 access_mask, /* access_mask */
1856 share_access, /* share_access */
1857 create_disposition, /* create_disposition*/
1858 create_options, /* create_options */
1859 file_attributes, /* file_attributes */
1860 oplock_request, /* oplock_request */
1866 if(!NT_STATUS_IS_OK(status)) {
1867 file_free(req, fsp);
1871 if (NT_STATUS_EQUAL(status, NT_STATUS_FILE_IS_A_DIRECTORY)) {
1873 /* A stream open never opens a directory */
1876 status = NT_STATUS_FILE_IS_A_DIRECTORY;
1881 * Fail the open if it was explicitly a non-directory
1885 if (create_options & FILE_NON_DIRECTORY_FILE) {
1886 status = NT_STATUS_FILE_IS_A_DIRECTORY;
1890 create_options |= FILE_DIRECTORY_FILE;
1892 status = onefs_open_directory(
1896 access_mask, /* access_mask */
1897 share_access, /* share_access */
1898 create_disposition, /* create_disposition*/
1899 create_options, /* create_options */
1900 file_attributes, /* file_attributes */
1908 if (!NT_STATUS_IS_OK(status)) {
1912 fsp->base_fsp = base_fsp;
1916 if ((ea_list != NULL) && (info == FILE_WAS_CREATED)) {
1917 status = set_ea(conn, fsp, fname, ea_list);
1918 if (!NT_STATUS_IS_OK(status)) {
1923 if (!fsp->is_directory && S_ISDIR(sbuf.st_mode)) {
1924 status = NT_STATUS_ACCESS_DENIED;
1928 /* Save the requested allocation size. */
1929 if ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN)) {
1931 && (allocation_size > sbuf.st_size)) {
1932 fsp->initial_allocation_size = smb_roundup(
1933 fsp->conn, allocation_size);
1934 if (fsp->is_directory) {
1935 /* Can't set allocation size on a directory. */
1936 status = NT_STATUS_ACCESS_DENIED;
1939 if (vfs_allocate_file_space(
1940 fsp, fsp->initial_allocation_size) == -1) {
1941 status = NT_STATUS_DISK_FULL;
1945 fsp->initial_allocation_size = smb_roundup(
1946 fsp->conn, (uint64_t)sbuf.st_size);
1950 DEBUG(10, ("onefs_create_file_unixpath: info=%d\n", info));
1953 if (pinfo != NULL) {
1956 if (psbuf != NULL) {
1957 if ((fsp->fh == NULL) || (fsp->fh->fd == -1)) {
1961 SMB_VFS_FSTAT(fsp, psbuf);
1964 return NT_STATUS_OK;
1967 DEBUG(10, ("onefs_create_file_unixpath: %s\n", nt_errstr(status)));
1970 if (base_fsp && fsp->base_fsp == base_fsp) {
1972 * The close_file below will close
1977 close_file(req, fsp, ERROR_CLOSE);
1980 if (base_fsp != NULL) {
1981 close_file(req, base_fsp, ERROR_CLOSE);
1988 * SMB_VFS_CREATE_FILE interface to onefs.
1990 NTSTATUS onefs_create_file(vfs_handle_struct *handle,
1991 struct smb_request *req,
1992 uint16_t root_dir_fid,
1994 uint32_t create_file_flags,
1995 uint32_t access_mask,
1996 uint32_t share_access,
1997 uint32_t create_disposition,
1998 uint32_t create_options,
1999 uint32_t file_attributes,
2000 uint32_t oplock_request,
2001 uint64_t allocation_size,
2002 struct security_descriptor *sd,
2003 struct ea_list *ea_list,
2004 files_struct **result,
2006 SMB_STRUCT_STAT *psbuf)
2008 connection_struct *conn = handle->conn;
2009 struct case_semantics_state *case_state = NULL;
2010 SMB_STRUCT_STAT sbuf;
2011 int info = FILE_WAS_OPENED;
2012 files_struct *fsp = NULL;
2015 DEBUG(10,("onefs_create_file: access_mask = 0x%x "
2016 "file_attributes = 0x%x, share_access = 0x%x, "
2017 "create_disposition = 0x%x create_options = 0x%x "
2018 "oplock_request = 0x%x "
2019 "root_dir_fid = 0x%x, ea_list = 0x%p, sd = 0x%p, "
2020 "create_file_flags = 0x%x, fname = %s\n",
2021 (unsigned int)access_mask,
2022 (unsigned int)file_attributes,
2023 (unsigned int)share_access,
2024 (unsigned int)create_disposition,
2025 (unsigned int)create_options,
2026 (unsigned int)oplock_request,
2027 (unsigned int)root_dir_fid,
2028 ea_list, sd, create_file_flags, fname));
2030 /* Get the file name if root_dir_fid was specified. */
2031 if (root_dir_fid != 0) {
2034 status = get_relative_fid_filename(conn, req, root_dir_fid,
2036 if (!NT_STATUS_IS_OK(status)) {
2043 /* Resolve the file name if this was a DFS pathname. */
2044 if ((req != NULL) && (req->flags2 & FLAGS2_DFS_PATHNAMES)) {
2045 char *resolved_fname;
2047 status = resolve_dfspath(talloc_tos(), conn, true, fname,
2050 if (!NT_STATUS_IS_OK(status)) {
2052 * For PATH_NOT_COVERED we had
2053 * reply_botherror(req, NT_STATUS_PATH_NOT_COVERED,
2054 * ERRSRV, ERRbadpath);
2055 * Need to fix in callers
2059 fname = resolved_fname;
2062 /* Check if POSIX semantics are wanted. */
2063 if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
2064 case_state = set_posix_case_semantics(talloc_tos(), conn);
2067 /* Convert dos path to unix path if it hasn't already been done. */
2068 if (create_file_flags & CFF_DOS_PATH) {
2069 char *converted_fname;
2071 SET_STAT_INVALID(sbuf);
2073 status = unix_convert(talloc_tos(), conn, fname, False,
2074 &converted_fname, NULL, &sbuf);
2075 if (!NT_STATUS_IS_OK(status)) {
2078 fname = converted_fname;
2080 if (psbuf != NULL) {
2083 if (SMB_VFS_STAT(conn, fname, &sbuf) == -1) {
2084 SET_STAT_INVALID(sbuf);
2090 TALLOC_FREE(case_state);
2092 /* All file access must go through check_name() */
2093 status = check_name(conn, fname);
2094 if (!NT_STATUS_IS_OK(status)) {
2098 status = onefs_create_file_unixpath(
2102 access_mask, /* access_mask */
2103 share_access, /* share_access */
2104 create_disposition, /* create_disposition*/
2105 create_options, /* create_options */
2106 file_attributes, /* file_attributes */
2107 oplock_request, /* oplock_request */
2108 allocation_size, /* allocation_size */
2110 ea_list, /* ea_list */
2115 if (!NT_STATUS_IS_OK(status)) {
2119 DEBUG(10, ("onefs_create_file: info=%d\n", info));
2122 if (pinfo != NULL) {
2125 if (psbuf != NULL) {
2128 return NT_STATUS_OK;
2131 DEBUG(10, ("onefs_create_file: %s\n", nt_errstr(status)));
2134 close_file(req, fsp, ERROR_CLOSE);