b6b2ef5bb8a4400e1ce407adf3b5c058e9cf688b
[kai/samba.git] / source / smbd / open.c
1 /* 
2    Unix SMB/Netbios implementation.
3    Version 1.9.
4    file opening and share modes
5    Copyright (C) Andrew Tridgell 1992-1998
6    
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or
10    (at your option) any later version.
11    
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16    
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22 #include "includes.h"
23
24 extern int DEBUGLEVEL;
25
26 extern pstring sesssetup_user;
27 extern uint16 global_oplock_port;
28
29
30 /****************************************************************************
31 fd support routines - attempt to do a dos_open
32 ****************************************************************************/
33 static int fd_attempt_open(char *fname, int flags, mode_t mode)
34 {
35   int fd = dos_open(fname,flags,mode);
36
37   /* Fix for files ending in '.' */
38   if((fd == -1) && (errno == ENOENT) &&
39      (strchr(fname,'.')==NULL))
40     {
41       pstrcat(fname,".");
42       fd = dos_open(fname,flags,mode);
43     }
44
45 #if (defined(ENAMETOOLONG) && defined(HAVE_PATHCONF))
46   if ((fd == -1) && (errno == ENAMETOOLONG))
47     {
48       int max_len;
49       char *p = strrchr(fname, '/');
50
51       if (p == fname)   /* name is "/xxx" */
52         {
53           max_len = pathconf("/", _PC_NAME_MAX);
54           p++;
55         }
56       else if ((p == NULL) || (p == fname))
57         {
58           p = fname;
59           max_len = pathconf(".", _PC_NAME_MAX);
60         }
61       else
62         {
63           *p = '\0';
64           max_len = pathconf(fname, _PC_NAME_MAX);
65           *p = '/';
66           p++;
67         }
68       if (strlen(p) > max_len)
69         {
70           char tmp = p[max_len];
71
72           p[max_len] = '\0';
73           if ((fd = dos_open(fname,flags,mode)) == -1)
74             p[max_len] = tmp;
75         }
76     }
77 #endif
78   return fd;
79 }
80
81 /****************************************************************************
82 Cache a uid_t currently with this file open. This is an optimization only
83 used when multiple sessionsetup's have been done to one smbd.
84 ****************************************************************************/
85 void fd_add_to_uid_cache(file_fd_struct *fd_ptr, uid_t u)
86 {
87   if(fd_ptr->uid_cache_count >= sizeof(fd_ptr->uid_users_cache)/sizeof(uid_t))
88     return;
89   fd_ptr->uid_users_cache[fd_ptr->uid_cache_count++] = u;
90 }
91
92 /****************************************************************************
93 Remove a uid_t that currently has this file open. This is an optimization only
94 used when multiple sessionsetup's have been done to one smbd.
95 ****************************************************************************/
96 static void fd_remove_from_uid_cache(file_fd_struct *fd_ptr, uid_t u)
97 {
98   int i;
99   for(i = 0; i < fd_ptr->uid_cache_count; i++)
100     if(fd_ptr->uid_users_cache[i] == u) {
101       if(i < (fd_ptr->uid_cache_count-1))
102         memmove((char *)&fd_ptr->uid_users_cache[i], (char *)&fd_ptr->uid_users_cache[i+1],
103                sizeof(uid_t)*(fd_ptr->uid_cache_count-1-i) );
104       fd_ptr->uid_cache_count--;
105     }
106   return;
107 }
108
109 /****************************************************************************
110 Check if a uid_t that currently has this file open is present. This is an
111 optimization only used when multiple sessionsetup's have been done to one smbd.
112 ****************************************************************************/
113 static BOOL fd_is_in_uid_cache(file_fd_struct *fd_ptr, uid_t u)
114 {
115   int i;
116   for(i = 0; i < fd_ptr->uid_cache_count; i++)
117     if(fd_ptr->uid_users_cache[i] == u)
118       return True;
119   return False;
120 }
121
122
123 /****************************************************************************
124 fd support routines - attempt to re-open an already open fd as O_RDWR.
125 Save the already open fd (we cannot close due to POSIX file locking braindamage.
126 ****************************************************************************/
127 static void fd_attempt_reopen(char *fname, mode_t mode, file_fd_struct *fd_ptr)
128 {
129   int fd = dos_open( fname, O_RDWR, mode);
130
131   if(fd == -1)
132     return;
133
134   if(fd_ptr->real_open_flags == O_RDONLY)
135     fd_ptr->fd_readonly = fd_ptr->fd;
136   if(fd_ptr->real_open_flags == O_WRONLY)
137     fd_ptr->fd_writeonly = fd_ptr->fd;
138
139   fd_ptr->fd = fd;
140   fd_ptr->real_open_flags = O_RDWR;
141 }
142
143 /****************************************************************************
144 fd support routines - attempt to close the file referenced by this fd.
145 Decrements the ref_count and returns it.
146 ****************************************************************************/
147 uint16 fd_attempt_close(file_fd_struct *fd_ptr)
148 {
149   extern struct current_user current_user;
150   uint16 ret_ref = fd_ptr->ref_count;
151
152   DEBUG(3,("fd_attempt_close fd = %d, dev = %x, inode = %.0f, open_flags = %d, ref_count = %d.\n",
153           fd_ptr->fd, (unsigned int)fd_ptr->dev, (double)fd_ptr->inode,
154           fd_ptr->real_open_flags,
155           fd_ptr->ref_count));
156
157   SMB_ASSERT(fd_ptr->ref_count != 0);
158
159   fd_ptr->ref_count--;
160   ret_ref = fd_ptr->ref_count;
161
162   if(fd_ptr->ref_count == 0) {
163     if(fd_ptr->fd != -1)
164       close(fd_ptr->fd);
165     if(fd_ptr->fd_readonly != -1)
166       close(fd_ptr->fd_readonly);
167     if(fd_ptr->fd_writeonly != -1)
168       close(fd_ptr->fd_writeonly);
169     /*
170      * Delete this fd_ptr.
171      */
172     fd_ptr_free(fd_ptr);
173   } else {
174     fd_remove_from_uid_cache(fd_ptr, (uid_t)current_user.uid);
175   }
176
177  return ret_ref;
178 }
179
180 /****************************************************************************
181 fd support routines - check that current user has permissions
182 to open this file. Used when uid not found in optimization cache.
183 This is really ugly code, as due to POSIX locking braindamage we must
184 fork and then attempt to open the file, and return success or failure
185 via an exit code.
186 ****************************************************************************/
187 static BOOL check_access_allowed_for_current_user( char *fname, int accmode )
188 {
189   pid_t child_pid;
190
191   if((child_pid = fork()) < 0) {
192     DEBUG(0,("check_access_allowed_for_current_user: fork failed.\n"));
193     return False;
194   }
195
196   if(child_pid) {
197     /*
198      * Parent.
199      */
200     pid_t wpid;
201     int status_code;
202     if ((wpid = sys_waitpid(child_pid, &status_code, 0)) < 0) {
203       DEBUG(0,("check_access_allowed_for_current_user: The process is no longer waiting!\n"));
204       return(False);
205     }
206
207     if (child_pid != wpid) {
208       DEBUG(0,("check_access_allowed_for_current_user: We were waiting for the wrong process ID\n"));
209       return(False);
210     }
211 #if defined(WIFEXITED) && defined(WEXITSTATUS)
212     if (WIFEXITED(status_code) == 0) {
213       DEBUG(0,("check_access_allowed_for_current_user: The process exited while we were waiting\n"));
214       return(False);
215     }
216     if (WEXITSTATUS(status_code) != 0) {
217       DEBUG(9,("check_access_allowed_for_current_user: The status of the process exiting was %d. Returning access denied.\n", status_code));
218       return(False);
219     }
220 #else /* defined(WIFEXITED) && defined(WEXITSTATUS) */
221     if(status_code != 0) {
222       DEBUG(9,("check_access_allowed_for_current_user: The status of the process exiting was %d. Returning access denied.\n", status_code));
223       return(False);
224     }
225 #endif /* defined(WIFEXITED) && defined(WEXITSTATUS) */
226
227     /*
228      * Success - the child could open the file.
229      */
230     DEBUG(9,("check_access_allowed_for_current_user: The status of the process exiting was %d. Returning access allowed.\n", status_code));
231     return True;
232   } else {
233     /*
234      * Child.
235      */
236     int fd;
237     DEBUG(9,("check_access_allowed_for_current_user: Child - attempting to open %s with mode %d.\n", fname, accmode ));
238     if((fd = fd_attempt_open( fname, accmode, 0)) < 0) {
239       /* Access denied. */
240       _exit(EACCES);
241     }
242     close(fd);
243     DEBUG(9,("check_access_allowed_for_current_user: Child - returning ok.\n"));
244     _exit(0);
245   }
246
247   return False;
248 }
249
250 /****************************************************************************
251 check a filename for the pipe string
252 ****************************************************************************/
253 static void check_for_pipe(char *fname)
254 {
255         /* special case of pipe opens */
256         char s[10];
257         StrnCpy(s,fname,9);
258         strlower(s);
259         if (strstr(s,"pipe/")) {
260                 DEBUG(3,("Rejecting named pipe open for %s\n",fname));
261                 unix_ERR_class = ERRSRV;
262                 unix_ERR_code = ERRaccess;
263         }
264 }
265
266 /****************************************************************************
267 open a file
268 ****************************************************************************/
269 static void open_file(files_struct *fsp,connection_struct *conn,
270                       char *fname1,int flags,mode_t mode, SMB_STRUCT_STAT *sbuf)
271 {
272   extern struct current_user current_user;
273   pstring fname;
274   SMB_STRUCT_STAT statbuf;
275   file_fd_struct *fd_ptr;
276   int accmode = (flags & O_ACCMODE);
277
278   fsp->open = False;
279   fsp->fd_ptr = 0;
280   fsp->granted_oplock = False;
281   errno = EPERM;
282
283   pstrcpy(fname,fname1);
284
285   /* check permissions */
286
287   /*
288    * This code was changed after seeing a client open request 
289    * containing the open mode of (DENY_WRITE/read-only) with
290    * the 'create if not exist' bit set. The previous code
291    * would fail to open the file read only on a read-only share
292    * as it was checking the flags parameter  directly against O_RDONLY,
293    * this was failing as the flags parameter was set to O_RDONLY|O_CREAT.
294    * JRA.
295    */
296
297   if (conn->read_only && !conn->printer) {
298     /* It's a read-only share - fail if we wanted to write. */
299     if(accmode != O_RDONLY) {
300       DEBUG(3,("Permission denied opening %s\n",fname));
301       check_for_pipe(fname);
302       return;
303     } else if(flags & O_CREAT) {
304       /* We don't want to write - but we must make sure that O_CREAT
305          doesn't create the file if we have write access into the
306          directory.
307        */
308       flags &= ~O_CREAT;
309     }
310   }
311
312   /* this handles a bug in Win95 - it doesn't say to create the file when it 
313      should */
314   if (conn->printer) {
315           flags |= O_CREAT;
316   }
317
318 /*
319   if (flags == O_WRONLY)
320     DEBUG(3,("Bug in client? Set O_WRONLY without O_CREAT\n"));
321 */
322
323   /*
324    * Ensure we have a valid struct stat so we can search the
325    * open fd table.
326    */
327   if(sbuf == 0) {
328     if(dos_stat(fname, &statbuf) < 0) {
329       if(errno != ENOENT) {
330         DEBUG(3,("Error doing stat on file %s (%s)\n",
331                  fname,strerror(errno)));
332
333         check_for_pipe(fname);
334         return;
335       }
336       sbuf = 0;
337     } else {
338       sbuf = &statbuf;
339     }
340   }
341
342   /*
343    * Check to see if we have this file already
344    * open. If we do, just use the already open fd and increment the
345    * reference count (fd_get_already_open increments the ref_count).
346    */
347   if((fd_ptr = fd_get_already_open(sbuf))!= 0) {
348     /*
349      * File was already open.
350      */
351
352     /* 
353      * Check it wasn't open for exclusive use.
354      */
355     if((flags & O_CREAT) && (flags & O_EXCL)) {
356       fd_ptr->ref_count--;
357       errno = EEXIST;
358       return;
359     }
360
361     /*
362      * Ensure that the user attempting to open
363      * this file has permissions to do so, if
364      * the user who originally opened the file wasn't
365      * the same as the current user.
366      */
367
368     if(!fd_is_in_uid_cache(fd_ptr, (uid_t)current_user.uid)) {
369       if(!check_access_allowed_for_current_user( fname, accmode )) {
370         /* Error - permission denied. */
371         DEBUG(3,("Permission denied opening file %s (flags=%d, accmode = %d)\n",
372               fname, flags, accmode));
373         /* Ensure the ref_count is decremented. */
374         fd_ptr->ref_count--;
375         fd_remove_from_uid_cache(fd_ptr, (uid_t)current_user.uid);
376         errno = EACCES;
377         return;
378       }
379     }
380
381     fd_add_to_uid_cache(fd_ptr, (uid_t)current_user.uid);
382
383     /* 
384      * If not opened O_RDWR try
385      * and do that here - a chmod may have been done
386      * between the last open and now. 
387      */
388     if(fd_ptr->real_open_flags != O_RDWR)
389       fd_attempt_reopen(fname, mode, fd_ptr);
390
391     /*
392      * Ensure that if we wanted write access
393      * it has been opened for write, and if we wanted read it
394      * was open for read. 
395      */
396     if(((accmode == O_WRONLY) && (fd_ptr->real_open_flags == O_RDONLY)) ||
397        ((accmode == O_RDONLY) && (fd_ptr->real_open_flags == O_WRONLY)) ||
398        ((accmode == O_RDWR) && (fd_ptr->real_open_flags != O_RDWR))) {
399       DEBUG(3,("Error opening (already open for flags=%d) file %s (%s) (flags=%d)\n",
400                fd_ptr->real_open_flags, fname,strerror(EACCES),flags));
401       check_for_pipe(fname);
402       fd_remove_from_uid_cache(fd_ptr, (uid_t)current_user.uid);
403       fd_ptr->ref_count--;
404       return;
405     }
406
407   } else {
408     int open_flags;
409     /* We need to allocate a new file_fd_struct (this increments the
410        ref_count). */
411     if((fd_ptr = fd_get_new()) == 0)
412       return;
413     /*
414      * Whatever the requested flags, attempt read/write access,
415      * as we don't know what flags future file opens may require.
416      * If this fails, try again with the required flags. 
417      * Even if we open read/write when only read access was 
418      * requested the setting of the can_write flag in
419      * the file_struct will protect us from errant
420      * write requests. We never need to worry about O_APPEND
421      * as this is not set anywhere in Samba.
422      */
423     fd_ptr->real_open_flags = O_RDWR;
424     /* Set the flags as needed without the read/write modes. */
425     open_flags = flags & ~(O_RDWR|O_WRONLY|O_RDONLY);
426     fd_ptr->fd = fd_attempt_open(fname, open_flags|O_RDWR, mode);
427     /*
428      * On some systems opening a file for R/W access on a read only
429      * filesystems sets errno to EROFS.
430      */
431 #ifdef EROFS
432     if((fd_ptr->fd == -1) && ((errno == EACCES) || (errno == EROFS))) {
433 #else /* No EROFS */
434     if((fd_ptr->fd == -1) && (errno == EACCES)) {
435 #endif /* EROFS */
436       if(accmode != O_RDWR) {
437         fd_ptr->fd = fd_attempt_open(fname, open_flags|accmode, mode);
438         fd_ptr->real_open_flags = accmode;
439       }
440     }
441   }
442
443   if ((fd_ptr->fd >=0) && 
444       conn->printer && lp_minprintspace(SNUM(conn))) {
445     pstring dname;
446     SMB_BIG_UINT dum1,dum2,dum3;
447     char *p;
448     pstrcpy(dname,fname);
449     p = strrchr(dname,'/');
450     if (p) *p = 0;
451     if (sys_disk_free(dname,&dum1,&dum2,&dum3) < (SMB_BIG_UINT)lp_minprintspace(SNUM(conn))) {
452       if(fd_attempt_close(fd_ptr) == 0)
453         dos_unlink(fname);
454       fsp->fd_ptr = 0;
455       errno = ENOSPC;
456       return;
457     }
458   }
459     
460   if (fd_ptr->fd < 0)
461   {
462     DEBUG(3,("Error opening file %s (%s) (flags=%d)\n",
463       fname,strerror(errno),flags));
464     /* Ensure the ref_count is decremented. */
465     fd_attempt_close(fd_ptr);
466     check_for_pipe(fname);
467     return;
468   }
469
470   if (fd_ptr->fd >= 0)
471   {
472     if(sbuf == 0) {
473       /* Do the fstat */
474       if(sys_fstat(fd_ptr->fd, &statbuf) == -1) {
475         /* Error - backout !! */
476         DEBUG(3,("Error doing fstat on fd %d, file %s (%s)\n",
477                  fd_ptr->fd, fname,strerror(errno)));
478         /* Ensure the ref_count is decremented. */
479         fd_attempt_close(fd_ptr);
480         return;
481       }
482       sbuf = &statbuf;
483     }
484
485     /* Set the correct entries in fd_ptr. */
486     fd_ptr->dev = sbuf->st_dev;
487     fd_ptr->inode = sbuf->st_ino;
488
489     fsp->fd_ptr = fd_ptr;
490     conn->num_files_open++;
491     fsp->mode = sbuf->st_mode;
492     GetTimeOfDay(&fsp->open_time);
493     fsp->vuid = current_user.vuid;
494     fsp->size = 0;
495     fsp->pos = -1;
496     fsp->open = True;
497     fsp->mmap_ptr = NULL;
498     fsp->mmap_size = 0;
499     fsp->can_lock = True;
500     fsp->can_read = ((flags & O_WRONLY)==0);
501     fsp->can_write = ((flags & (O_WRONLY|O_RDWR))!=0);
502     fsp->share_mode = 0;
503     fsp->print_file = conn->printer;
504     fsp->modified = False;
505     fsp->granted_oplock = False;
506     fsp->sent_oplock_break = False;
507     fsp->is_directory = False;
508     fsp->conn = conn;
509     /*
510      * Note that the file name here is the *untranslated* name
511      * ie. it is still in the DOS codepage sent from the client.
512      * All use of this filename will pass though the sys_xxxx
513      * functions which will do the dos_to_unix translation before
514      * mapping into a UNIX filename. JRA.
515      */
516     string_set(&fsp->fsp_name,fname);
517     fsp->wbmpx_ptr = NULL;      
518
519     /*
520      * If the printer is marked as postscript output a leading
521      * file identifier to ensure the file is treated as a raw
522      * postscript file.
523      * This has a similar effect as CtrlD=0 in WIN.INI file.
524      * tim@fsg.com 09/06/94
525      */
526     if (fsp->print_file && lp_postscript(SNUM(conn)) && fsp->can_write) {
527             DEBUG(3,("Writing postscript line\n"));
528             write_file(fsp,"%!\n",3);
529     }
530       
531     DEBUG(2,("%s opened file %s read=%s write=%s (numopen=%d)\n",
532              *sesssetup_user ? sesssetup_user : conn->user,fsp->fsp_name,
533              BOOLSTR(fsp->can_read), BOOLSTR(fsp->can_write),
534              conn->num_files_open));
535
536   }
537 }
538
539 /****************************************************************************
540  If it's a read-only file, and we were compiled with mmap enabled,
541  try and mmap the file. This is split out from open_file() above
542  as mmap'ing the file can cause the kernel reference count to
543  be incremented, which can cause kernel oplocks to be refused.
544  Splitting this call off allows the kernel oplock to be granted, then
545  the file mmap'ed.
546 ****************************************************************************/
547
548 static void mmap_open_file(files_struct *fsp)
549 {
550 #if WITH_MMAP
551   /* mmap it if read-only */
552   if (!fsp->can_write) {
553           fsp->mmap_size = file_size(fsp->fsp_name);
554           if (fsp->mmap_size < MAX_MMAP_SIZE) {
555                   fsp->mmap_ptr = (char *)mmap(NULL,fsp->mmap_size,
556                                                PROT_READ,MAP_SHARED,fsp->fd_ptr->fd,0);
557
558                   if (fsp->mmap_ptr == (char *)-1 || !fsp->mmap_ptr) {
559                           DEBUG(3,("Failed to mmap() %s - %s\n",
560                                    fsp->fsp_name,strerror(errno)));
561                           fsp->mmap_ptr = NULL;
562                   }
563           }
564   }
565 #endif
566 }
567
568 /****************************************************************************
569   C. Hoch 11/22/95
570   Helper for open_file_shared. 
571   Truncate a file after checking locking; close file if locked.
572   **************************************************************************/
573 static void truncate_unless_locked(files_struct *fsp, connection_struct *conn, int token, 
574                                    BOOL *share_locked)
575 {
576         if (fsp->can_write){
577                 SMB_OFF_T mask = ((SMB_OFF_T)0xC) << (SMB_OFF_T_BITS-4);
578                 
579                 if (is_locked(fsp,conn,~mask,0,F_WRLCK)){
580                         /* If share modes are in force for this connection we
581                            have the share entry locked. Unlock it before closing. */
582                         if (*share_locked && lp_share_modes(SNUM(conn)))
583                                 unlock_share_entry( conn, fsp->fd_ptr->dev, 
584                                                     fsp->fd_ptr->inode, token);
585                         close_file(fsp,False);   
586                         /* Share mode no longer locked. */
587                         *share_locked = False;
588                         errno = EACCES;
589                         unix_ERR_class = ERRDOS;
590                   unix_ERR_code = ERRlock;
591                 } else {
592                         sys_ftruncate(fsp->fd_ptr->fd,0); 
593                 }
594         }
595 }
596
597
598 enum {AFAIL,AREAD,AWRITE,AALL};
599
600 /*******************************************************************
601 reproduce the share mode access table
602 ********************************************************************/
603 static int access_table(int new_deny,int old_deny,int old_mode,
604                         int share_pid,char *fname)
605 {
606   if (new_deny == DENY_ALL || old_deny == DENY_ALL) return(AFAIL);
607
608   if (new_deny == DENY_DOS || old_deny == DENY_DOS) {
609     int pid = getpid();
610     if (old_deny == new_deny && share_pid == pid) 
611         return(AALL);    
612
613     if (old_mode == 0) return(AREAD);
614
615     /* the new smbpub.zip spec says that if the file extension is
616        .com, .dll, .exe or .sym then allow the open. I will force
617        it to read-only as this seems sensible although the spec is
618        a little unclear on this. */
619     if ((fname = strrchr(fname,'.'))) {
620       if (strequal(fname,".com") ||
621           strequal(fname,".dll") ||
622           strequal(fname,".exe") ||
623           strequal(fname,".sym"))
624         return(AREAD);
625     }
626
627     return(AFAIL);
628   }
629
630   switch (new_deny) 
631     {
632     case DENY_WRITE:
633       if (old_deny==DENY_WRITE && old_mode==0) return(AREAD);
634       if (old_deny==DENY_READ && old_mode==0) return(AWRITE);
635       if (old_deny==DENY_NONE && old_mode==0) return(AALL);
636       return(AFAIL);
637     case DENY_READ:
638       if (old_deny==DENY_WRITE && old_mode==1) return(AREAD);
639       if (old_deny==DENY_READ && old_mode==1) return(AWRITE);
640       if (old_deny==DENY_NONE && old_mode==1) return(AALL);
641       return(AFAIL);
642     case DENY_NONE:
643       if (old_deny==DENY_WRITE) return(AREAD);
644       if (old_deny==DENY_READ) return(AWRITE);
645       if (old_deny==DENY_NONE) return(AALL);
646       return(AFAIL);      
647     }
648   return(AFAIL);      
649 }
650
651
652 /****************************************************************************
653 check if we can open a file with a share mode
654 ****************************************************************************/
655 static int check_share_mode( share_mode_entry *share, int deny_mode, 
656                              char *fname,
657                              BOOL fcbopen, int *flags)
658 {
659   int old_open_mode = GET_OPEN_MODE(share->share_mode);
660   int old_deny_mode = GET_DENY_MODE(share->share_mode);
661
662   if (old_deny_mode > 4 || old_open_mode > 2)
663   {
664     DEBUG(0,("Invalid share mode found (%d,%d,%d) on file %s\n",
665                deny_mode,old_deny_mode,old_open_mode,fname));
666     return False;
667   }
668
669   {
670     int access_allowed = access_table(deny_mode,old_deny_mode,old_open_mode,
671                                 share->pid,fname);
672
673     if ((access_allowed == AFAIL) ||
674         (!fcbopen && (access_allowed == AREAD && *flags == O_RDWR)) ||
675         (access_allowed == AREAD && *flags == O_WRONLY) ||
676         (access_allowed == AWRITE && *flags == O_RDONLY))
677     {
678       DEBUG(2,("Share violation on file (%d,%d,%d,%d,%s,fcbopen = %d, flags = %d) = %d\n",
679                 deny_mode,old_deny_mode,old_open_mode,
680                 share->pid,fname, fcbopen, *flags, access_allowed));
681       return False;
682     }
683
684     if (access_allowed == AREAD)
685       *flags = O_RDONLY;
686
687     if (access_allowed == AWRITE)
688       *flags = O_WRONLY;
689
690   }
691   return True;
692 }
693
694
695 /****************************************************************************
696 open a file with a share mode
697 ****************************************************************************/
698
699 void open_file_shared(files_struct *fsp,connection_struct *conn,char *fname,int share_mode,int ofun,
700                       mode_t mode,int oplock_request, int *Access,int *action)
701 {
702   int flags=0;
703   int flags2=0;
704   int deny_mode = GET_DENY_MODE(share_mode);
705   BOOL allow_share_delete = GET_ALLOW_SHARE_DELETE(share_mode);
706   SMB_STRUCT_STAT sbuf;
707   BOOL file_existed = file_exist(fname,&sbuf);
708   BOOL share_locked = False;
709   BOOL fcbopen = False;
710   int token;
711   SMB_DEV_T dev = 0;
712   SMB_INO_T inode = 0;
713   int num_share_modes = 0;
714
715   fsp->open = False;
716   fsp->fd_ptr = 0;
717
718   DEBUG(10,("open_file_shared: fname = %s, share_mode = %x, ofun = %x, mode = %o, oplock request = %d\n",
719         fname, share_mode, ofun, mode,  oplock_request ));
720
721   /* this is for OS/2 EAs - try and say we don't support them */
722   if (strstr(fname,".+,;=[].")) 
723   {
724     unix_ERR_class = ERRDOS;
725     /* OS/2 Workplace shell fix may be main code stream in a later release. */ 
726 #if 1 /* OS2_WPS_FIX - Recent versions of OS/2 need this. */
727     unix_ERR_code = ERRcannotopen;
728 #else /* OS2_WPS_FIX */
729     unix_ERR_code = ERROR_EAS_NOT_SUPPORTED;
730 #endif /* OS2_WPS_FIX */
731
732     DEBUG(5,("open_file_shared: OS/2 EA's are not supported.\n"));
733     return;
734   }
735
736   if ((GET_FILE_OPEN_DISPOSITION(ofun) == FILE_EXISTS_FAIL) && file_existed)  
737   {
738     DEBUG(5,("open_file_shared: create new requested for file %s and file already exists.\n",
739           fname ));
740     errno = EEXIST;
741     return;
742   }
743       
744   if (GET_FILE_CREATE_DISPOSITION(ofun) == FILE_CREATE_IF_NOT_EXIST)
745     flags2 |= O_CREAT;
746
747   if (GET_FILE_OPEN_DISPOSITION(ofun) == FILE_EXISTS_TRUNCATE)
748     flags2 |= O_TRUNC;
749
750   /* note that we ignore the append flag as 
751      append does not mean the same thing under dos and unix */
752
753   switch (GET_OPEN_MODE(share_mode))
754   {
755     case DOS_OPEN_WRONLY: 
756       flags = O_WRONLY; 
757       break;
758     case DOS_OPEN_FCB: 
759       fcbopen = True;
760       flags = O_RDWR; 
761       break;
762     case DOS_OPEN_RDWR: 
763       flags = O_RDWR; 
764       break;
765     default:
766       flags = O_RDONLY;
767       break;
768   }
769
770 #if defined(O_SYNC)
771   if (GET_FILE_SYNC_OPENMODE(share_mode)) {
772           flags2 |= O_SYNC;
773   }
774 #endif /* O_SYNC */
775   
776   if (flags != O_RDONLY && file_existed && 
777       (!CAN_WRITE(conn) || IS_DOS_READONLY(dos_mode(conn,fname,&sbuf)))) 
778   {
779     if (!fcbopen) 
780     {
781       DEBUG(5,("open_file_shared: read/write access requested for file %s on read only %s\n",
782             fname, !CAN_WRITE(conn) ? "share" : "file" ));
783       errno = EACCES;
784       return;
785     }
786     flags = O_RDONLY;
787   }
788
789   if (deny_mode > DENY_NONE && deny_mode!=DENY_FCB) 
790   {
791     DEBUG(2,("Invalid deny mode %d on file %s\n",deny_mode,fname));
792     errno = EINVAL;
793     return;
794   }
795
796   if (deny_mode == DENY_FCB)
797     deny_mode = DENY_DOS;
798
799   if (lp_share_modes(SNUM(conn))) 
800   {
801     int i;
802     share_mode_entry *old_shares = 0;
803
804     if (file_existed)
805     {
806       dev = sbuf.st_dev;
807       inode = sbuf.st_ino;
808       lock_share_entry(conn, dev, inode, &token);
809       share_locked = True;
810       num_share_modes = get_share_modes(conn, token, dev, inode, &old_shares);
811     }
812
813     /*
814      * Check if the share modes will give us access.
815      */
816
817     if(share_locked && (num_share_modes != 0))
818     {
819       BOOL broke_oplock;
820
821       do
822       {
823
824         broke_oplock = False;
825         for(i = 0; i < num_share_modes; i++)
826         {
827           share_mode_entry *share_entry = &old_shares[i];
828
829           /* 
830            * By observation of NetBench, oplocks are broken *before* share
831            * modes are checked. This allows a file to be closed by the client
832            * if the share mode would deny access and the client has an oplock. 
833            * Check if someone has an oplock on this file. If so we must break 
834            * it before continuing. 
835            */
836           if(share_entry->op_type & (EXCLUSIVE_OPLOCK|BATCH_OPLOCK))
837           {
838
839             DEBUG(5,("open_file_shared: breaking oplock (%x) on file %s, \
840 dev = %x, inode = %.0f\n", share_entry->op_type, fname, (unsigned int)dev, (double)inode));
841
842             /* Oplock break.... */
843             unlock_share_entry(conn, dev, inode, token);
844             if(request_oplock_break(share_entry, dev, inode) == False)
845             {
846               free((char *)old_shares);
847
848               DEBUG(0,("open_file_shared: FAILED when breaking oplock (%x) on file %s, \
849 dev = %x, inode = %.0f\n", old_shares[i].op_type, fname, (unsigned int)dev, (double)inode));
850
851               errno = EACCES;
852               unix_ERR_class = ERRDOS;
853               unix_ERR_code = ERRbadshare;
854               return;
855             }
856             lock_share_entry(conn, dev, inode, &token);
857             broke_oplock = True;
858             break;
859           }
860
861           /* someone else has a share lock on it, check to see 
862              if we can too */
863           if(check_share_mode(share_entry, deny_mode, fname, fcbopen, &flags) == False)
864           {
865             free((char *)old_shares);
866             unlock_share_entry(conn, dev, inode, token);
867             errno = EACCES;
868             unix_ERR_class = ERRDOS;
869             unix_ERR_code = ERRbadshare;
870             return;
871           }
872
873         } /* end for */
874
875         if(broke_oplock)
876         {
877           free((char *)old_shares);
878           num_share_modes = get_share_modes(conn, token, dev, inode, &old_shares);
879         }
880       } while(broke_oplock);
881     }
882
883     if(old_shares != 0)
884       free((char *)old_shares);
885   }
886
887   DEBUG(4,("calling open_file with flags=0x%X flags2=0x%X mode=0%o\n",
888            flags,flags2,(int)mode));
889
890   open_file(fsp,conn,fname,flags|(flags2&~(O_TRUNC)),mode,file_existed ? &sbuf : 0);
891   if (!fsp->open && flags==O_RDWR && errno!=ENOENT && fcbopen) 
892   {
893     flags = O_RDONLY;
894     open_file(fsp,conn,fname,flags,mode,file_existed ? &sbuf : 0 );
895   }
896
897   if (fsp->open) 
898   {
899     int open_mode=0;
900
901     if((share_locked == False) && lp_share_modes(SNUM(conn)))
902     {
903       /* We created the file - thus we must now lock the share entry before creating it. */
904       dev = fsp->fd_ptr->dev;
905       inode = fsp->fd_ptr->inode;
906       lock_share_entry(conn, dev, inode, &token);
907       share_locked = True;
908     }
909
910     switch (flags) 
911     {
912       case O_RDONLY:
913         open_mode = DOS_OPEN_RDONLY;
914         break;
915       case O_RDWR:
916         open_mode = DOS_OPEN_RDWR;
917         break;
918       case O_WRONLY:
919         open_mode = DOS_OPEN_WRONLY;
920         break;
921     }
922
923     fsp->share_mode = SET_DENY_MODE(deny_mode) | 
924                       SET_OPEN_MODE(open_mode) | 
925                       SET_ALLOW_SHARE_DELETE(allow_share_delete);
926
927     if (Access)
928       (*Access) = open_mode;
929
930     if (action) 
931     {
932       if (file_existed && !(flags2 & O_TRUNC)) *action = FILE_WAS_OPENED;
933       if (!file_existed) *action = FILE_WAS_CREATED;
934       if (file_existed && (flags2 & O_TRUNC)) *action = FILE_WAS_OVERWRITTEN;
935     }
936     /* We must create the share mode entry before truncate as
937        truncate can fail due to locking and have to close the
938        file (which expects the share_mode_entry to be there).
939      */
940     if (lp_share_modes(SNUM(conn)))
941     {
942       uint16 port = 0;
943
944       /* JRA. Currently this only services Exlcusive and batch
945          oplocks (no other opens on this file). This needs to
946          be extended to level II oplocks (multiple reader
947          oplocks). */
948
949       if((oplock_request) && (num_share_modes == 0) && lp_oplocks(SNUM(conn)) && 
950               !IS_VETO_OPLOCK_PATH(conn,fname) && set_file_oplock(fsp) )
951       {
952         port = global_oplock_port;
953       }
954       else
955       {
956         port = 0;
957         oplock_request = 0;
958       }
959
960       set_share_mode(token, fsp, port, oplock_request);
961     }
962
963     if ((flags2&O_TRUNC) && file_existed)
964       truncate_unless_locked(fsp,conn,token,&share_locked);
965
966     /*
967      * Attempt to mmap a read only file.
968      * Moved until after a kernel oplock may
969      * be granted due to reference count issues. JRA.
970      */
971     mmap_open_file(fsp);
972   }
973
974   if (share_locked && lp_share_modes(SNUM(conn)))
975     unlock_share_entry( conn, dev, inode, token);
976 }
977
978 /****************************************************************************
979  Open a directory from an NT SMB call.
980 ****************************************************************************/
981
982 int open_directory(files_struct *fsp,connection_struct *conn,
983                    char *fname, int smb_ofun, mode_t unixmode, int *action)
984 {
985         extern struct current_user current_user;
986         SMB_STRUCT_STAT st;
987
988         if (smb_ofun & 0x10) {
989                 /*
990                  * Create the directory.
991                  */
992
993                 if(dos_mkdir(fname, unix_mode(conn,aDIR)) < 0) {
994                         DEBUG(0,("open_directory: unable to create %s. Error was %s\n",
995                                  fname, strerror(errno) ));
996                         return -1;
997                 }
998
999                 *action = FILE_WAS_CREATED;
1000         } else {
1001                 /*
1002                  * Check that it *was* a directory.
1003                  */
1004
1005                 if(dos_stat(fname, &st) < 0) {
1006                         DEBUG(0,("open_directory: unable to stat name = %s. Error was %s\n",
1007                                  fname, strerror(errno) ));
1008                         return -1;
1009                 }
1010
1011                 if(!S_ISDIR(st.st_mode)) {
1012                         DEBUG(0,("open_directory: %s is not a directory !\n", fname ));
1013                         return -1;
1014                 }
1015                 *action = FILE_WAS_OPENED;
1016         }
1017         
1018         DEBUG(5,("open_directory: opening directory %s\n",
1019                  fname));
1020
1021         /*
1022          * Setup the files_struct for it.
1023          */
1024         
1025         fsp->fd_ptr = NULL;
1026         conn->num_files_open++;
1027         fsp->mode = 0;
1028         GetTimeOfDay(&fsp->open_time);
1029         fsp->vuid = current_user.vuid;
1030         fsp->size = 0;
1031         fsp->pos = -1;
1032         fsp->open = True;
1033         fsp->mmap_ptr = NULL;
1034         fsp->mmap_size = 0;
1035         fsp->can_lock = True;
1036         fsp->can_read = False;
1037         fsp->can_write = False;
1038         fsp->share_mode = 0;
1039         fsp->print_file = False;
1040         fsp->modified = False;
1041         fsp->granted_oplock = False;
1042         fsp->sent_oplock_break = False;
1043         fsp->is_directory = True;
1044         fsp->conn = conn;
1045         /*
1046          * Note that the file name here is the *untranslated* name
1047          * ie. it is still in the DOS codepage sent from the client.
1048          * All use of this filename will pass though the sys_xxxx
1049          * functions which will do the dos_to_unix translation before
1050          * mapping into a UNIX filename. JRA.
1051          */
1052         string_set(&fsp->fsp_name,fname);
1053         fsp->wbmpx_ptr = NULL;
1054
1055         return 0;
1056 }
1057
1058
1059 /*******************************************************************
1060 check if the share mode on a file allows it to be deleted or unlinked
1061 return True if sharing doesn't prevent the operation
1062 ********************************************************************/
1063
1064 BOOL check_file_sharing(connection_struct *conn,char *fname, BOOL rename_op)
1065 {
1066   int i;
1067   int ret = False;
1068   share_mode_entry *old_shares = 0;
1069   int num_share_modes;
1070   SMB_STRUCT_STAT sbuf;
1071   int token;
1072   int pid = getpid();
1073   SMB_DEV_T dev;
1074   SMB_INO_T inode;
1075
1076   if(!lp_share_modes(SNUM(conn)))
1077     return True;
1078
1079   if (dos_stat(fname,&sbuf) == -1) return(True);
1080
1081   dev = sbuf.st_dev;
1082   inode = sbuf.st_ino;
1083
1084   lock_share_entry(conn, dev, inode, &token);
1085   num_share_modes = get_share_modes(conn, token, dev, inode, &old_shares);
1086
1087   /*
1088    * Check if the share modes will give us access.
1089    */
1090
1091   if(num_share_modes != 0)
1092   {
1093     BOOL broke_oplock;
1094
1095     do
1096     {
1097
1098       broke_oplock = False;
1099       for(i = 0; i < num_share_modes; i++)
1100       {
1101         share_mode_entry *share_entry = &old_shares[i];
1102
1103         /* 
1104          * Break oplocks before checking share modes. See comment in
1105          * open_file_shared for details. 
1106          * Check if someone has an oplock on this file. If so we must 
1107          * break it before continuing. 
1108          */
1109         if(share_entry->op_type & BATCH_OPLOCK)
1110         {
1111
1112           /*
1113            * It appears that the NT redirector may have a bug, in that
1114            * it tries to do an SMBmv on a file that it has open with a
1115            * batch oplock, and then fails to respond to the oplock break
1116            * request. This only seems to occur when the client is doing an
1117            * SMBmv to the smbd it is using - thus we try and detect this
1118            * condition by checking if the file being moved is open and oplocked by
1119            * this smbd process, and then not sending the oplock break in this
1120            * special case. If the file was open with a deny mode that 
1121            * prevents the move the SMBmv will fail anyway with a share
1122            * violation error. JRA.
1123            */
1124           if(rename_op && (share_entry->pid == pid))
1125           {
1126
1127             DEBUG(0,("check_file_sharing: NT redirector workaround - rename attempted on \
1128 batch oplocked file %s, dev = %x, inode = %.0f\n", fname, (unsigned int)dev, (double)inode));
1129
1130             /* 
1131              * This next line is a test that allows the deny-mode
1132              * processing to be skipped. This seems to be needed as
1133              * NT insists on the rename succeeding (in Office 9x no less !).
1134              * This should be removed as soon as (a) MS fix the redirector
1135              * bug or (b) NT SMB support in Samba makes NT not issue the
1136              * call (as is my fervent hope). JRA.
1137              */ 
1138             continue;
1139           }
1140           else
1141           {
1142
1143             DEBUG(5,("check_file_sharing: breaking oplock (%x) on file %s, \
1144 dev = %x, inode = %.0f\n", share_entry->op_type, fname, (unsigned int)dev, (double)inode));
1145
1146             /* Oplock break.... */
1147             unlock_share_entry(conn, dev, inode, token);
1148             if(request_oplock_break(share_entry, dev, inode) == False)
1149             {
1150               free((char *)old_shares);
1151
1152               DEBUG(0,("check_file_sharing: FAILED when breaking oplock (%x) on file %s, \
1153 dev = %x, inode = %.0f\n", old_shares[i].op_type, fname, (unsigned int)dev, (double)inode));
1154
1155               return False;
1156             }
1157             lock_share_entry(conn, dev, inode, &token);
1158             broke_oplock = True;
1159             break;
1160           }
1161         }
1162
1163         /* 
1164          * If this is a delete request and ALLOW_SHARE_DELETE is set then allow 
1165          * this to proceed. This takes precedence over share modes.
1166          */
1167
1168         if(!rename_op && GET_ALLOW_SHARE_DELETE(share_entry->share_mode))
1169           continue;
1170
1171         /* 
1172          * Someone else has a share lock on it, check to see 
1173          * if we can too.
1174          */
1175
1176         if ((GET_DENY_MODE(share_entry->share_mode) != DENY_DOS) || (share_entry->pid != pid))
1177           goto free_and_exit;
1178
1179       } /* end for */
1180
1181       if(broke_oplock)
1182       {
1183         free((char *)old_shares);
1184         num_share_modes = get_share_modes(conn, token, dev, inode, &old_shares);
1185       }
1186     } while(broke_oplock);
1187   }
1188
1189   /* XXXX exactly what share mode combinations should be allowed for
1190      deleting/renaming? */
1191   /* 
1192    * If we got here then either there were no share modes or
1193    * all share modes were DENY_DOS and the pid == getpid() or
1194    * delete access was requested and all share modes had the
1195    * ALLOW_SHARE_DELETE bit set (takes precedence over other
1196    * share modes).
1197    */
1198
1199   ret = True;
1200
1201 free_and_exit:
1202
1203   unlock_share_entry(conn, dev, inode, token);
1204   if(old_shares != NULL)
1205     free((char *)old_shares);
1206   return(ret);
1207 }