Plumb SMB2 stubs into all the places we defer SMB1 operations.
[samba.git] / source3 / modules / onefs_open.c
1 /*
2  * Unix SMB/CIFS implementation.
3  *
4  * This file began with some code from source3/smbd/open.c and has been
5  * modified it work with ifs_createfile.
6  *
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
12  *    - Streams
13  *    - Setting security descriptors at create time
14  *    - Setting dos_attributes at create time
15  *
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
20  *
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.
25  *
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.
30  *
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/>.
33  */
34
35 #include "includes.h"
36 #include "onefs.h"
37 #include "onefs_config.h"
38 #include "oplock_onefs.h"
39 #include "smbd/globals.h"
40
41 extern const struct generic_mapping file_generic_mapping;
42
43 struct onefs_fsp_data {
44         uint64_t oplock_callback_id;
45 };
46
47 static NTSTATUS onefs_create_file_unixpath(connection_struct *conn,
48                               struct smb_request *req,
49                               struct smb_filename *smb_fname,
50                               uint32_t access_mask,
51                               uint32_t share_access,
52                               uint32_t create_disposition,
53                               uint32_t create_options,
54                               uint32_t file_attributes,
55                               uint32_t oplock_request,
56                               uint64_t allocation_size,
57                               uint32_t private_flags,
58                               struct security_descriptor *sd,
59                               struct ea_list *ea_list,
60                               files_struct **result,
61                               int *pinfo,
62                               struct onefs_fsp_data *fsp_data);
63
64 /****************************************************************************
65  Open a file.
66 ****************************************************************************/
67
68 static NTSTATUS onefs_open_file(files_struct *fsp,
69                                 connection_struct *conn,
70                                 struct smb_request *req,
71                                 const char *parent_dir,
72                                 struct smb_filename *smb_fname,
73                                 int flags,
74                                 mode_t unx_mode,
75                                 uint32 access_mask,
76                                 uint32 open_access_mask,
77                                 int oplock_request,
78                                 uint64 id,
79                                 uint32 share_access,
80                                 uint32 create_options,
81                                 uint32_t new_dos_attributes,
82                                 struct security_descriptor *sd,
83                                 int *granted_oplock)
84 {
85         struct smb_filename *smb_fname_onefs = NULL;
86         NTSTATUS status = NT_STATUS_OK;
87         int accmode = (flags & O_ACCMODE);
88         int local_flags = flags;
89         bool file_existed = VALID_STAT(smb_fname->st);
90         const char *wild;
91         int base_fd = -1;
92
93         fsp->fh->fd = -1;
94         errno = EPERM;
95
96         /* Check permissions */
97
98         /*
99          * This code was changed after seeing a client open request
100          * containing the open mode of (DENY_WRITE/read-only) with
101          * the 'create if not exist' bit set. The previous code
102          * would fail to open the file read only on a read-only share
103          * as it was checking the flags parameter  directly against O_RDONLY,
104          * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
105          * JRA.
106          */
107
108         if (!CAN_WRITE(conn)) {
109                 /* It's a read-only share - fail if we wanted to write. */
110                 if(accmode != O_RDONLY) {
111                         DEBUG(3, ("Permission denied opening %s\n",
112                                   smb_fname_str_dbg(smb_fname)));
113                         return NT_STATUS_ACCESS_DENIED;
114                 } else if(flags & O_CREAT) {
115                         /* We don't want to write - but we must make sure that
116                            O_CREAT doesn't create the file if we have write
117                            access into the directory.
118                         */
119                         flags &= ~O_CREAT;
120                         local_flags &= ~O_CREAT;
121                 }
122         }
123
124         /*
125          * This little piece of insanity is inspired by the
126          * fact that an NT client can open a file for O_RDONLY,
127          * but set the create disposition to FILE_EXISTS_TRUNCATE.
128          * If the client *can* write to the file, then it expects to
129          * truncate the file, even though it is opening for readonly.
130          * Quicken uses this stupid trick in backup file creation...
131          * Thanks *greatly* to "David W. Chapman Jr." <dwcjr@inethouston.net>
132          * for helping track this one down. It didn't bite us in 2.0.x
133          * as we always opened files read-write in that release. JRA.
134          */
135
136         if ((accmode == O_RDONLY) && ((flags & O_TRUNC) == O_TRUNC)) {
137                 DEBUG(10,("onefs_open_file: truncate requested on read-only "
138                           "open for file %s\n", smb_fname_str_dbg(smb_fname)));
139                 local_flags = (flags & ~O_ACCMODE)|O_RDWR;
140         }
141
142 #if defined(O_NONBLOCK) && defined(S_ISFIFO)
143         /*
144          * We would block on opening a FIFO with no one else on the
145          * other end. Do what we used to do and add O_NONBLOCK to the
146          * open flags. JRA.
147          */
148
149         if (file_existed && S_ISFIFO(smb_fname->st.st_ex_mode)) {
150                 local_flags |= O_NONBLOCK;
151         }
152 #endif
153
154         /* Don't create files with Microsoft wildcard characters. */
155         if (fsp->base_fsp) {
156                 /*
157                  * wildcard characters are allowed in stream names
158                  * only test the basefilename
159                  */
160                 wild = fsp->base_fsp->fsp_name->base_name;
161         } else {
162                 wild = smb_fname->base_name;
163         }
164         if ((local_flags & O_CREAT) && !file_existed &&
165             ms_has_wild(wild))  {
166                 /*
167                  * XXX: may need to remvoe this return...
168                  *
169                  * We dont think this check needs to exist. All it does is
170                  * block creating files with Microsoft wildcards, which is
171                  * fine if the creation originated from NFS or locally and
172                  * then was copied via Samba.
173                  */
174                 DEBUG(1, ("onefs_open_file: creating file with wildcard: %s\n",
175                           smb_fname_str_dbg(smb_fname)));
176                 return NT_STATUS_OBJECT_NAME_INVALID;
177         }
178
179         /* Actually do the open */
180
181 #ifdef O_NOFOLLOW
182         /*
183          * Never follow symlinks on a POSIX client. The
184          * client should be doing this.
185          */
186
187         if (fsp->posix_open || !lp_symlinks(SNUM(conn))) {
188                 flags |= O_NOFOLLOW;
189         }
190 #endif
191         /* Setup a onefs-style smb_fname struct. */
192         status = onefs_stream_prep_smb_fname(talloc_tos(), smb_fname,
193                                              &smb_fname_onefs);
194         if (!NT_STATUS_IS_OK(status)) {
195                 return status;
196         }
197
198         /* If it's a stream pass in the base_fd */
199         if ((conn->fs_capabilities & FILE_NAMED_STREAMS) &&
200             is_ntfs_stream_smb_fname(smb_fname_onefs)) {
201                 SMB_ASSERT(fsp->base_fsp);
202
203                 DEBUG(10, ("Opening a stream: base=%s(%d), stream=%s\n",
204                            smb_fname_onefs->base_name, fsp->base_fsp->fh->fd,
205                            smb_fname_onefs->stream_name));
206
207                 base_fd = fsp->base_fsp->fh->fd;
208         }
209
210         fsp->fh->fd = onefs_sys_create_file(conn,
211                                             base_fd,
212                                             smb_fname_onefs->stream_name != NULL ?
213                                             smb_fname_onefs->stream_name :
214                                             smb_fname_onefs->base_name,
215                                             access_mask,
216                                             open_access_mask,
217                                             share_access,
218                                             create_options,
219                                             flags,
220                                             unx_mode,
221                                             oplock_request,
222                                             id,
223                                             sd,
224                                             new_dos_attributes,
225                                             granted_oplock);
226         TALLOC_FREE(smb_fname_onefs);
227
228         if (fsp->fh->fd == -1) {
229                 if (errno == EMFILE) {
230                         static time_t last_warned = 0L;
231
232                         if (time((time_t *) NULL) > last_warned) {
233                                 DEBUG(0, ("Too many open files, unable "
234                                           "to open more!  smbd's max "
235                                           "open files = %d, also check "
236                                           "sysctl kern.maxfiles and "
237                                           "sysctl kern.maxfilesperproc\n",
238                                           lp_max_open_files()));
239                                 last_warned = time((time_t *) NULL);
240                         }
241                 }
242
243                 status = map_nt_error_from_unix(errno);
244                 DEBUG(3, ("Error opening file %s (%s) (local_flags=%d) "
245                           "(flags=%d)\n", smb_fname_str_dbg(smb_fname),
246                           strerror(errno), local_flags, flags));
247                 return status;
248         }
249
250         if ((local_flags & O_CREAT) && !file_existed) {
251
252                 /* Inherit the ACL if required */
253                 if (lp_inherit_perms(SNUM(conn))) {
254                         inherit_access_posix_acl(conn, parent_dir,
255                             smb_fname->base_name, unx_mode);
256                 }
257
258                 /* Change the owner if required. */
259                 if (lp_inherit_owner(SNUM(conn))) {
260                         change_file_owner_to_parent(conn, parent_dir,
261                             fsp);
262                 }
263
264                 notify_fname(conn, NOTIFY_ACTION_ADDED,
265                     FILE_NOTIFY_CHANGE_FILE_NAME, smb_fname->base_name);
266         }
267
268         if (!file_existed) {
269                 int ret;
270
271                 if (fsp->fh->fd == -1) {
272                         ret = SMB_VFS_STAT(conn, smb_fname);
273                 } else {
274                         ret = SMB_VFS_FSTAT(fsp, &smb_fname->st);
275                         /* If we have an fd, this stat should succeed. */
276                         if (ret == -1) {
277                                 DEBUG(0, ("Error doing fstat on open file %s "
278                                           "(%s)\n",
279                                           smb_fname_str_dbg(smb_fname),
280                                           strerror(errno) ));
281                         }
282                 }
283
284                 /* For a non-io open, this stat failing means file not found. JRA */
285                 if (ret == -1) {
286                         status = map_nt_error_from_unix(errno);
287                         fd_close(fsp);
288                         return status;
289                 }
290         }
291
292         /*
293          * POSIX allows read-only opens of directories. We don't
294          * want to do this (we use a different code path for this)
295          * so catch a directory open and return an EISDIR. JRA.
296          */
297
298         if(S_ISDIR(smb_fname->st.st_ex_mode)) {
299                 fd_close(fsp);
300                 errno = EISDIR;
301                 return NT_STATUS_FILE_IS_A_DIRECTORY;
302         }
303
304         fsp->mode = smb_fname->st.st_ex_mode;
305         fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
306         fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
307         fsp->file_pid = req ? req->smbpid : 0;
308         fsp->can_lock = True;
309         fsp->can_read = (access_mask & (FILE_READ_DATA)) ? True : False;
310         if (!CAN_WRITE(conn)) {
311                 fsp->can_write = False;
312         } else {
313                 fsp->can_write = (access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ?
314                         True : False;
315         }
316         fsp->print_file = False;
317         fsp->modified = False;
318         fsp->sent_oplock_break = NO_BREAK_SENT;
319         fsp->is_directory = False;
320         if (conn->aio_write_behind_list &&
321             is_in_path(smb_fname->base_name, conn->aio_write_behind_list,
322                        conn->case_sensitive)) {
323                 fsp->aio_write_behind = True;
324         }
325
326         fsp->wcp = NULL; /* Write cache pointer. */
327
328         DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
329                  conn->server_info->unix_name,
330                  smb_fname_str_dbg(smb_fname),
331                  BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
332                  conn->num_files_open));
333
334         errno = 0;
335         return NT_STATUS_OK;
336 }
337
338 /****************************************************************************
339  Handle the 1 second delay in returning a SHARING_VIOLATION error.
340 ****************************************************************************/
341
342 static void defer_open(struct share_mode_lock *lck,
343                        struct timeval request_time,
344                        struct timeval timeout,
345                        struct smb_request *req,
346                        struct deferred_open_record *state)
347 {
348         int i;
349
350         /* Paranoia check */
351
352         for (i=0; i<lck->num_share_modes; i++) {
353                 struct share_mode_entry *e = &lck->share_modes[i];
354
355                 if (!is_deferred_open_entry(e)) {
356                         continue;
357                 }
358
359                 if (procid_is_me(&e->pid) && (e->op_mid == req->mid)) {
360                         DEBUG(0, ("Trying to defer an already deferred "
361                                   "request: mid=%d, exiting\n", req->mid));
362                         exit_server("attempt to defer a deferred request");
363                 }
364         }
365
366         /* End paranoia check */
367
368         DEBUG(10,("defer_open_sharing_error: time [%u.%06u] adding deferred "
369                   "open entry for mid %u\n",
370                   (unsigned int)request_time.tv_sec,
371                   (unsigned int)request_time.tv_usec,
372                   (unsigned int)req->mid));
373
374         if (!push_deferred_open_message_smb(req, request_time, timeout,
375                                        (char *)state, sizeof(*state))) {
376                 exit_server("push_deferred_open_message_smb failed");
377         }
378         add_deferred_open(lck, req->mid, request_time, state->id);
379 }
380
381 static void schedule_defer_open(struct share_mode_lock *lck,
382                                 struct timeval request_time,
383                                 struct smb_request *req)
384 {
385         struct deferred_open_record state;
386
387         /* This is a relative time, added to the absolute
388            request_time value to get the absolute timeout time.
389            Note that if this is the second or greater time we enter
390            this codepath for this particular request mid then
391            request_time is left as the absolute time of the *first*
392            time this request mid was processed. This is what allows
393            the request to eventually time out. */
394
395         struct timeval timeout;
396
397         /* Normally the smbd we asked should respond within
398          * OPLOCK_BREAK_TIMEOUT seconds regardless of whether
399          * the client did, give twice the timeout as a safety
400          * measure here in case the other smbd is stuck
401          * somewhere else. */
402
403         /*
404          * On OneFS, the kernel will always send an oplock_revoked message
405          * before this timeout is hit.
406          */
407         timeout = timeval_set(OPLOCK_BREAK_TIMEOUT*10, 0);
408
409         /* Nothing actually uses state.delayed_for_oplocks
410            but it's handy to differentiate in debug messages
411            between a 30 second delay due to oplock break, and
412            a 1 second delay for share mode conflicts. */
413
414         state.delayed_for_oplocks = True;
415         state.failed = false;
416         state.id = lck->id;
417
418         if (!request_timed_out(request_time, timeout)) {
419                 defer_open(lck, request_time, timeout, req, &state);
420         } else {
421                 /* A delayed-for-oplocks deferred open timing out should only
422                  * happen if there is a bug or extreme load, since we set the
423                  * timeout to 300 seconds. */
424                 DEBUG(0, ("Deferred open timeout! request_time=%d.%d, "
425                     "mid=%d\n", request_time.tv_sec, request_time.tv_usec,
426                     req->mid));
427         }
428 }
429
430 /****************************************************************************
431  Open a file with a share mode.  Passed in an already created files_struct.
432 ****************************************************************************/
433 NTSTATUS onefs_open_file_ntcreate(connection_struct *conn,
434                                   struct smb_request *req,
435                                   struct smb_filename *smb_fname,
436                                   uint32 access_mask,
437                                   uint32 share_access,
438                                   uint32 create_disposition,
439                                   uint32 create_options,
440                                   uint32 new_dos_attributes,
441                                   int oplock_request,
442                                   uint32_t private_flags,
443                                   struct security_descriptor *sd,
444                                   files_struct *fsp,
445                                   int *pinfo,
446                                   struct onefs_fsp_data *fsp_data)
447 {
448         int flags=0;
449         int flags2=0;
450         bool file_existed = VALID_STAT(smb_fname->st);
451         bool def_acl = False;
452         bool posix_open = False;
453         bool new_file_created = False;
454         bool clear_ads = False;
455         struct file_id id;
456         mode_t new_unx_mode = (mode_t)0;
457         mode_t unx_mode = (mode_t)0;
458         int info;
459         uint32 existing_dos_attributes = 0;
460         struct timeval request_time = timeval_zero();
461         struct share_mode_lock *lck = NULL;
462         uint32 open_access_mask = access_mask;
463         NTSTATUS status;
464         int ret_flock;
465         char *parent_dir;
466         int granted_oplock;
467         uint64_t oplock_callback_id = 0;
468         uint32 createfile_attributes = 0;
469
470         ZERO_STRUCT(id);
471
472         if (conn->printer) {
473                 /*
474                  * Printers are handled completely differently.
475                  * Most of the passed parameters are ignored.
476                  */
477
478                 if (pinfo) {
479                         *pinfo = FILE_WAS_CREATED;
480                 }
481
482                 DEBUG(10, ("onefs_open_file_ntcreate: printer open fname=%s\n",
483                            smb_fname_str_dbg(smb_fname)));
484
485                 return print_fsp_open(req, conn, smb_fname->base_name,
486                                       req->vuid, fsp);
487         }
488
489         if (!parent_dirname(talloc_tos(), smb_fname->base_name, &parent_dir,
490                             NULL)) {
491                 return NT_STATUS_NO_MEMORY;
492         }
493
494         if (new_dos_attributes & FILE_FLAG_POSIX_SEMANTICS) {
495                 posix_open = True;
496                 unx_mode = (mode_t)(new_dos_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
497                 new_dos_attributes = 0;
498         } else {
499                 /* We add aARCH to this as this mode is only used if the file is
500                  * created new. */
501                 unx_mode = unix_mode(conn, new_dos_attributes | aARCH,
502                                      smb_fname, parent_dir);
503         }
504
505         DEBUG(10,("onefs_open_file_ntcreate: fname=%s, dos_attrs=0x%x "
506                   "access_mask=0x%x share_access=0x%x "
507                   "create_disposition = 0x%x create_options=0x%x "
508                   "unix mode=0%o oplock_request=0x%x\n",
509                   smb_fname_str_dbg(smb_fname), new_dos_attributes,
510                   access_mask, share_access, create_disposition,
511                   create_options, unx_mode, oplock_request));
512
513         /*
514          * Any non-stat-only open has the potential to contend oplocks, which
515          * means to avoid blocking in the kernel (which is unacceptable), the
516          * open must be deferred.  In order to defer opens, req must not be
517          * NULL.  The known cases of calling with a NULL req:
518          *
519          *   1. Open the base file of a stream: Always done stat-only
520          *
521          *   2. open_file_fchmod(), which is called from 3 places:
522          *      A. try_chown: Posix acls only. Never called on onefs.
523          *      B. set_ea_dos_attributes: Can't be called from onefs, because
524          *         SMB_VFS_SETXATTR return ENOSYS.
525          *      C. file_set_dos_mode: This would only happen if the "dos
526          *         filemode" smb.conf parameter is set to yes.  We ship with
527          *         it off, but if a customer were to turn it on it would be
528          *         bad.
529          */
530         if (req == NULL && !is_stat_open(access_mask) &&
531             !is_ntfs_stream_smb_fname(smb_fname)) {
532                 smb_panic("NULL req on a non-stat-open!");
533         }
534
535         if ((req == NULL) && ((oplock_request & INTERNAL_OPEN_ONLY) == 0)) {
536                 DEBUG(0, ("No smb request but not an internal only open!\n"));
537                 return NT_STATUS_INTERNAL_ERROR;
538         }
539
540         /*
541          * Only non-internal opens can be deferred at all
542          */
543
544         if (req) {
545                 void *ptr;
546                 if (get_deferred_open_message_state(req->mid,
547                                 &request_time,
548                                 &ptr)) {
549                         struct deferred_open_record *state = (struct deferred_open_record *)ptr;
550
551                         /* Remember the absolute time of the original
552                            request with this mid. We'll use it later to
553                            see if this has timed out. */
554
555                         /* Remove the deferred open entry under lock. */
556                         lck = get_share_mode_lock(talloc_tos(), state->id,
557                                         NULL, NULL, NULL);
558                         if (lck == NULL) {
559                                 DEBUG(0, ("could not get share mode lock\n"));
560                         } else {
561                                 del_deferred_open_entry(lck, req->mid);
562                                 TALLOC_FREE(lck);
563                         }
564
565                         /* Ensure we don't reprocess this message. */
566                         remove_deferred_open_message_smb(req->mid);
567
568                         /*
569                          * When receiving a semlock_async_failure message, the
570                          * deferred open will be marked as "failed". Returning
571                          * INTERNAL_ERROR.
572                          */
573                         if (state->failed) {
574                                 DEBUG(0, ("onefs_open_file_ntcreate: "
575                                           "semlock_async_failure detected!\n"));
576                                 return NT_STATUS_INTERNAL_ERROR;
577                         }
578                 }
579         }
580
581         status = check_name(conn, smb_fname->base_name);
582         if (!NT_STATUS_IS_OK(status)) {
583                 return status;
584         }
585
586         if (!posix_open) {
587                 new_dos_attributes &= SAMBA_ATTRIBUTES_MASK;
588                 if (file_existed) {
589                         existing_dos_attributes = dos_mode(conn, smb_fname);
590                 }
591         }
592
593         /* Setup dos_attributes to be set by ifs_createfile */
594         if (lp_store_dos_attributes(SNUM(conn))) {
595                 createfile_attributes = (new_dos_attributes | aARCH) &
596                     ~(FILE_ATTRIBUTE_NONINDEXED | FILE_ATTRIBUTE_COMPRESSED);
597         }
598
599         /* Ignore oplock requests if oplocks are disabled. */
600         if (!lp_oplocks(SNUM(conn)) || global_client_failed_oplock_break ||
601             IS_VETO_OPLOCK_PATH(conn, smb_fname->base_name)) {
602                 /* Mask off everything except the private Samba bits. */
603                 oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
604         }
605
606         /* this is for OS/2 long file names - say we don't support them */
607         if (!lp_posix_pathnames() && strstr(smb_fname->base_name,".+,;=[].")) {
608                 /* OS/2 Workplace shell fix may be main code stream in a later
609                  * release. */
610                 DEBUG(5,("onefs_open_file_ntcreate: OS/2 long filenames are "
611                           "not supported.\n"));
612                 if (use_nt_status()) {
613                         return NT_STATUS_OBJECT_NAME_NOT_FOUND;
614                 }
615                 return NT_STATUS_DOS(ERRDOS, ERRcannotopen);
616         }
617
618         switch( create_disposition ) {
619                 /*
620                  * Currently we're using FILE_SUPERSEDE as the same as
621                  * FILE_OVERWRITE_IF but they really are
622                  * different. FILE_SUPERSEDE deletes an existing file
623                  * (requiring delete access) then recreates it.
624                  */
625                 case FILE_SUPERSEDE:
626                         /**
627                          * @todo: Clear all file attributes?
628                          * http://www.osronline.com/article.cfm?article=302
629                          * create if not exist, trunc if exist
630                          *
631                          * If file exists replace/overwrite. If file doesn't
632                          * exist create.
633                          */
634                         flags2 |= (O_CREAT | O_TRUNC);
635                         clear_ads = true;
636                         break;
637
638                 case FILE_OVERWRITE_IF:
639                         /* If file exists replace/overwrite. If file doesn't
640                          * exist create. */
641                         flags2 |= (O_CREAT | O_TRUNC);
642                         clear_ads = true;
643                         break;
644
645                 case FILE_OPEN:
646                         /* If file exists open. If file doesn't exist error. */
647                         if (!file_existed) {
648                                 DEBUG(5,("onefs_open_file_ntcreate: FILE_OPEN "
649                                          "requested for file %s and file "
650                                          "doesn't exist.\n",
651                                          smb_fname_str_dbg(smb_fname)));
652                                 errno = ENOENT;
653                                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
654                         }
655                         break;
656
657                 case FILE_OVERWRITE:
658                         /* If file exists overwrite. If file doesn't exist
659                          * error. */
660                         if (!file_existed) {
661                                 DEBUG(5, ("onefs_open_file_ntcreate: "
662                                           "FILE_OVERWRITE requested for file "
663                                           "%s and file doesn't exist.\n",
664                                           smb_fname_str_dbg(smb_fname)));
665                                 errno = ENOENT;
666                                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
667                         }
668                         flags2 |= O_TRUNC;
669                         clear_ads = true;
670                         break;
671
672                 case FILE_CREATE:
673                         /* If file exists error. If file doesn't exist
674                          * create. */
675                         if (file_existed) {
676                                 DEBUG(5, ("onefs_open_file_ntcreate: "
677                                           "FILE_CREATE requested for file %s "
678                                           "and file already exists.\n",
679                                           smb_fname_str_dbg(smb_fname)));
680                                 if (S_ISDIR(smb_fname->st.st_ex_mode)) {
681                                         errno = EISDIR;
682                                 } else {
683                                         errno = EEXIST;
684                                 }
685                                 return map_nt_error_from_unix(errno);
686                         }
687                         flags2 |= (O_CREAT|O_EXCL);
688                         break;
689
690                 case FILE_OPEN_IF:
691                         /* If file exists open. If file doesn't exist
692                          * create. */
693                         flags2 |= O_CREAT;
694                         break;
695
696                 default:
697                         return NT_STATUS_INVALID_PARAMETER;
698         }
699
700         /* Match attributes on file exists and overwrite. */
701         if (!posix_open && file_existed &&
702             ((create_disposition == FILE_OVERWRITE) ||
703                 (create_disposition == FILE_OVERWRITE_IF))) {
704                 if (!open_match_attributes(conn, existing_dos_attributes,
705                                            new_dos_attributes,
706                                            smb_fname->st.st_ex_mode,
707                                            unx_mode, &new_unx_mode)) {
708                         DEBUG(5, ("onefs_open_file_ntcreate: attributes "
709                                   "missmatch for file %s (%x %x) (0%o, 0%o)\n",
710                                   smb_fname_str_dbg(smb_fname),
711                                   existing_dos_attributes,
712                                   new_dos_attributes,
713                                   (unsigned int)smb_fname->st.st_ex_mode,
714                                   (unsigned int)unx_mode ));
715                         errno = EACCES;
716                         return NT_STATUS_ACCESS_DENIED;
717                 }
718         }
719
720         /*
721          * OneFS understands MAXIMUM_ALLOWED_ACCESS, so only hack the
722          * access_mask, but leave the MAA for the actual open in
723          * open_access_mask.
724          */
725         open_access_mask = access_mask;
726         if (open_access_mask & MAXIMUM_ALLOWED_ACCESS) {
727                 access_mask |= FILE_GENERIC_ALL;
728         }
729
730         /* Convert GENERIC bits to specific bits. */
731         se_map_generic(&access_mask, &file_generic_mapping);
732         se_map_generic(&open_access_mask, &file_generic_mapping);
733
734         if ((flags2 & O_TRUNC) || (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
735                 /* This will cause oplock breaks. */
736                 open_access_mask |= FILE_WRITE_DATA;
737         }
738
739         DEBUG(10, ("onefs_open_file_ntcreate: fname=%s, after mapping "
740                    "open_access_mask=%#x, access_mask=0x%x\n",
741                    smb_fname_str_dbg(smb_fname), open_access_mask,
742                    access_mask));
743
744         /*
745          * Note that we ignore the append flag as append does not
746          * mean the same thing under DOS and Unix.
747          */
748
749         if ((access_mask & (FILE_WRITE_DATA | FILE_APPEND_DATA)) ||
750             (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE)) {
751
752                 /*
753                  * DENY_DOS opens are always underlying read-write on the
754                  * file handle, no matter what the requested access mask
755                  * says. Stock samba just sets the flags, but since
756                  * ifs_createfile uses the access_mask, it must be updated as
757                  * well.  This allows BASE-DENY* to pass.
758                  */
759                 if (create_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS) {
760
761                         DEBUG(10,("onefs_open_file_ntcreate: deny_dos: "
762                                   "Adding O_RDWR to flags "
763                                   "(0x%x) and some READ bits to "
764                                   "open_access_mask (0x%x)\n",
765                                   flags, open_access_mask));
766
767                         flags = O_RDWR;
768                         open_access_mask |= (FILE_READ_ATTRIBUTES |
769                             FILE_READ_DATA | FILE_READ_EA | FILE_EXECUTE);
770
771                 } else if (access_mask & (FILE_READ_ATTRIBUTES |
772                                FILE_READ_DATA |
773                                FILE_READ_EA |
774                                FILE_EXECUTE)) {
775                         flags = O_RDWR;
776                 } else {
777                         flags = O_WRONLY;
778                 }
779         } else {
780                 flags = O_RDONLY;
781         }
782
783         /* Currently we only look at FILE_WRITE_THROUGH for create options. */
784 #if defined(O_SYNC)
785         if ((create_options & FILE_WRITE_THROUGH) &&
786             lp_strict_sync(SNUM(conn))) {
787                 flags2 |= O_SYNC;
788         }
789 #endif /* O_SYNC */
790
791         if (posix_open && (access_mask & FILE_APPEND_DATA)) {
792                 flags2 |= O_APPEND;
793         }
794
795         if (!posix_open && !CAN_WRITE(conn)) {
796                 /*
797                  * We should really return a permission denied error if either
798                  * O_CREAT or O_TRUNC are set, but for compatibility with
799                  * older versions of Samba we just AND them out.
800                  */
801                 flags2 &= ~(O_CREAT|O_TRUNC);
802
803                 /* Deny DELETE_ACCESS explicitly if the share is read only. */
804                 if (access_mask & DELETE_ACCESS) {
805                         return map_nt_error_from_unix(EACCES);
806                 }
807         }
808
809         /* Ensure we can't write on a read-only share or file. */
810         if (flags != O_RDONLY && file_existed &&
811             (!CAN_WRITE(conn) || IS_DOS_READONLY(existing_dos_attributes))) {
812                 DEBUG(5, ("onefs_open_file_ntcreate: write access requested "
813                           "for file %s on read only %s\n",
814                           smb_fname_str_dbg(smb_fname),
815                           !CAN_WRITE(conn) ? "share" : "file" ));
816                 errno = EACCES;
817                 return NT_STATUS_ACCESS_DENIED;
818         }
819
820         DEBUG(10, ("fsp = %p\n", fsp));
821
822         fsp->share_access = share_access;
823         fsp->fh->private_options = private_flags;
824         fsp->access_mask = open_access_mask; /* We change this to the
825                                               * requested access_mask after
826                                               * the open is done. */
827         fsp->posix_open = posix_open;
828
829         /* Ensure no SAMBA_PRIVATE bits can be set. */
830         fsp->oplock_type = (oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK);
831
832         if (timeval_is_zero(&request_time)) {
833                 request_time = fsp->open_time;
834         }
835
836         if (file_existed) {
837                 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
838                 id = vfs_file_id_from_sbuf(conn, &smb_fname->st);
839
840                 lck = get_share_mode_lock(talloc_tos(), id,
841                                           conn->connectpath,
842                                           smb_fname, &old_write_time);
843
844                 if (lck == NULL) {
845                         DEBUG(0, ("Could not get share mode lock\n"));
846                         return NT_STATUS_SHARING_VIOLATION;
847                 }
848
849                 if (lck->delete_on_close) {
850                         /* DELETE_PENDING is not deferred for a second */
851                         TALLOC_FREE(lck);
852                         return NT_STATUS_DELETE_PENDING;
853                 }
854         }
855
856         SMB_ASSERT(!file_existed || (lck != NULL));
857
858         /*
859          * Ensure we pay attention to default ACLs on directories.  May be
860          * neccessary depending on ACL policies.
861          */
862         if ((flags2 & O_CREAT) && lp_inherit_acls(SNUM(conn)) &&
863             (def_acl = directory_has_default_acl(conn, parent_dir))) {
864                 unx_mode = 0777;
865         }
866
867         DEBUG(4,("calling onefs_open_file with flags=0x%X flags2=0x%X "
868                  "mode=0%o, access_mask = 0x%x, open_access_mask = 0x%x\n",
869                  (unsigned int)flags, (unsigned int)flags2,
870                  (unsigned int)unx_mode, (unsigned int)access_mask,
871                  (unsigned int)open_access_mask));
872
873         /*
874          * Since the open is guaranteed to be stat only if req == NULL, a
875          * callback record is only needed if req != NULL.
876          */
877         if (req) {
878                 SMB_ASSERT(fsp_data);
879                 oplock_callback_id = onefs_oplock_wait_record(req->mid);
880                 if (oplock_callback_id == 0) {
881                         return NT_STATUS_NO_MEMORY;
882                 }
883         } else {
884                 /*
885                  * It is also already asserted it's either a stream or a
886                  * stat-only open at this point.
887                  */
888                 SMB_ASSERT(fsp->oplock_type == NO_OPLOCK);
889
890                 /* The kernel and Samba's version of stat-only differs
891                  * slightly: The kernel doesn't think its stat-only if we're
892                  * truncating.  We'd better have a req in order to defer the
893                  * open. */
894                 SMB_ASSERT(!((flags|flags2) & O_TRUNC));
895         }
896
897         /* Do the open. */
898         status = onefs_open_file(fsp,
899                                  conn,
900                                  req,
901                                  parent_dir,
902                                  smb_fname,
903                                  flags|flags2,
904                                  unx_mode,
905                                  access_mask,
906                                  open_access_mask,
907                                  fsp->oplock_type,
908                                  oplock_callback_id,
909                                  share_access,
910                                  create_options,
911                                  createfile_attributes,
912                                  sd,
913                                  &granted_oplock);
914
915         if (!NT_STATUS_IS_OK(status)) {
916
917                 /* OneFS Oplock Handling */
918                 if (errno == EINPROGRESS) {
919
920                         /* If we get EINPROGRESS, the kernel will send us an
921                          * asynchronous semlock event back. Ensure we can defer
922                          * the open, by asserting req. */
923                         SMB_ASSERT(req);
924
925                         if (lck == NULL) {
926                                 /*
927                                  * We hit the race that when we did the stat
928                                  * on the file it did not exist, and someone
929                                  * has created it in between the stat and the
930                                  * open_file() call. Defer our open waiting,
931                                  * to break the oplock of the first opener.
932                                  */
933
934                                 struct timespec old_write_time;
935
936                                 DEBUG(3, ("Someone created file %s with an "
937                                           "oplock after we looked: Retrying\n",
938                                           smb_fname_str_dbg(smb_fname)));
939                                 /*
940                                  * We hit the race that when we did the stat
941                                  * on the file it did not exist, and someone
942                                  * has created it in between the stat and the
943                                  * open_file() call. Just retry immediately.
944                                  */
945                                 id = vfs_file_id_from_sbuf(conn,
946                                                            &smb_fname->st);
947                                 if (!(lck = get_share_mode_lock(talloc_tos(),
948                                           id, conn->connectpath, smb_fname,
949                                           &old_write_time))) {
950                                         /*
951                                          * Emergency exit
952                                          */
953                                         DEBUG(0, ("onefs_open_file_ntcreate: "
954                                                   "Could not get share mode "
955                                                   "lock for %s\n",
956                                                 smb_fname_str_dbg(smb_fname)));
957                                         status = NT_STATUS_SHARING_VIOLATION;
958
959                                         /* XXXZLK: This will cause us to get a
960                                          * semlock event when we aren't
961                                          * expecting one. */
962                                         goto cleanup_destroy;
963                                 }
964
965                                 schedule_defer_open(lck, request_time, req);
966                                 goto cleanup;
967                         }
968                         /* Waiting for an oplock */
969                         DEBUG(5,("Async createfile because a client has an "
970                                  "oplock on %s\n",
971                                  smb_fname_str_dbg(smb_fname)));
972
973                         SMB_ASSERT(req);
974                         schedule_defer_open(lck, request_time, req);
975                         goto cleanup;
976                 }
977
978                 /* Check for a sharing violation */
979                 if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
980                         uint32 can_access_mask;
981                         bool can_access = True;
982
983                         /* If we raced on open we may not have a valid file_id
984                          * or stat buf.  Get them again. */
985                         if (SMB_VFS_STAT(conn, fname, psbuf) == -1) {
986                                 DEBUG(0,("Error doing stat on file %s "
987                                         "(%s)\n", fname, strerror(errno)));
988                                 status = NT_STATUS_SHARING_VIOLATION;
989                                 goto cleanup_destroy;
990                         }
991                         id = vfs_file_id_from_sbuf(conn, psbuf);
992
993                         /* Check if this can be done with the deny_dos and fcb
994                          * calls. */
995
996                         /* Try to find dup fsp if possible. */
997                         if (private_flags &
998                             (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS|
999                              NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
1000
1001                                 if (req == NULL) {
1002                                         DEBUG(0, ("DOS open without an SMB "
1003                                                   "request!\n"));
1004                                         status = NT_STATUS_INTERNAL_ERROR;
1005                                         goto cleanup_destroy;
1006                                 }
1007
1008                                 /* Use the client requested access mask here,
1009                                  * not the one we open with. */
1010                                 status = fcb_or_dos_open(req,
1011                                                         conn,
1012                                                         fsp,
1013                                                         smb_fname,
1014                                                         id,
1015                                                         req->smbpid,
1016                                                         req->vuid,
1017                                                         access_mask,
1018                                                         share_access,
1019                                                         create_options);
1020
1021                                 if (NT_STATUS_IS_OK(status)) {
1022                                         if (pinfo) {
1023                                                 *pinfo = FILE_WAS_OPENED;
1024                                         }
1025                                         status =  NT_STATUS_OK;
1026                                         goto cleanup;
1027                                 }
1028                         }
1029
1030                         /*
1031                          * This next line is a subtlety we need for
1032                          * MS-Access. If a file open will fail due to share
1033                          * permissions and also for security (access) reasons,
1034                          * we need to return the access failed error, not the
1035                          * share error. We can't open the file due to kernel
1036                          * oplock deadlock (it's possible we failed above on
1037                          * the open_mode_check()) so use a userspace check.
1038                          */
1039
1040                         if (flags & O_RDWR) {
1041                                 can_access_mask = FILE_READ_DATA|FILE_WRITE_DATA;
1042                         } else if (flags & O_WRONLY) {
1043                                 can_access_mask = FILE_WRITE_DATA;
1044                         } else {
1045                                 can_access_mask = FILE_READ_DATA;
1046                         }
1047
1048                         if (((can_access_mask & FILE_WRITE_DATA) &&
1049                                 !CAN_WRITE(conn)) ||
1050                             !can_access_file_data(conn, smb_fname,
1051                                                   can_access_mask)) {
1052                                 can_access = False;
1053                         }
1054
1055                         /*
1056                          * If we're returning a share violation, ensure we
1057                          * cope with the braindead 1 second delay.
1058                          */
1059                         if (!(oplock_request & INTERNAL_OPEN_ONLY) &&
1060                             lp_defer_sharing_violations()) {
1061                                 struct timeval timeout;
1062                                 struct deferred_open_record state;
1063                                 int timeout_usecs;
1064
1065                                 /* this is a hack to speed up torture tests
1066                                    in 'make test' */
1067                                 timeout_usecs = lp_parm_int(SNUM(conn),
1068                                     "smbd","sharedelay",
1069                                     SHARING_VIOLATION_USEC_WAIT);
1070
1071                                 /* This is a relative time, added to the
1072                                    absolute request_time value to get the
1073                                    absolute timeout time.  Note that if this
1074                                    is the second or greater time we enter this
1075                                    codepath for this particular request mid
1076                                    then request_time is left as the absolute
1077                                    time of the *first* time this request mid
1078                                    was processed. This is what allows the
1079                                    request to eventually time out. */
1080
1081                                 timeout = timeval_set(0, timeout_usecs);
1082
1083                                 /* Nothing actually uses
1084                                    state.delayed_for_oplocks but it's handy to
1085                                    differentiate in debug messages between a
1086                                    30 second delay due to oplock break, and a
1087                                    1 second delay for share mode conflicts. */
1088
1089                                 state.delayed_for_oplocks = False;
1090                                 state.id = id;
1091                                 state.failed = false;
1092
1093                                 /*
1094                                  * We hit the race that when we did the stat
1095                                  * on the file it did not exist, and someone
1096                                  * has created it in between the stat and the
1097                                  * open_file() call.  Retrieve the share_mode
1098                                  * lock on the newly opened file so we can
1099                                  * defer our request.
1100                                  */
1101                                 if (lck == NULL) {
1102                                         struct timespec old_write_time;
1103                                         old_write_time = get_mtimespec(psbuf);
1104
1105                                         lck = get_share_mode_lock(talloc_tos(),
1106                                             id, conn->connectpath, fname,
1107                                             &old_write_time);
1108                                         if (lck == NULL) {
1109                                                 DEBUG(0,
1110                                                     ("onefs_open_file_ntcreate:"
1111                                                      " Could not get share "
1112                                                      "mode lock for %s\n",
1113                                                      fname));
1114                                                 /* This will cause us to return
1115                                                  * immediately skipping the
1116                                                  * the 1 second delay, which
1117                                                  * isn't a big deal */
1118                                                 status = NT_STATUS_SHARING_VIOLATION;
1119                                                 goto cleanup_destroy;
1120                                         }
1121                                 }
1122
1123                                 if ((req != NULL) &&
1124                                     !request_timed_out(request_time, timeout))
1125                                 {
1126                                         defer_open(lck, request_time, timeout,
1127                                                    req, &state);
1128                                 }
1129                         }
1130
1131                         if (can_access) {
1132                                 /*
1133                                  * We have detected a sharing violation here
1134                                  * so return the correct error code
1135                                  */
1136                                 status = NT_STATUS_SHARING_VIOLATION;
1137                         } else {
1138                                 status = NT_STATUS_ACCESS_DENIED;
1139                         }
1140
1141                         goto cleanup_destroy;
1142                 }
1143
1144                 /*
1145                  * Normal error, for example EACCES
1146                  */
1147          cleanup_destroy:
1148                 if (oplock_callback_id != 0) {
1149                         destroy_onefs_callback_record(oplock_callback_id);
1150                 }
1151          cleanup:
1152                 TALLOC_FREE(lck);
1153                 return status;
1154         }
1155
1156         fsp->oplock_type = granted_oplock;
1157
1158         if (oplock_callback_id != 0) {
1159                 onefs_set_oplock_callback(oplock_callback_id, fsp);
1160                 fsp_data->oplock_callback_id = oplock_callback_id;
1161         } else {
1162                 SMB_ASSERT(fsp->oplock_type == NO_OPLOCK);
1163         }
1164
1165         if (!file_existed) {
1166                 struct timespec old_write_time = smb_fname->st.st_ex_mtime;
1167                 /*
1168                  * Deal with the race condition where two smbd's detect the
1169                  * file doesn't exist and do the create at the same time. One
1170                  * of them will win and set a share mode, the other (ie. this
1171                  * one) should check if the requested share mode for this
1172                  * create is allowed.
1173                  */
1174
1175                 /*
1176                  * Now the file exists and fsp is successfully opened,
1177                  * fsp->file_id is valid and should replace the
1178                  * dev=0, inode=0 from a non existent file. Spotted by
1179                  * Nadav Danieli <nadavd@exanet.com>. JRA.
1180                  */
1181
1182                 id = fsp->file_id;
1183
1184                 lck = get_share_mode_lock(talloc_tos(), id,
1185                                           conn->connectpath,
1186                                           smb_fname, &old_write_time);
1187
1188                 if (lck == NULL) {
1189                         DEBUG(0, ("onefs_open_file_ntcreate: Could not get "
1190                                   "share mode lock for %s\n",
1191                                   smb_fname_str_dbg(smb_fname)));
1192                         fd_close(fsp);
1193                         return NT_STATUS_SHARING_VIOLATION;
1194                 }
1195
1196                 if (lck->delete_on_close) {
1197                         status = NT_STATUS_DELETE_PENDING;
1198                 }
1199
1200                 if (!NT_STATUS_IS_OK(status)) {
1201                         struct deferred_open_record state;
1202
1203                         fd_close(fsp);
1204
1205                         state.delayed_for_oplocks = False;
1206                         state.id = id;
1207
1208                         /* Do it all over again immediately. In the second
1209                          * round we will find that the file existed and handle
1210                          * the DELETE_PENDING and FCB cases correctly. No need
1211                          * to duplicate the code here. Essentially this is a
1212                          * "goto top of this function", but don't tell
1213                          * anybody... */
1214
1215                         if (req != NULL) {
1216                                 defer_open(lck, request_time, timeval_zero(),
1217                                            req, &state);
1218                         }
1219                         TALLOC_FREE(lck);
1220                         return status;
1221                 }
1222
1223                 /*
1224                  * We exit this block with the share entry *locked*.....
1225                  */
1226
1227         }
1228
1229         SMB_ASSERT(lck != NULL);
1230
1231         /* Delete streams if create_disposition requires it */
1232         if (file_existed && clear_ads &&
1233             !is_ntfs_stream_smb_fname(smb_fname)) {
1234                 status = delete_all_streams(conn, smb_fname->base_name);
1235                 if (!NT_STATUS_IS_OK(status)) {
1236                         TALLOC_FREE(lck);
1237                         fd_close(fsp);
1238                         return status;
1239                 }
1240         }
1241
1242         /* note that we ignore failure for the following. It is
1243            basically a hack for NFS, and NFS will never set one of
1244            these only read them. Nobody but Samba can ever set a deny
1245            mode and we have already checked our more authoritative
1246            locking database for permission to set this deny mode. If
1247            the kernel refuses the operations then the kernel is wrong.
1248            note that GPFS supports it as well - jmcd */
1249
1250         if (fsp->fh->fd != -1) {
1251                 ret_flock = SMB_VFS_KERNEL_FLOCK(fsp, share_access, access_mask);
1252                 if(ret_flock == -1 ){
1253
1254                         TALLOC_FREE(lck);
1255                         fd_close(fsp);
1256                         return NT_STATUS_SHARING_VIOLATION;
1257                 }
1258         }
1259
1260         /*
1261          * At this point onwards, we can guarentee that the share entry
1262          * is locked, whether we created the file or not, and that the
1263          * deny mode is compatible with all current opens.
1264          */
1265
1266         /*
1267          * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
1268          */
1269         fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
1270
1271         if (file_existed) {
1272                 /* stat opens on existing files don't get oplocks. */
1273                 if (is_stat_open(open_access_mask)) {
1274                         fsp->oplock_type = NO_OPLOCK;
1275                 }
1276
1277                 if (!(flags2 & O_TRUNC)) {
1278                         info = FILE_WAS_OPENED;
1279                 } else {
1280                         info = FILE_WAS_OVERWRITTEN;
1281                 }
1282         } else {
1283                 info = FILE_WAS_CREATED;
1284         }
1285
1286         if (pinfo) {
1287                 *pinfo = info;
1288         }
1289
1290         /*
1291          * Setup the oplock info in both the shared memory and
1292          * file structs.
1293          */
1294
1295         if ((fsp->oplock_type != NO_OPLOCK) &&
1296             (fsp->oplock_type != FAKE_LEVEL_II_OPLOCK)) {
1297                 if (!set_file_oplock(fsp, fsp->oplock_type)) {
1298                         /* Could not get the kernel oplock */
1299                         fsp->oplock_type = NO_OPLOCK;
1300                 }
1301         }
1302
1303         if (fsp->oplock_type == LEVEL_II_OPLOCK &&
1304             (!lp_level2_oplocks(SNUM(conn)) ||
1305                 !(global_client_caps & CAP_LEVEL_II_OPLOCKS))) {
1306
1307                 DEBUG(5, ("Downgrading level2 oplock on open "
1308                           "because level2 oplocks = off\n"));
1309
1310                 release_file_oplock(fsp);
1311         }
1312
1313         if (info == FILE_WAS_OVERWRITTEN || info == FILE_WAS_CREATED ||
1314             info == FILE_WAS_SUPERSEDED) {
1315                 new_file_created = True;
1316         }
1317
1318         set_share_mode(lck, fsp, conn->server_info->utok.uid, 0,
1319                        fsp->oplock_type);
1320
1321         /* Handle strange delete on close create semantics. */
1322         if (create_options & FILE_DELETE_ON_CLOSE) {
1323                 status = can_set_delete_on_close(fsp, new_dos_attributes);
1324
1325                 if (!NT_STATUS_IS_OK(status)) {
1326                         /* Remember to delete the mode we just added. */
1327                         del_share_mode(lck, fsp);
1328                         TALLOC_FREE(lck);
1329                         fd_close(fsp);
1330                         return status;
1331                 }
1332                 /* Note that here we set the *inital* delete on close flag,
1333                    not the regular one. The magic gets handled in close. */
1334                 fsp->initial_delete_on_close = True;
1335         }
1336
1337         /*
1338          * Take care of inherited ACLs on created files - if default ACL not
1339          * selected.
1340          * May be necessary depending on acl policies.
1341          */
1342         if (!posix_open && !file_existed && !def_acl &&
1343             !(VALID_STAT(smb_fname->st) &&
1344                 (smb_fname->st.st_ex_flags & SF_HASNTFSACL))) {
1345
1346                 int saved_errno = errno; /* We might get ENOSYS in the next
1347                                           * call.. */
1348
1349                 if (SMB_VFS_FCHMOD_ACL(fsp, unx_mode) == -1 &&
1350                     errno == ENOSYS) {
1351                         errno = saved_errno; /* Ignore ENOSYS */
1352                 }
1353
1354         } else if (new_unx_mode) {
1355
1356                 int ret = -1;
1357
1358                 /* Attributes need changing. File already existed. */
1359
1360                 {
1361                         int saved_errno = errno; /* We might get ENOSYS in the
1362                                                   * next call.. */
1363                         ret = SMB_VFS_FCHMOD_ACL(fsp, new_unx_mode);
1364
1365                         if (ret == -1 && errno == ENOSYS) {
1366                                 errno = saved_errno; /* Ignore ENOSYS */
1367                         } else {
1368                                 DEBUG(5, ("onefs_open_file_ntcreate: reset "
1369                                           "attributes of file %s to 0%o\n",
1370                                           smb_fname_str_dbg(smb_fname),
1371                                           (unsigned int)new_unx_mode));
1372                                 ret = 0; /* Don't do the fchmod below. */
1373                         }
1374                 }
1375
1376                 if ((ret == -1) &&
1377                     (SMB_VFS_FCHMOD(fsp, new_unx_mode) == -1))
1378                         DEBUG(5, ("onefs_open_file_ntcreate: failed to reset "
1379                                   "attributes of file %s to 0%o\n",
1380                                   smb_fname_str_dbg(smb_fname),
1381                                   (unsigned int)new_unx_mode));
1382         }
1383
1384         /* If this is a successful open, we must remove any deferred open
1385          * records. */
1386         if (req != NULL) {
1387                 del_deferred_open_entry(lck, req->mid);
1388         }
1389         TALLOC_FREE(lck);
1390
1391         return NT_STATUS_OK;
1392 }
1393
1394
1395 /****************************************************************************
1396  Open a directory from an NT SMB call.
1397 ****************************************************************************/
1398 static NTSTATUS onefs_open_directory(connection_struct *conn,
1399                                      struct smb_request *req,
1400                                      struct smb_filename *smb_dname,
1401                                      uint32 access_mask,
1402                                      uint32 share_access,
1403                                      uint32 create_disposition,
1404                                      uint32 create_options,
1405                                      uint32 file_attributes,
1406                                      struct security_descriptor *sd,
1407                                      files_struct **result,
1408                                      int *pinfo)
1409 {
1410         files_struct *fsp = NULL;
1411         struct share_mode_lock *lck = NULL;
1412         NTSTATUS status;
1413         struct timespec mtimespec;
1414         int info = 0;
1415         char *parent_dir;
1416         bool posix_open = false;
1417         uint32 create_flags = 0;
1418         uint32 mode = lp_dir_mask(SNUM(conn));
1419
1420         DEBUG(5, ("onefs_open_directory: opening directory %s, "
1421                   "access_mask = 0x%x, "
1422                   "share_access = 0x%x create_options = 0x%x, "
1423                   "create_disposition = 0x%x, file_attributes = 0x%x\n",
1424                   smb_fname_str_dbg(smb_dname), (unsigned int)access_mask,
1425                   (unsigned int)share_access, (unsigned int)create_options,
1426                   (unsigned int)create_disposition,
1427                   (unsigned int)file_attributes));
1428
1429         if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
1430             (conn->fs_capabilities & FILE_NAMED_STREAMS) &&
1431             is_ntfs_stream_smb_fname(smb_dname)) {
1432                 DEBUG(2, ("onefs_open_directory: %s is a stream name!\n",
1433                           smb_fname_str_dbg(smb_dname)));
1434                 return NT_STATUS_NOT_A_DIRECTORY;
1435         }
1436
1437         switch (create_disposition) {
1438                 case FILE_OPEN:
1439                         /* If directory exists open. If directory doesn't
1440                          * exist error. */
1441                         create_flags = 0;
1442                         info = FILE_WAS_OPENED;
1443                         break;
1444                 case FILE_CREATE:
1445                         /* If directory exists error. If directory doesn't
1446                          * exist create. */
1447                         create_flags = O_CREAT | O_EXCL;
1448                         info = FILE_WAS_CREATED;
1449                         break;
1450                 case FILE_OPEN_IF:
1451                         /* If directory exists open. If directory doesn't
1452                          * exist create. */
1453
1454                         /* Note: in order to return whether the directory was
1455                          * opened or created, we first try to open and then try
1456                          * to create. */
1457                         create_flags = 0;
1458                         info = FILE_WAS_OPENED;
1459                         break;
1460                 case FILE_SUPERSEDE:
1461                 case FILE_OVERWRITE:
1462                 case FILE_OVERWRITE_IF:
1463                 default:
1464                         DEBUG(5, ("onefs_open_directory: invalid "
1465                                   "create_disposition 0x%x for directory %s\n",
1466                                   (unsigned int)create_disposition,
1467                                   smb_fname_str_dbg(smb_dname)));
1468                         return NT_STATUS_INVALID_PARAMETER;
1469         }
1470
1471         /*
1472          * Check for write access to the share. Done in mkdir_internal() in
1473          * mainline samba.
1474          */
1475         if (!CAN_WRITE(conn) && (create_flags & O_CREAT)) {
1476                 return NT_STATUS_ACCESS_DENIED;
1477         }
1478
1479         /* Get parent dirname */
1480         if (!parent_dirname(talloc_tos(), smb_dname->base_name, &parent_dir,
1481                             NULL)) {
1482                 return NT_STATUS_NO_MEMORY;
1483         }
1484
1485         if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
1486                 posix_open = true;
1487                 mode = (mode_t)(file_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
1488                 file_attributes = 0;
1489         } else {
1490                 mode = unix_mode(conn, aDIR, smb_dname, parent_dir);
1491         }
1492
1493         /*
1494          * The NONINDEXED and COMPRESSED bits seem to always be cleared on
1495          * directories, no matter if you specify that they should be set.
1496          */
1497         file_attributes &=
1498             ~(FILE_ATTRIBUTE_NONINDEXED | FILE_ATTRIBUTE_COMPRESSED);
1499
1500         status = file_new(req, conn, &fsp);
1501         if(!NT_STATUS_IS_OK(status)) {
1502                 return status;
1503         }
1504
1505         /*
1506          * Actual open with retry magic to handle FILE_OPEN_IF which is
1507          * unique because the kernel won't tell us if the file was opened or
1508          * created.
1509          */
1510  retry_open:
1511         fsp->fh->fd = onefs_sys_create_file(conn,
1512                                             -1,
1513                                             smb_dname->base_name,
1514                                             access_mask,
1515                                             access_mask,
1516                                             share_access,
1517                                             create_options,
1518                                             create_flags | O_DIRECTORY,
1519                                             mode,
1520                                             0,
1521                                             0,
1522                                             sd,
1523                                             file_attributes,
1524                                             NULL);
1525
1526         if (fsp->fh->fd == -1) {
1527                 DEBUG(3, ("Error opening %s. Errno=%d (%s).\n",
1528                           smb_fname_str_dbg(smb_dname), errno,
1529                           strerror(errno)));
1530                 SMB_ASSERT(errno != EINPROGRESS);
1531
1532                 if (create_disposition == FILE_OPEN_IF) {
1533                         if (errno == ENOENT) {
1534                                 /* Try again, creating it this time. */
1535                                 create_flags = O_CREAT | O_EXCL;
1536                                 info = FILE_WAS_CREATED;
1537                                 goto retry_open;
1538                         } else if (errno == EEXIST) {
1539                                 /* Uggh. Try again again. */
1540                                 create_flags = 0;
1541                                 info = FILE_WAS_OPENED;
1542                                 goto retry_open;
1543                         }
1544                 }
1545
1546                 /* Error cases below: */
1547                 file_free(req, fsp);
1548
1549                 if ((errno == ENOENT) && (create_disposition == FILE_OPEN)) {
1550                         DEBUG(5, ("onefs_open_directory: FILE_OPEN requested "
1551                                   "for directory %s and it doesn't "
1552                                   "exist.\n", smb_fname_str_dbg(smb_dname)));
1553                         return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1554                 } else if ((errno == EEXIST) &&
1555                     (create_disposition == FILE_CREATE)) {
1556                         DEBUG(5, ("onefs_open_directory: FILE_CREATE "
1557                                   "requested for directory %s and it "
1558                                   "already exists.\n",
1559                                   smb_fname_str_dbg(smb_dname)));
1560                         return NT_STATUS_OBJECT_NAME_COLLISION;
1561                 } else if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
1562                         /* Catch sharing violations. */
1563                         return NT_STATUS_SHARING_VIOLATION;
1564                 }
1565
1566                 return map_nt_error_from_unix(errno);
1567         }
1568
1569         if (info == FILE_WAS_CREATED) {
1570
1571                 /* Pulled from mkdir_internal() */
1572                 if (SMB_VFS_LSTAT(conn, smb_dname) == -1) {
1573                         DEBUG(2, ("Could not stat directory '%s' just "
1574                                   "created: %s\n",
1575                                   smb_fname_str_dbg(smb_dname),
1576                                   strerror(errno)));
1577                         return map_nt_error_from_unix(errno);
1578                 }
1579
1580                 if (!S_ISDIR(smb_dname->st.st_ex_mode)) {
1581                         DEBUG(0, ("Directory just '%s' created is not a "
1582                                   "directory\n",
1583                                   smb_fname_str_dbg(smb_dname)));
1584                         return NT_STATUS_ACCESS_DENIED;
1585                 }
1586
1587                 if (!posix_open) {
1588                         /*
1589                          * Check if high bits should have been set, then (if
1590                          * bits are missing): add them.  Consider bits
1591                          * automagically set by UNIX, i.e. SGID bit from
1592                          * parent dir.
1593                          */
1594                         if (mode & ~(S_IRWXU|S_IRWXG|S_IRWXO) &&
1595                             (mode & ~smb_dname->st.st_ex_mode)) {
1596                                 SMB_VFS_CHMOD(conn, smb_dname->base_name,
1597                                     (smb_dname->st.st_ex_mode |
1598                                         (mode & ~smb_dname->st.st_ex_mode)));
1599                         }
1600                 }
1601
1602                 /* Change the owner if required. */
1603                 if (lp_inherit_owner(SNUM(conn))) {
1604                         change_dir_owner_to_parent(conn, parent_dir,
1605                                                    smb_dname->base_name,
1606                                                    &smb_dname->st);
1607                 }
1608
1609                 notify_fname(conn, NOTIFY_ACTION_ADDED,
1610                              FILE_NOTIFY_CHANGE_DIR_NAME,
1611                              smb_dname->base_name);
1612         }
1613
1614         /* Stat the fd for Samba bookkeeping. */
1615         if(SMB_VFS_FSTAT(fsp, &smb_dname->st) != 0) {
1616                 fd_close(fsp);
1617                 file_free(req, fsp);
1618                 return map_nt_error_from_unix(errno);
1619         }
1620
1621         /* Setup the files_struct for it. */
1622         fsp->mode = smb_dname->st.st_ex_mode;
1623         fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_dname->st);
1624         fsp->vuid = req ? req->vuid : UID_FIELD_INVALID;
1625         fsp->file_pid = req ? req->smbpid : 0;
1626         fsp->can_lock = False;
1627         fsp->can_read = False;
1628         fsp->can_write = False;
1629
1630         fsp->share_access = share_access;
1631         fsp->fh->private_options = 0;
1632         /*
1633          * According to Samba4, SEC_FILE_READ_ATTRIBUTE is always granted,
1634          */
1635         fsp->access_mask = access_mask | FILE_READ_ATTRIBUTES;
1636         fsp->print_file = False;
1637         fsp->modified = False;
1638         fsp->oplock_type = NO_OPLOCK;
1639         fsp->sent_oplock_break = NO_BREAK_SENT;
1640         fsp->is_directory = True;
1641         fsp->posix_open = posix_open;
1642
1643         status = fsp_set_smb_fname(fsp, smb_dname);
1644         if (!NT_STATUS_IS_OK(status)) {
1645                 fd_close(fsp);
1646                 file_free(req, fsp);
1647                 return status;
1648         }
1649
1650         mtimespec = smb_dname->st.st_ex_mtime;
1651
1652         /*
1653          * Still set the samba share mode lock for correct delete-on-close
1654          * semantics and to make smbstatus more useful.
1655          */
1656         lck = get_share_mode_lock(talloc_tos(), fsp->file_id,
1657                                   conn->connectpath, smb_dname, &mtimespec);
1658
1659         if (lck == NULL) {
1660                 DEBUG(0, ("onefs_open_directory: Could not get share mode "
1661                           "lock for %s\n", smb_fname_str_dbg(smb_dname)));
1662                 fd_close(fsp);
1663                 file_free(req, fsp);
1664                 return NT_STATUS_SHARING_VIOLATION;
1665         }
1666
1667         if (lck->delete_on_close) {
1668                 TALLOC_FREE(lck);
1669                 fd_close(fsp);
1670                 file_free(req, fsp);
1671                 return NT_STATUS_DELETE_PENDING;
1672         }
1673
1674         set_share_mode(lck, fsp, conn->server_info->utok.uid, 0, NO_OPLOCK);
1675
1676         /*
1677          * For directories the delete on close bit at open time seems
1678          * always to be honored on close... See test 19 in Samba4 BASE-DELETE.
1679          */
1680         if (create_options & FILE_DELETE_ON_CLOSE) {
1681                 status = can_set_delete_on_close(fsp, 0);
1682                 if (!NT_STATUS_IS_OK(status) &&
1683                     !NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
1684                         TALLOC_FREE(lck);
1685                         fd_close(fsp);
1686                         file_free(req, fsp);
1687                         return status;
1688                 }
1689
1690                 if (NT_STATUS_IS_OK(status)) {
1691                         /* Note that here we set the *inital* delete on close flag,
1692                            not the regular one. The magic gets handled in close. */
1693                         fsp->initial_delete_on_close = True;
1694                 }
1695         }
1696
1697         TALLOC_FREE(lck);
1698
1699         if (pinfo) {
1700                 *pinfo = info;
1701         }
1702
1703         *result = fsp;
1704         return NT_STATUS_OK;
1705 }
1706
1707 /*
1708  * Wrapper around onefs_open_file_ntcreate and onefs_open_directory.
1709  */
1710 static NTSTATUS onefs_create_file_unixpath(connection_struct *conn,
1711                                            struct smb_request *req,
1712                                            struct smb_filename *smb_fname,
1713                                            uint32_t access_mask,
1714                                            uint32_t share_access,
1715                                            uint32_t create_disposition,
1716                                            uint32_t create_options,
1717                                            uint32_t file_attributes,
1718                                            uint32_t oplock_request,
1719                                            uint64_t allocation_size,
1720                                            uint32_t private_flags,
1721                                            struct security_descriptor *sd,
1722                                            struct ea_list *ea_list,
1723                                            files_struct **result,
1724                                            int *pinfo,
1725                                            struct onefs_fsp_data *fsp_data)
1726 {
1727         int info = FILE_WAS_OPENED;
1728         files_struct *base_fsp = NULL;
1729         files_struct *fsp = NULL;
1730         NTSTATUS status;
1731
1732         DEBUG(10,("onefs_create_file_unixpath: access_mask = 0x%x "
1733                   "file_attributes = 0x%x, share_access = 0x%x, "
1734                   "create_disposition = 0x%x create_options = 0x%x "
1735                   "oplock_request = 0x%x private_flags = 0x%x "
1736                   "ea_list = 0x%p, sd = 0x%p, "
1737                   "fname = %s\n",
1738                   (unsigned int)access_mask,
1739                   (unsigned int)file_attributes,
1740                   (unsigned int)share_access,
1741                   (unsigned int)create_disposition,
1742                   (unsigned int)create_options,
1743                   (unsigned int)oplock_request,
1744                   (unsigned int)private_flags,
1745                   ea_list, sd, smb_fname_str_dbg(smb_fname)));
1746
1747         if (create_options & FILE_OPEN_BY_FILE_ID) {
1748                 status = NT_STATUS_NOT_SUPPORTED;
1749                 goto fail;
1750         }
1751
1752         if (create_options & NTCREATEX_OPTIONS_INVALID_PARAM_MASK) {
1753                 status = NT_STATUS_INVALID_PARAMETER;
1754                 goto fail;
1755         }
1756
1757         if (req == NULL) {
1758                 SMB_ASSERT((oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK) ==
1759                             NO_OPLOCK);
1760                 oplock_request |= INTERNAL_OPEN_ONLY;
1761         }
1762
1763         if (lp_parm_bool(SNUM(conn), PARM_ONEFS_TYPE,
1764                 PARM_IGNORE_SACLS, PARM_IGNORE_SACLS_DEFAULT)) {
1765                 access_mask &= ~SYSTEM_SECURITY_ACCESS;
1766         }
1767
1768         if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
1769             && (access_mask & DELETE_ACCESS)
1770             && !is_ntfs_stream_smb_fname(smb_fname)) {
1771                 /*
1772                  * We can't open a file with DELETE access if any of the
1773                  * streams is open without FILE_SHARE_DELETE
1774                  */
1775                 status = open_streams_for_delete(conn, smb_fname->base_name);
1776
1777                 if (!NT_STATUS_IS_OK(status)) {
1778                         goto fail;
1779                 }
1780         }
1781
1782         if ((conn->fs_capabilities & FILE_NAMED_STREAMS)
1783             && is_ntfs_stream_smb_fname(smb_fname)) {
1784                 uint32 base_create_disposition;
1785                 struct smb_filename *smb_fname_base = NULL;
1786
1787                 if (create_options & FILE_DIRECTORY_FILE) {
1788                         status = NT_STATUS_NOT_A_DIRECTORY;
1789                         goto fail;
1790                 }
1791
1792                 switch (create_disposition) {
1793                 case FILE_OPEN:
1794                         base_create_disposition = FILE_OPEN;
1795                         break;
1796                 default:
1797                         base_create_disposition = FILE_OPEN_IF;
1798                         break;
1799                 }
1800
1801                 /* Create an smb_filename with stream_name == NULL. */
1802                 status = create_synthetic_smb_fname(talloc_tos(),
1803                                                     smb_fname->base_name,
1804                                                     NULL, NULL,
1805                                                     &smb_fname_base);
1806                 if (!NT_STATUS_IS_OK(status)) {
1807                         goto fail;
1808                 }
1809
1810                 if (SMB_VFS_STAT(conn, smb_fname_base) == -1) {
1811                         DEBUG(10, ("Unable to stat stream: %s\n",
1812                                    smb_fname_str_dbg(smb_fname_base)));
1813                 }
1814
1815                 status = onefs_create_file_unixpath(
1816                         conn,                           /* conn */
1817                         NULL,                           /* req */
1818                         smb_fname_base,                 /* fname */
1819                         SYNCHRONIZE_ACCESS,             /* access_mask */
1820                         (FILE_SHARE_READ |
1821                             FILE_SHARE_WRITE |
1822                             FILE_SHARE_DELETE),         /* share_access */
1823                         base_create_disposition,        /* create_disposition*/
1824                         0,                              /* create_options */
1825                         file_attributes,                /* file_attributes */
1826                         NO_OPLOCK,                      /* oplock_request */
1827                         0,                              /* allocation_size */
1828                         0,                              /* private_flags */
1829                         NULL,                           /* sd */
1830                         NULL,                           /* ea_list */
1831                         &base_fsp,                      /* result */
1832                         NULL,                           /* pinfo */
1833                         NULL);                          /* fsp_data */
1834
1835                 TALLOC_FREE(smb_fname_base);
1836
1837                 if (!NT_STATUS_IS_OK(status)) {
1838                         DEBUG(10, ("onefs_create_file_unixpath for base %s "
1839                                    "failed: %s\n", smb_fname->base_name,
1840                                    nt_errstr(status)));
1841                         goto fail;
1842                 }
1843
1844                 /*
1845                  * Testing against windows xp/2003/vista shows that oplocks
1846                  * can actually be requested and granted on streams (see the
1847                  * RAW-OPLOCK-STREAM1 smbtorture test).
1848                  */
1849                 if ((oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK) !=
1850                      NO_OPLOCK) {
1851                         DEBUG(5, ("Oplock(%d) being requested on a stream! "
1852                                   "Ignoring oplock request: fname=%s\n",
1853                                   oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK,
1854                                 smb_fname_str_dbg(smb_fname)));
1855                         /* Request NO_OPLOCK instead. */
1856                         oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
1857                 }
1858         }
1859
1860         /* Covert generic bits in the security descriptor. */
1861         if (sd != NULL) {
1862                 security_acl_map_generic(sd->dacl, &file_generic_mapping);
1863                 security_acl_map_generic(sd->sacl, &file_generic_mapping);
1864         }
1865
1866         /*
1867          * If it's a request for a directory open, deal with it separately.
1868          */
1869
1870         if (create_options & FILE_DIRECTORY_FILE) {
1871
1872                 if (create_options & FILE_NON_DIRECTORY_FILE) {
1873                         status = NT_STATUS_INVALID_PARAMETER;
1874                         goto fail;
1875                 }
1876
1877                 /* Can't open a temp directory. IFS kit test. */
1878                 if (!(file_attributes & FILE_FLAG_POSIX_SEMANTICS) &&
1879                      (file_attributes & FILE_ATTRIBUTE_TEMPORARY)) {
1880                         status = NT_STATUS_INVALID_PARAMETER;
1881                         goto fail;
1882                 }
1883
1884                 /*
1885                  * We will get a create directory here if the Win32
1886                  * app specified a security descriptor in the
1887                  * CreateDirectory() call.
1888                  */
1889
1890                 status = onefs_open_directory(
1891                         conn,                           /* conn */
1892                         req,                            /* req */
1893                         smb_fname,                      /* fname */
1894                         access_mask,                    /* access_mask */
1895                         share_access,                   /* share_access */
1896                         create_disposition,             /* create_disposition*/
1897                         create_options,                 /* create_options */
1898                         file_attributes,                /* file_attributes */
1899                         sd,                             /* sd */
1900                         &fsp,                           /* result */
1901                         &info);                         /* pinfo */
1902         } else {
1903
1904                 /*
1905                  * Ordinary file case.
1906                  */
1907
1908                 status = file_new(req, conn, &fsp);
1909                 if(!NT_STATUS_IS_OK(status)) {
1910                         goto fail;
1911                 }
1912
1913                 /*
1914                  * We're opening the stream element of a base_fsp
1915                  * we already opened. Set up the base_fsp pointer.
1916                  */
1917                 if (base_fsp) {
1918                         fsp->base_fsp = base_fsp;
1919                 }
1920
1921                 status = onefs_open_file_ntcreate(
1922                         conn,                           /* conn */
1923                         req,                            /* req */
1924                         smb_fname,                      /* fname */
1925                         access_mask,                    /* access_mask */
1926                         share_access,                   /* share_access */
1927                         create_disposition,             /* create_disposition*/
1928                         create_options,                 /* create_options */
1929                         file_attributes,                /* file_attributes */
1930                         oplock_request,                 /* oplock_request */
1931                         sd,                             /* sd */
1932                         fsp,                            /* result */
1933                         &info,                          /* pinfo */
1934                         fsp_data);                      /* fsp_data */
1935
1936                 if(!NT_STATUS_IS_OK(status)) {
1937                         file_free(req, fsp);
1938                         fsp = NULL;
1939                 }
1940
1941                 if (NT_STATUS_EQUAL(status, NT_STATUS_FILE_IS_A_DIRECTORY)) {
1942
1943                         /* A stream open never opens a directory */
1944
1945                         if (base_fsp) {
1946                                 status = NT_STATUS_FILE_IS_A_DIRECTORY;
1947                                 goto fail;
1948                         }
1949
1950                         /*
1951                          * Fail the open if it was explicitly a non-directory
1952                          * file.
1953                          */
1954
1955                         if (create_options & FILE_NON_DIRECTORY_FILE) {
1956                                 status = NT_STATUS_FILE_IS_A_DIRECTORY;
1957                                 goto fail;
1958                         }
1959
1960                         create_options |= FILE_DIRECTORY_FILE;
1961
1962                         status = onefs_open_directory(
1963                                 conn,                   /* conn */
1964                                 req,                    /* req */
1965                                 smb_fname,              /* fname */
1966                                 access_mask,            /* access_mask */
1967                                 share_access,           /* share_access */
1968                                 create_disposition,     /* create_disposition*/
1969                                 create_options,         /* create_options */
1970                                 file_attributes,        /* file_attributes */
1971                                 sd,                     /* sd */
1972                                 &fsp,                   /* result */
1973                                 &info);                 /* pinfo */
1974                 }
1975         }
1976
1977         if (!NT_STATUS_IS_OK(status)) {
1978                 goto fail;
1979         }
1980
1981         fsp->base_fsp = base_fsp;
1982
1983         SMB_ASSERT(fsp);
1984
1985         if ((ea_list != NULL) && (info == FILE_WAS_CREATED)) {
1986                 status = set_ea(conn, fsp, smb_fname, ea_list);
1987                 if (!NT_STATUS_IS_OK(status)) {
1988                         goto fail;
1989                 }
1990         }
1991
1992         if (!fsp->is_directory && S_ISDIR(smb_fname->st.st_ex_mode)) {
1993                 status = NT_STATUS_ACCESS_DENIED;
1994                 goto fail;
1995         }
1996
1997         /* Save the requested allocation size. */
1998         if ((info == FILE_WAS_CREATED) || (info == FILE_WAS_OVERWRITTEN)) {
1999                 if (allocation_size
2000                     && (allocation_size > smb_fname->st.st_ex_size)) {
2001                         fsp->initial_allocation_size = smb_roundup(
2002                                 fsp->conn, allocation_size);
2003                         if (fsp->is_directory) {
2004                                 /* Can't set allocation size on a directory. */
2005                                 status = NT_STATUS_ACCESS_DENIED;
2006                                 goto fail;
2007                         }
2008                         if (vfs_allocate_file_space(
2009                                     fsp, fsp->initial_allocation_size) == -1) {
2010                                 status = NT_STATUS_DISK_FULL;
2011                                 goto fail;
2012                         }
2013                 } else {
2014                         fsp->initial_allocation_size = smb_roundup(
2015                                 fsp->conn, (uint64_t)smb_fname->st.st_ex_size);
2016                 }
2017         }
2018
2019         DEBUG(10, ("onefs_create_file_unixpath: info=%d\n", info));
2020
2021         *result = fsp;
2022         if (pinfo != NULL) {
2023                 *pinfo = info;
2024         }
2025         if ((fsp->fh != NULL) && (fsp->fh->fd != -1)) {
2026                 SMB_VFS_FSTAT(fsp, &smb_fname->st);
2027         }
2028         return NT_STATUS_OK;
2029
2030  fail:
2031         DEBUG(10, ("onefs_create_file_unixpath: %s\n", nt_errstr(status)));
2032
2033         if (fsp != NULL) {
2034                 if (base_fsp && fsp->base_fsp == base_fsp) {
2035                         /*
2036                          * The close_file below will close
2037                          * fsp->base_fsp.
2038                          */
2039                         base_fsp = NULL;
2040                 }
2041                 close_file(req, fsp, ERROR_CLOSE);
2042                 fsp = NULL;
2043         }
2044         if (base_fsp != NULL) {
2045                 close_file(req, base_fsp, ERROR_CLOSE);
2046                 base_fsp = NULL;
2047         }
2048         return status;
2049 }
2050
2051 static void destroy_onefs_fsp_data(void *p_data)
2052 {
2053         struct onefs_fsp_data *fsp_data = (struct onefs_fsp_data *)p_data;
2054
2055         destroy_onefs_callback_record(fsp_data->oplock_callback_id);
2056 }
2057
2058 /**
2059  * SMB_VFS_CREATE_FILE interface to onefs.
2060  */
2061 NTSTATUS onefs_create_file(vfs_handle_struct *handle,
2062                            struct smb_request *req,
2063                            uint16_t root_dir_fid,
2064                            struct smb_filename *smb_fname,
2065                            uint32_t access_mask,
2066                            uint32_t share_access,
2067                            uint32_t create_disposition,
2068                            uint32_t create_options,
2069                            uint32_t file_attributes,
2070                            uint32_t oplock_request,
2071                            uint64_t allocation_size,
2072                            uint32_t private_flags,
2073                            struct security_descriptor *sd,
2074                            struct ea_list *ea_list,
2075                            files_struct **result,
2076                            int *pinfo)
2077 {
2078         connection_struct *conn = handle->conn;
2079         struct onefs_fsp_data fsp_data = {};
2080         int info = FILE_WAS_OPENED;
2081         files_struct *fsp = NULL;
2082         NTSTATUS status;
2083
2084         DEBUG(10,("onefs_create_file: access_mask = 0x%x "
2085                   "file_attributes = 0x%x, share_access = 0x%x, "
2086                   "create_disposition = 0x%x create_options = 0x%x "
2087                   "oplock_request = 0x%x private_flags = 0x%x"
2088                   "root_dir_fid = 0x%x, ea_list = 0x%p, sd = 0x%p, "
2089                   "fname = %s\n",
2090                   (unsigned int)access_mask,
2091                   (unsigned int)file_attributes,
2092                   (unsigned int)share_access,
2093                   (unsigned int)create_disposition,
2094                   (unsigned int)create_options,
2095                   (unsigned int)oplock_request,
2096                   (unsigned int)private_flags,
2097                   (unsigned int)root_dir_fid,
2098                   ea_list, sd, smb_fname_str_dbg(smb_fname)));
2099
2100         /* Get the file name if root_dir_fid was specified. */
2101         if (root_dir_fid != 0) {
2102                 status = get_relative_fid_filename(conn, req, root_dir_fid,
2103                                                    smb_fname);
2104                 if (!NT_STATUS_IS_OK(status)) {
2105                         goto fail;
2106                 }
2107         }
2108
2109         /* All file access must go through check_name() */
2110         status = check_name(conn, smb_fname->base_name);
2111         if (!NT_STATUS_IS_OK(status)) {
2112                 goto fail;
2113         }
2114
2115         status = onefs_create_file_unixpath(
2116                 conn,                                   /* conn */
2117                 req,                                    /* req */
2118                 smb_fname,                              /* fname */
2119                 access_mask,                            /* access_mask */
2120                 share_access,                           /* share_access */
2121                 create_disposition,                     /* create_disposition*/
2122                 create_options,                         /* create_options */
2123                 file_attributes,                        /* file_attributes */
2124                 oplock_request,                         /* oplock_request */
2125                 allocation_size,                        /* allocation_size */
2126                 private_flags,
2127                 sd,                                     /* sd */
2128                 ea_list,                                /* ea_list */
2129                 &fsp,                                   /* result */
2130                 &info,                                  /* pinfo */
2131                 &fsp_data);                             /* psbuf */
2132
2133         if (!NT_STATUS_IS_OK(status)) {
2134                 goto fail;
2135         }
2136
2137         DEBUG(10, ("onefs_create_file: info=%d\n", info));
2138
2139         /*
2140          * Setup private onefs_fsp_data.  Currently the private data struct is
2141          * only used to store the oplock_callback_id so that when the file is
2142          * closed, the onefs_callback_record can be properly cleaned up in the
2143          * oplock_onefs sub-system.
2144          */
2145         if (fsp) {
2146                 struct onefs_fsp_data *fsp_data_tmp = NULL;
2147                 fsp_data_tmp = (struct onefs_fsp_data *)
2148                     VFS_ADD_FSP_EXTENSION(handle, fsp, struct onefs_fsp_data,
2149                         &destroy_onefs_fsp_data);
2150
2151                 if (fsp_data_tmp == NULL) {
2152                         status = NT_STATUS_NO_MEMORY;
2153                         goto fail;
2154                 }
2155
2156                 *fsp_data_tmp = fsp_data;
2157         }
2158
2159         *result = fsp;
2160         if (pinfo != NULL) {
2161                 *pinfo = info;
2162         }
2163         return NT_STATUS_OK;
2164
2165  fail:
2166         DEBUG(10, ("onefs_create_file: %s\n", nt_errstr(status)));
2167
2168         if (fsp != NULL) {
2169                 close_file(req, fsp, ERROR_CLOSE);
2170                 fsp = NULL;
2171         }
2172         return status;
2173 }