Move nttrans.c into the NTSTATUS age.
[nivanova/samba-autobuild/.git] / source3 / smbd / nttrans.c
1 /*
2    Unix SMB/CIFS implementation.
3    SMB NT transaction handling
4    Copyright (C) Jeremy Allison 1994-1998
5
6    This program is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 2 of the License, or
9    (at your option) any later version.
10
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with this program; if not, write to the Free Software
18    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21 #include "includes.h"
22
23 extern int Protocol;
24 extern int smb_read_error;
25 extern int global_oplock_break;
26 extern BOOL case_sensitive;
27 extern BOOL case_preserve;
28 extern BOOL short_case_preserve;
29
30 static char *known_nt_pipes[] = {
31   "\\LANMAN",
32   "\\srvsvc",
33   "\\samr",
34   "\\wkssvc",
35   "\\NETLOGON",
36   "\\ntlsa",
37   "\\ntsvcs",
38   "\\lsass",
39   "\\lsarpc",
40   "\\winreg",
41   "\\spoolss",
42   "\\netdfs",
43   NULL
44 };
45
46 /* Map generic permissions to file object specific permissions */
47  
48 struct generic_mapping file_generic_mapping = {
49         FILE_GENERIC_READ,
50         FILE_GENERIC_WRITE,
51         FILE_GENERIC_EXECUTE,
52         FILE_GENERIC_ALL
53 };
54
55 /****************************************************************************
56  Send the required number of replies back.
57  We assume all fields other than the data fields are
58  set correctly for the type of call.
59  HACK ! Always assumes smb_setup field is zero.
60 ****************************************************************************/
61
62 static int send_nt_replies(char *inbuf, char *outbuf, int bufsize, NTSTATUS nt_error, char *params,
63                            int paramsize, char *pdata, int datasize)
64 {
65   extern int max_send;
66   int data_to_send = datasize;
67   int params_to_send = paramsize;
68   int useable_space;
69   char *pp = params;
70   char *pd = pdata;
71   int params_sent_thistime, data_sent_thistime, total_sent_thistime;
72   int alignment_offset = 3;
73   int data_alignment_offset = 0;
74
75   /*
76    * Initially set the wcnt area to be 18 - this is true for all
77    * transNT replies.
78    */
79
80   set_message(outbuf,18,0,True);
81
82   if (NT_STATUS_V(nt_error)) {
83           ERROR_NT(nt_error);
84   }
85
86   /* 
87    * If there genuinely are no parameters or data to send just send
88    * the empty packet.
89    */
90
91   if(params_to_send == 0 && data_to_send == 0) {
92     if (!send_smb(smbd_server_fd(),outbuf))
93                 exit_server("send_nt_replies: send_smb failed.");
94     return 0;
95   }
96
97   /*
98    * When sending params and data ensure that both are nicely aligned.
99    * Only do this alignment when there is also data to send - else
100    * can cause NT redirector problems.
101    */
102
103   if (((params_to_send % 4) != 0) && (data_to_send != 0))
104     data_alignment_offset = 4 - (params_to_send % 4);
105
106   /* 
107    * Space is bufsize minus Netbios over TCP header minus SMB header.
108    * The alignment_offset is to align the param bytes on a four byte
109    * boundary (2 bytes for data len, one byte pad). 
110    * NT needs this to work correctly.
111    */
112
113   useable_space = bufsize - ((smb_buf(outbuf)+
114                     alignment_offset+data_alignment_offset) -
115                     outbuf);
116
117   /*
118    * useable_space can never be more than max_send minus the
119    * alignment offset.
120    */
121
122   useable_space = MIN(useable_space,
123                       max_send - (alignment_offset+data_alignment_offset));
124
125
126   while (params_to_send || data_to_send) {
127
128     /*
129      * Calculate whether we will totally or partially fill this packet.
130      */
131
132     total_sent_thistime = params_to_send + data_to_send +
133                             alignment_offset + data_alignment_offset;
134
135     /* 
136      * We can never send more than useable_space.
137      */
138
139     total_sent_thistime = MIN(total_sent_thistime, useable_space);
140
141     set_message(outbuf, 18, total_sent_thistime, True);
142
143     /*
144      * Set total params and data to be sent.
145      */
146
147     SIVAL(outbuf,smb_ntr_TotalParameterCount,paramsize);
148     SIVAL(outbuf,smb_ntr_TotalDataCount,datasize);
149
150     /* 
151      * Calculate how many parameters and data we can fit into
152      * this packet. Parameters get precedence.
153      */
154
155     params_sent_thistime = MIN(params_to_send,useable_space);
156     data_sent_thistime = useable_space - params_sent_thistime;
157     data_sent_thistime = MIN(data_sent_thistime,data_to_send);
158
159     SIVAL(outbuf,smb_ntr_ParameterCount,params_sent_thistime);
160
161     if(params_sent_thistime == 0) {
162       SIVAL(outbuf,smb_ntr_ParameterOffset,0);
163       SIVAL(outbuf,smb_ntr_ParameterDisplacement,0);
164     } else {
165       /*
166        * smb_ntr_ParameterOffset is the offset from the start of the SMB header to the
167        * parameter bytes, however the first 4 bytes of outbuf are
168        * the Netbios over TCP header. Thus use smb_base() to subtract
169        * them from the calculation.
170        */
171
172       SIVAL(outbuf,smb_ntr_ParameterOffset,
173             ((smb_buf(outbuf)+alignment_offset) - smb_base(outbuf)));
174       /* 
175        * Absolute displacement of param bytes sent in this packet.
176        */
177
178       SIVAL(outbuf,smb_ntr_ParameterDisplacement,pp - params);
179     }
180
181     /*
182      * Deal with the data portion.
183      */
184
185     SIVAL(outbuf,smb_ntr_DataCount, data_sent_thistime);
186
187     if(data_sent_thistime == 0) {
188       SIVAL(outbuf,smb_ntr_DataOffset,0);
189       SIVAL(outbuf,smb_ntr_DataDisplacement, 0);
190     } else {
191       /*
192        * The offset of the data bytes is the offset of the
193        * parameter bytes plus the number of parameters being sent this time.
194        */
195
196       SIVAL(outbuf,smb_ntr_DataOffset,((smb_buf(outbuf)+alignment_offset) -
197             smb_base(outbuf)) + params_sent_thistime + data_alignment_offset);
198       SIVAL(outbuf,smb_ntr_DataDisplacement, pd - pdata);
199     }
200
201     /* 
202      * Copy the param bytes into the packet.
203      */
204
205     if(params_sent_thistime)
206       memcpy((smb_buf(outbuf)+alignment_offset),pp,params_sent_thistime);
207
208     /*
209      * Copy in the data bytes
210      */
211
212     if(data_sent_thistime)
213       memcpy(smb_buf(outbuf)+alignment_offset+params_sent_thistime+
214              data_alignment_offset,pd,data_sent_thistime);
215     
216     DEBUG(9,("nt_rep: params_sent_thistime = %d, data_sent_thistime = %d, useable_space = %d\n",
217           params_sent_thistime, data_sent_thistime, useable_space));
218     DEBUG(9,("nt_rep: params_to_send = %d, data_to_send = %d, paramsize = %d, datasize = %d\n",
219           params_to_send, data_to_send, paramsize, datasize));
220     
221     /* Send the packet */
222     if (!send_smb(smbd_server_fd(),outbuf))
223                 exit_server("send_nt_replies: send_smb failed.");
224     
225     pp += params_sent_thistime;
226     pd += data_sent_thistime;
227     
228     params_to_send -= params_sent_thistime;
229     data_to_send -= data_sent_thistime;
230
231     /*
232      * Sanity check
233      */
234
235     if(params_to_send < 0 || data_to_send < 0) {
236       DEBUG(0,("send_nt_replies failed sanity check pts = %d, dts = %d\n!!!",
237             params_to_send, data_to_send));
238       return -1;
239     }
240   } 
241
242   return 0;
243 }
244
245 /****************************************************************************
246  Save case statics.
247 ****************************************************************************/
248
249 static BOOL saved_case_sensitive;
250 static BOOL saved_case_preserve;
251 static BOOL saved_short_case_preserve;
252
253 /****************************************************************************
254  Save case semantics.
255 ****************************************************************************/
256
257 static void set_posix_case_semantics(uint32 file_attributes)
258 {
259         if(!(file_attributes & FILE_FLAG_POSIX_SEMANTICS))
260                 return;
261
262         saved_case_sensitive = case_sensitive;
263         saved_case_preserve = case_preserve;
264         saved_short_case_preserve = short_case_preserve;
265
266         /* Set to POSIX. */
267         case_sensitive = True;
268         case_preserve = True;
269         short_case_preserve = True;
270 }
271
272 /****************************************************************************
273  Restore case semantics.
274 ****************************************************************************/
275
276 static void restore_case_semantics(uint32 file_attributes)
277 {
278         if(!(file_attributes & FILE_FLAG_POSIX_SEMANTICS))
279                 return;
280
281         case_sensitive = saved_case_sensitive;
282         case_preserve = saved_case_preserve;
283         short_case_preserve = saved_short_case_preserve;
284 }
285
286 /****************************************************************************
287  Utility function to map create disposition.
288 ****************************************************************************/
289
290 static int map_create_disposition( uint32 create_disposition)
291 {
292         int ret;
293
294         switch( create_disposition ) {
295                 case FILE_CREATE:
296                         /* create if not exist, fail if exist */
297                         ret = (FILE_CREATE_IF_NOT_EXIST|FILE_EXISTS_FAIL);
298                         break;
299                 case FILE_SUPERSEDE:
300                 case FILE_OVERWRITE_IF:
301                         /* create if not exist, trunc if exist */
302                         ret = (FILE_CREATE_IF_NOT_EXIST|FILE_EXISTS_TRUNCATE);
303                         break;
304                 case FILE_OPEN:
305                         /* fail if not exist, open if exists */
306                         ret = (FILE_FAIL_IF_NOT_EXIST|FILE_EXISTS_OPEN);
307                         break;
308                 case FILE_OPEN_IF:
309                         /* create if not exist, open if exists */
310                         ret = (FILE_CREATE_IF_NOT_EXIST|FILE_EXISTS_OPEN);
311                         break;
312                 case FILE_OVERWRITE:
313                         /* fail if not exist, truncate if exists */
314                         ret = (FILE_FAIL_IF_NOT_EXIST|FILE_EXISTS_TRUNCATE);
315                         break;
316                 default:
317                         DEBUG(0,("map_create_disposition: Incorrect value for create_disposition = %d\n",
318                                 create_disposition ));
319                         return -1;
320         }
321
322         DEBUG(10,("map_create_disposition: Mapped create_disposition 0x%lx to 0x%x\n",
323                         (unsigned long)create_disposition, ret ));
324
325         return ret;
326 }
327
328 /****************************************************************************
329  Utility function to map share modes.
330 ****************************************************************************/
331
332 static int map_share_mode( char *fname, uint32 create_options,
333                         uint32 *desired_access, uint32 share_access, uint32 file_attributes)
334 {
335         int smb_open_mode = -1;
336
337         /*
338          * Convert GENERIC bits to specific bits.
339          */
340
341         se_map_generic(desired_access, &file_generic_mapping);
342
343         switch( *desired_access & (FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA) ) {
344                 case FILE_READ_DATA:
345                         smb_open_mode = DOS_OPEN_RDONLY;
346                         break;
347                 case FILE_WRITE_DATA:
348                 case FILE_APPEND_DATA:
349                 case FILE_WRITE_DATA|FILE_APPEND_DATA:
350                         smb_open_mode = DOS_OPEN_WRONLY;
351                         break;
352                 case FILE_READ_DATA|FILE_WRITE_DATA:
353                 case FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA:
354                 case FILE_READ_DATA|FILE_APPEND_DATA:
355                         smb_open_mode = DOS_OPEN_RDWR;
356                         break;
357         }
358
359         /*
360          * NB. For DELETE_ACCESS we should really check the
361          * directory permissions, as that is what controls
362          * delete, and for WRITE_DAC_ACCESS we should really
363          * check the ownership, as that is what controls the
364          * chmod. Note that this is *NOT* a security hole (this
365          * note is for you, Andrew) as we are not *allowing*
366          * the access at this point, the actual unlink or
367          * chown or chmod call would do this. We are just helping
368          * clients out by telling them if they have a hope
369          * of any of this succeeding. POSIX acls may still
370          * deny the real call. JRA.
371          */
372
373         if (smb_open_mode == -1) {
374
375                 if(*desired_access & (DELETE_ACCESS|WRITE_DAC_ACCESS|WRITE_OWNER_ACCESS|
376                                         FILE_EXECUTE|FILE_READ_ATTRIBUTES|
377                                         FILE_READ_EA|FILE_WRITE_EA|SYSTEM_SECURITY_ACCESS|
378                                         FILE_WRITE_ATTRIBUTES|READ_CONTROL_ACCESS)) {
379                         smb_open_mode = DOS_OPEN_RDONLY;
380                 } else if(*desired_access == 0) {
381
382                         /* 
383                          * JRA - NT seems to sometimes send desired_access as zero. play it safe
384                          * and map to a stat open.
385                          */
386
387                         smb_open_mode = DOS_OPEN_RDONLY;
388
389                 } else {
390                         DEBUG(0,("map_share_mode: Incorrect value 0x%lx for desired_access to file %s\n",
391                                 (unsigned long)*desired_access, fname));
392                         return -1;
393                 }
394         }
395
396         /*
397          * Set the special bit that means allow share delete.
398          * This is held outside the normal share mode bits at 1<<15.
399          * JRA.
400          */
401
402         if(share_access & FILE_SHARE_DELETE) {
403                 smb_open_mode |= ALLOW_SHARE_DELETE;
404                 DEBUG(10,("map_share_mode: FILE_SHARE_DELETE requested. open_mode = 0x%x\n", smb_open_mode));
405         }
406
407         /*
408          * We need to store the intent to open for Delete. This
409          * is what determines if a delete on close flag can be set.
410          * This is the wrong way (and place) to store this, but for 2.2 this
411          * is the only practical way. JRA.
412          */
413
414         if(*desired_access & DELETE_ACCESS) {
415                 DEBUG(10,("map_share_mode: DELETE_ACCESS requested. open_mode = 0x%x\n", smb_open_mode));
416         }
417
418         if (create_options & FILE_DELETE_ON_CLOSE) {
419                 /* Implicit delete access is *NOT* requested... */
420                 smb_open_mode |= DELETE_ON_CLOSE_FLAG;
421                 DEBUG(10,("map_share_mode: FILE_DELETE_ON_CLOSE requested. open_mode = 0x%x\n", smb_open_mode));
422         }
423
424         /* Add in the requested share mode. */
425         switch( share_access & (FILE_SHARE_READ|FILE_SHARE_WRITE)) {
426                 case FILE_SHARE_READ:
427                         smb_open_mode |= SET_DENY_MODE(DENY_WRITE);
428                         break;
429                 case FILE_SHARE_WRITE:
430                         smb_open_mode |= SET_DENY_MODE(DENY_READ);
431                         break;
432                 case (FILE_SHARE_READ|FILE_SHARE_WRITE):
433                         smb_open_mode |= SET_DENY_MODE(DENY_NONE);
434                         break;
435                 case FILE_SHARE_NONE:
436                         smb_open_mode |= SET_DENY_MODE(DENY_ALL);
437                         break;
438         }
439
440         /*
441          * Handle an O_SYNC request.
442          */
443
444         if(file_attributes & FILE_FLAG_WRITE_THROUGH)
445                 smb_open_mode |= FILE_SYNC_OPENMODE;
446
447         DEBUG(10,("map_share_mode: Mapped desired access 0x%lx, share access 0x%lx, file attributes 0x%lx \
448 to open_mode 0x%x\n", (unsigned long)*desired_access, (unsigned long)share_access,
449                 (unsigned long)file_attributes, smb_open_mode ));
450  
451         return smb_open_mode;
452 }
453
454 /****************************************************************************
455  Reply to an NT create and X call on a pipe.
456 ****************************************************************************/
457
458 static int nt_open_pipe(char *fname, connection_struct *conn,
459                         char *inbuf, char *outbuf, int *ppnum)
460 {
461         smb_np_struct *p = NULL;
462
463         uint16 vuid = SVAL(inbuf, smb_uid);
464         int i;
465
466         DEBUG(4,("nt_open_pipe: Opening pipe %s.\n", fname));
467     
468         /* See if it is one we want to handle. */
469
470         if (lp_disable_spoolss() && strequal(fname, "\\spoolss"))
471                 return(ERROR_BOTH(NT_STATUS_OBJECT_NAME_NOT_FOUND,ERRDOS,ERRbadpipe));
472
473         for( i = 0; known_nt_pipes[i]; i++ )
474                 if( strequal(fname,known_nt_pipes[i]))
475                         break;
476     
477         if ( known_nt_pipes[i] == NULL )
478                 return(ERROR_BOTH(NT_STATUS_OBJECT_NAME_NOT_FOUND,ERRDOS,ERRbadpipe));
479     
480         /* Strip \\ off the name. */
481         fname++;
482     
483         DEBUG(3,("nt_open_pipe: Known pipe %s opening.\n", fname));
484
485         p = open_rpc_pipe_p(fname, conn, vuid);
486         if (!p)
487                 return(ERROR_DOS(ERRSRV,ERRnofids));
488
489         *ppnum = p->pnum;
490
491         return 0;
492 }
493
494 /****************************************************************************
495  Reply to an NT create and X call for pipes.
496 ****************************************************************************/
497
498 static int do_ntcreate_pipe_open(connection_struct *conn,
499                          char *inbuf,char *outbuf,int length,int bufsize)
500 {
501         pstring fname;
502         int ret;
503         int pnum = -1;
504         char *p = NULL;
505
506         srvstr_pull_buf(inbuf, fname, smb_buf(inbuf), sizeof(fname), STR_TERMINATE);
507
508         if ((ret = nt_open_pipe(fname, conn, inbuf, outbuf, &pnum)) != 0)
509                 return ret;
510
511         /*
512          * Deal with pipe return.
513          */  
514
515         set_message(outbuf,34,0,True);
516
517         p = outbuf + smb_vwv2;
518         p++;
519         SSVAL(p,0,pnum);
520         p += 2;
521         SIVAL(p,0,FILE_WAS_OPENED);
522         p += 4;
523         p += 32;
524         SIVAL(p,0,FILE_ATTRIBUTE_NORMAL); /* File Attributes. */
525         p += 20;
526         /* File type. */
527         SSVAL(p,0,FILE_TYPE_MESSAGE_MODE_PIPE);
528         /* Device state. */
529         SSVAL(p,2, 0x5FF); /* ? */
530
531         DEBUG(5,("do_ntcreate_pipe_open: open pipe = %s\n", fname));
532
533         return chain_reply(inbuf,outbuf,length,bufsize);
534 }
535
536 /****************************************************************************
537  Reply to an NT create and X call.
538 ****************************************************************************/
539
540 int reply_ntcreate_and_X(connection_struct *conn,
541                          char *inbuf,char *outbuf,int length,int bufsize)
542 {  
543         int result;
544         pstring fname;
545         uint32 flags = IVAL(inbuf,smb_ntcreate_Flags);
546         uint32 desired_access = IVAL(inbuf,smb_ntcreate_DesiredAccess);
547         uint32 file_attributes = IVAL(inbuf,smb_ntcreate_FileAttributes);
548         uint32 share_access = IVAL(inbuf,smb_ntcreate_ShareAccess);
549         uint32 create_disposition = IVAL(inbuf,smb_ntcreate_CreateDisposition);
550         uint32 create_options = IVAL(inbuf,smb_ntcreate_CreateOptions);
551         uint16 root_dir_fid = (uint16)IVAL(inbuf,smb_ntcreate_RootDirectoryFid);
552         int smb_ofun;
553         int smb_open_mode;
554         int smb_attr = (file_attributes & SAMBA_ATTRIBUTES_MASK);
555         /* Breakout the oplock request bits so we can set the
556            reply bits separately. */
557         int oplock_request = 0;
558         mode_t unixmode;
559         int fmode=0,rmode=0;
560         SMB_OFF_T file_len = 0;
561         SMB_STRUCT_STAT sbuf;
562         int smb_action = 0;
563         BOOL bad_path = False;
564         files_struct *fsp=NULL;
565         char *p = NULL;
566         time_t c_time;
567         START_PROFILE(SMBntcreateX);
568
569         /* If it's an IPC, use the pipe handler. */
570
571         if (IS_IPC(conn)) {
572                 if (lp_nt_pipe_support()) {
573                         END_PROFILE(SMBntcreateX);
574                         return do_ntcreate_pipe_open(conn,inbuf,outbuf,length,bufsize);
575                 } else {
576                         END_PROFILE(SMBntcreateX);
577                         return(ERROR_DOS(ERRDOS,ERRbadaccess));
578                 }
579         }
580                         
581
582         /* 
583          * We need to construct the open_and_X ofun value from the
584          * NT values, as that's what our code is structured to accept.
585          */    
586         
587         if((smb_ofun = map_create_disposition( create_disposition )) == -1) {
588                 END_PROFILE(SMBntcreateX);
589                 return(ERROR_DOS(ERRDOS,ERRbadaccess));
590         }
591
592         /*
593          * Get the file name.
594          */
595
596         if(root_dir_fid != 0) {
597                 /*
598                  * This filename is relative to a directory fid.
599                  */
600                 files_struct *dir_fsp = file_fsp(inbuf,smb_ntcreate_RootDirectoryFid);
601                 size_t dir_name_len;
602
603                 if(!dir_fsp) {
604                         END_PROFILE(SMBntcreateX);
605                         return(ERROR_DOS(ERRDOS,ERRbadfid));
606                 }
607
608                 if(!dir_fsp->is_directory) {
609
610                         srvstr_pull_buf(inbuf, fname, smb_buf(inbuf), sizeof(fname), STR_TERMINATE);
611
612                         /* 
613                          * Check to see if this is a mac fork of some kind.
614                          */
615
616                         if( strchr_m(fname, ':')) {
617                                 END_PROFILE(SMBntcreateX);
618                                 return ERROR_NT(NT_STATUS_OBJECT_PATH_NOT_FOUND);
619                         }
620                         END_PROFILE(SMBntcreateX);
621                         return(ERROR_DOS(ERRDOS,ERRbadfid));
622                 }
623
624                 /*
625                  * Copy in the base directory name.
626                  */
627
628                 pstrcpy( fname, dir_fsp->fsp_name );
629                 dir_name_len = strlen(fname);
630
631                 /*
632                  * Ensure it ends in a '\'.
633                  */
634
635                 if(fname[dir_name_len-1] != '\\' && fname[dir_name_len-1] != '/') {
636                         pstrcat(fname, "\\");
637                         dir_name_len++;
638                 }
639
640                 srvstr_pull_buf(inbuf, &fname[dir_name_len], smb_buf(inbuf), sizeof(fname)-dir_name_len, STR_TERMINATE);
641         } else {
642                 srvstr_pull_buf(inbuf, fname, smb_buf(inbuf), sizeof(fname), STR_TERMINATE);
643
644                 /* 
645                  * Check to see if this is a mac fork of some kind.
646                  */
647
648                 if( strchr_m(fname, ':')) {
649                         END_PROFILE(SMBntcreateX);
650                         return ERROR_NT(NT_STATUS_OBJECT_PATH_NOT_FOUND);
651                 }
652         }
653         
654         /*
655          * Now contruct the smb_open_mode value from the filename, 
656          * desired access and the share access.
657          */
658         RESOLVE_DFSPATH(fname, conn, inbuf, outbuf);
659
660         if((smb_open_mode = map_share_mode(fname, create_options, &desired_access, 
661                                            share_access, 
662                                            file_attributes)) == -1) {
663                 END_PROFILE(SMBntcreateX);
664                 return ERROR_DOS(ERRDOS,ERRbadaccess);
665         }
666
667         oplock_request = (flags & REQUEST_OPLOCK) ? EXCLUSIVE_OPLOCK : 0;
668         if (oplock_request) {
669                 oplock_request |= (flags & REQUEST_BATCH_OPLOCK) ? BATCH_OPLOCK : 0;
670         }
671
672         /*
673          * Ordinary file or directory.
674          */
675                 
676         /*
677          * Check if POSIX semantics are wanted.
678          */
679                 
680         set_posix_case_semantics(file_attributes);
681                 
682         unix_convert(fname,conn,0,&bad_path,&sbuf);
683                 
684         unixmode = unix_mode(conn,smb_attr | aARCH, fname);
685     
686         /* 
687          * If it's a request for a directory open, deal with it separately.
688          */
689
690         if(create_options & FILE_DIRECTORY_FILE) {
691                 oplock_request = 0;
692                 
693                 fsp = open_directory(conn, fname, &sbuf, desired_access, smb_open_mode, smb_ofun, unixmode, &smb_action);
694                         
695                 restore_case_semantics(file_attributes);
696
697                 if(!fsp) {
698                         set_bad_path_error(errno, bad_path);
699                         END_PROFILE(SMBntcreateX);
700                         return(UNIXERROR(ERRDOS,ERRnoaccess));
701                 }
702         } else {
703                 /*
704                  * Ordinary file case.
705                  */
706
707                 /* NB. We have a potential bug here. If we
708                  * cause an oplock break to ourselves, then we
709                  * could end up processing filename related
710                  * SMB requests whilst we await the oplock
711                  * break response. As we may have changed the
712                  * filename case semantics to be POSIX-like,
713                  * this could mean a filename request could
714                  * fail when it should succeed. This is a rare
715                  * condition, but eventually we must arrange
716                  * to restore the correct case semantics
717                  * before issuing an oplock break request to
718                  * our client. JRA.  */
719
720                 fsp = open_file_shared1(conn,fname,&sbuf,
721                                         desired_access,
722                                         smb_open_mode,
723                                         smb_ofun,unixmode, oplock_request,
724                                         &rmode,&smb_action);
725
726                 if (!fsp) { 
727                         /* We cheat here. There are two cases we
728                          * care about. One is a directory rename,
729                          * where the NT client will attempt to
730                          * open the source directory for
731                          * DELETE access. Note that when the
732                          * NT client does this it does *not*
733                          * set the directory bit in the
734                          * request packet. This is translated
735                          * into a read/write open
736                          * request. POSIX states that any open
737                          * for write request on a directory
738                          * will generate an EISDIR error, so
739                          * we can catch this here and open a
740                          * pseudo handle that is flagged as a
741                          * directory. The second is an open
742                          * for a permissions read only, which
743                          * we handle in the open_file_stat case. JRA.
744                          */
745
746                         if(errno == EISDIR) {
747
748                                 /*
749                                  * Fail the open if it was explicitly a non-directory file.
750                                  */
751
752                                 if (create_options & FILE_NON_DIRECTORY_FILE) {
753                                         restore_case_semantics(file_attributes);
754                                         SSVAL(outbuf, smb_flg2, 
755                                               SVAL(outbuf,smb_flg2) | FLAGS2_32_BIT_ERROR_CODES);
756                                         END_PROFILE(SMBntcreateX);
757                                         return ERROR_NT(NT_STATUS_FILE_IS_A_DIRECTORY);
758                                 }
759         
760                                 oplock_request = 0;
761                                 fsp = open_directory(conn, fname, &sbuf, desired_access, smb_open_mode, smb_ofun, unixmode, &smb_action);
762                                 
763                                 if(!fsp) {
764                                         restore_case_semantics(file_attributes);
765                                         set_bad_path_error(errno, bad_path);
766                                         END_PROFILE(SMBntcreateX);
767                                         return(UNIXERROR(ERRDOS,ERRnoaccess));
768                                 }
769                         } else {
770
771                                 restore_case_semantics(file_attributes);
772                                 set_bad_path_error(errno, bad_path);
773                                 END_PROFILE(SMBntcreateX);
774                                 return(UNIXERROR(ERRDOS,ERRnoaccess));
775                         }
776                 } 
777         }
778                 
779         restore_case_semantics(file_attributes);
780                 
781         file_len = sbuf.st_size;
782         fmode = dos_mode(conn,fname,&sbuf);
783         if(fmode == 0)
784                 fmode = FILE_ATTRIBUTE_NORMAL;
785         if (!fsp->is_directory && (fmode & aDIR)) {
786                 close_file(fsp,False);
787                 END_PROFILE(SMBntcreateX);
788                 return ERROR_DOS(ERRDOS,ERRnoaccess);
789         } 
790         
791         /* 
792          * If the caller set the extended oplock request bit
793          * and we granted one (by whatever means) - set the
794          * correct bit for extended oplock reply.
795          */
796         
797         if (oplock_request && lp_fake_oplocks(SNUM(conn)))
798                 smb_action |= EXTENDED_OPLOCK_GRANTED;
799         
800         if(oplock_request && EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))
801                 smb_action |= EXTENDED_OPLOCK_GRANTED;
802
803 #if 0
804         /* W2K sends back 42 words here ! If we do the same it breaks offline sync. Go figure... ? JRA. */
805         set_message(outbuf,42,0,True);
806 #else
807         set_message(outbuf,34,0,True);
808 #endif
809         
810         p = outbuf + smb_vwv2;
811         
812         /*
813          * Currently as we don't support level II oplocks we just report
814          * exclusive & batch here.
815          */
816
817         if (smb_action & EXTENDED_OPLOCK_GRANTED) {
818                 if (flags & REQUEST_BATCH_OPLOCK) {
819                         SCVAL(p,0, BATCH_OPLOCK_RETURN);
820                 } else {
821                         SCVAL(p,0, EXCLUSIVE_OPLOCK_RETURN);
822                 }
823         } else if (LEVEL_II_OPLOCK_TYPE(fsp->oplock_type)) {
824                 SCVAL(p,0, LEVEL_II_OPLOCK_RETURN);
825         } else {
826                 SCVAL(p,0,NO_OPLOCK_RETURN);
827         }
828         
829         p++;
830         SSVAL(p,0,fsp->fnum);
831         p += 2;
832         SIVAL(p,0,smb_action);
833         p += 4;
834         
835         /* Create time. */  
836         c_time = get_create_time(&sbuf,lp_fake_dir_create_times(SNUM(conn)));
837
838         if (lp_dos_filetime_resolution(SNUM(conn))) {
839                 c_time &= ~1;
840                 sbuf.st_atime &= ~1;
841                 sbuf.st_mtime &= ~1;
842                 sbuf.st_mtime &= ~1;
843         }
844
845         put_long_date(p,c_time);
846         p += 8;
847         put_long_date(p,sbuf.st_atime); /* access time */
848         p += 8;
849         put_long_date(p,sbuf.st_mtime); /* write time */
850         p += 8;
851         put_long_date(p,sbuf.st_mtime); /* change time */
852         p += 8;
853         SIVAL(p,0,fmode); /* File Attributes. */
854         p += 4;
855         SOFF_T(p, 0, SMB_ROUNDUP_ALLOCATION(file_len));
856         p += 8;
857         SOFF_T(p,0,file_len);
858         p += 12;
859         SCVAL(p,0,fsp->is_directory ? 1 : 0);
860         
861         DEBUG(5,("reply_ntcreate_and_X: fnum = %d, open name = %s\n", fsp->fnum, fsp->fsp_name));
862
863         result = chain_reply(inbuf,outbuf,length,bufsize);
864         END_PROFILE(SMBntcreateX);
865         return result;
866 }
867
868 /****************************************************************************
869  Reply to a NT_TRANSACT_CREATE call to open a pipe.
870 ****************************************************************************/
871
872 static int do_nt_transact_create_pipe( connection_struct *conn,
873                                         char *inbuf, char *outbuf, int length, 
874                                         int bufsize, char **ppsetup, char **ppparams, 
875                                         char **ppdata)
876 {
877         pstring fname;
878         int total_parameter_count = (int)IVAL(inbuf, smb_nt_TotalParameterCount);
879         char *params = *ppparams;
880         int ret;
881         int pnum = -1;
882         char *p = NULL;
883
884         /*
885          * Ensure minimum number of parameters sent.
886          */
887
888         if(total_parameter_count < 54) {
889                 DEBUG(0,("do_nt_transact_create_pipe - insufficient parameters (%u)\n", (unsigned int)total_parameter_count));
890                 return ERROR_DOS(ERRDOS,ERRbadaccess);
891         }
892
893         srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
894
895         if ((ret = nt_open_pipe(fname, conn, inbuf, outbuf, &pnum)) != 0)
896                 return ret;
897         
898         /* Realloc the size of parameters and data we will return */
899         params = Realloc(*ppparams, 69);
900         if(params == NULL)
901                 return ERROR_DOS(ERRDOS,ERRnomem);
902         
903         *ppparams = params;
904         
905         memset((char *)params,'\0',69);
906         
907         p = params;
908         SCVAL(p,0,NO_OPLOCK_RETURN);
909         
910         p += 2;
911         SSVAL(p,0,pnum);
912         p += 2;
913         SIVAL(p,0,FILE_WAS_OPENED);
914         p += 8;
915         
916         p += 32;
917         SIVAL(p,0,FILE_ATTRIBUTE_NORMAL); /* File Attributes. */
918         p += 20;
919         /* File type. */
920         SSVAL(p,0,FILE_TYPE_MESSAGE_MODE_PIPE);
921         /* Device state. */
922         SSVAL(p,2, 0x5FF); /* ? */
923         
924         DEBUG(5,("do_nt_transact_create_pipe: open name = %s\n", fname));
925         
926         /* Send the required number of replies */
927         send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_OK, params, 69, *ppdata, 0);
928         
929         return -1;
930 }
931
932 /****************************************************************************
933  Internal fn to set security descriptors.
934 ****************************************************************************/
935
936 static NTSTATUS set_sd(files_struct *fsp, char *data, uint32 sd_len, uint32 security_info_sent)
937 {
938         prs_struct pd;
939         SEC_DESC *psd = NULL;
940         TALLOC_CTX *mem_ctx;
941         BOOL ret;
942         
943         if (sd_len == 0) {
944                 return NT_STATUS_OK;
945         }
946
947         /*
948          * Init the parse struct we will unmarshall from.
949          */
950
951         if ((mem_ctx = talloc_init()) == NULL) {
952                 DEBUG(0,("set_sd: talloc_init failed.\n"));
953                 return NT_STATUS_NO_MEMORY;
954         }
955
956         prs_init(&pd, 0, mem_ctx, UNMARSHALL);
957
958         /*
959          * Setup the prs_struct to point at the memory we just
960          * allocated.
961          */
962         
963         prs_give_memory( &pd, data, sd_len, False);
964
965         /*
966          * Finally, unmarshall from the data buffer.
967          */
968
969         if(!sec_io_desc( "sd data", &psd, &pd, 1)) {
970                 DEBUG(0,("set_sd: Error in unmarshalling security descriptor.\n"));
971                 /*
972                  * Return access denied for want of a better error message..
973                  */ 
974                 talloc_destroy(mem_ctx);
975                 return NT_STATUS_NO_MEMORY;
976         }
977         
978         if (psd->off_owner_sid==0)
979                 security_info_sent &= ~OWNER_SECURITY_INFORMATION;
980         if (psd->off_grp_sid==0)
981                 security_info_sent &= ~GROUP_SECURITY_INFORMATION;
982         if (psd->off_sacl==0)
983                 security_info_sent &= ~SACL_SECURITY_INFORMATION;
984         if (psd->off_dacl==0)
985                 security_info_sent &= ~DACL_SECURITY_INFORMATION;
986         
987         ret = fsp->conn->vfs_ops.fset_nt_acl( fsp, fsp->fd, security_info_sent, psd);
988         
989         if (!ret) {
990                 talloc_destroy(mem_ctx);
991                 return NT_STATUS_ACCESS_DENIED;
992         }
993         
994         talloc_destroy(mem_ctx);
995         
996         return NT_STATUS_OK;
997 }
998
999 /****************************************************************************
1000  Reply to a NT_TRANSACT_CREATE call (needs to process SD's).
1001 ****************************************************************************/
1002
1003 static int call_nt_transact_create(connection_struct *conn,
1004                                         char *inbuf, char *outbuf, int length, 
1005                                         int bufsize, char **ppsetup, char **ppparams, 
1006                                         char **ppdata)
1007 {
1008         pstring fname;
1009         char *params = *ppparams;
1010         char *data = *ppdata;
1011         int total_parameter_count = (int)IVAL(inbuf, smb_nt_TotalParameterCount);
1012         /* Breakout the oplock request bits so we can set the reply bits separately. */
1013         int oplock_request = 0;
1014         mode_t unixmode;
1015         int fmode=0,rmode=0;
1016         SMB_OFF_T file_len = 0;
1017         SMB_STRUCT_STAT sbuf;
1018         int smb_action = 0;
1019         BOOL bad_path = False;
1020         files_struct *fsp = NULL;
1021         char *p = NULL;
1022         uint32 flags;
1023         uint32 desired_access;
1024         uint32 file_attributes;
1025         uint32 share_access;
1026         uint32 create_disposition;
1027         uint32 create_options;
1028         uint32 sd_len;
1029         uint16 root_dir_fid;
1030         int smb_ofun;
1031         int smb_open_mode;
1032         int smb_attr;
1033         time_t c_time;
1034         NTSTATUS nt_status;
1035
1036         DEBUG(5,("call_nt_transact_create\n"));
1037
1038         /*
1039          * If it's an IPC, use the pipe handler.
1040          */
1041
1042         if (IS_IPC(conn)) {
1043                 if (lp_nt_pipe_support())
1044                         return do_nt_transact_create_pipe(conn, inbuf, outbuf, length, 
1045                                         bufsize, ppsetup, ppparams, ppdata);
1046                 else
1047                         return ERROR_DOS(ERRDOS,ERRbadaccess);
1048         }
1049
1050         /*
1051          * Ensure minimum number of parameters sent.
1052          */
1053
1054         if(total_parameter_count < 54) {
1055                 DEBUG(0,("call_nt_transact_create - insufficient parameters (%u)\n", (unsigned int)total_parameter_count));
1056                 return ERROR_DOS(ERRDOS,ERRbadaccess);
1057         }
1058
1059         flags = IVAL(params,0);
1060         desired_access = IVAL(params,8);
1061         file_attributes = IVAL(params,20);
1062         share_access = IVAL(params,24);
1063         create_disposition = IVAL(params,28);
1064         create_options = IVAL(params,32);
1065         sd_len = IVAL(params,36);
1066         root_dir_fid = (uint16)IVAL(params,4);
1067         smb_attr = (file_attributes & SAMBA_ATTRIBUTES_MASK);
1068
1069         /* 
1070          * We need to construct the open_and_X ofun value from the
1071          * NT values, as that's what our code is structured to accept.
1072          */    
1073
1074         if((smb_ofun = map_create_disposition( create_disposition )) == -1)
1075                 return ERROR_DOS(ERRDOS,ERRbadmem);
1076
1077         /*
1078          * Get the file name.
1079          */
1080
1081         if(root_dir_fid != 0) {
1082                 /*
1083                  * This filename is relative to a directory fid.
1084                  */
1085
1086                 files_struct *dir_fsp = file_fsp(params,4);
1087                 size_t dir_name_len;
1088
1089                 if(!dir_fsp)
1090                         return ERROR_DOS(ERRDOS,ERRbadfid);
1091
1092                 if(!dir_fsp->is_directory) {
1093
1094                         srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
1095
1096                         /*
1097                          * Check to see if this is a mac fork of some kind.
1098                          */
1099
1100                         if( strchr_m(fname, ':'))
1101                                 return ERROR_NT(NT_STATUS_OBJECT_PATH_NOT_FOUND);
1102
1103                         return ERROR_DOS(ERRDOS,ERRbadfid);
1104                 }
1105
1106                 /*
1107                  * Copy in the base directory name.
1108                  */
1109
1110                 pstrcpy( fname, dir_fsp->fsp_name );
1111                 dir_name_len = strlen(fname);
1112
1113                 /*
1114                  * Ensure it ends in a '\'.
1115                  */
1116
1117                 if((fname[dir_name_len-1] != '\\') && (fname[dir_name_len-1] != '/')) {
1118                         pstrcat(fname, "\\");
1119                         dir_name_len++;
1120                 }
1121
1122                 srvstr_pull(inbuf, &fname[dir_name_len], params+53, sizeof(fname)-dir_name_len, 
1123                                 total_parameter_count-53, STR_TERMINATE);
1124         } else {
1125                 srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
1126
1127                 /*
1128                  * Check to see if this is a mac fork of some kind.
1129                  */
1130
1131                 if( strchr_m(fname, ':'))
1132                         return ERROR_NT(NT_STATUS_OBJECT_PATH_NOT_FOUND);
1133         }
1134
1135         /*
1136          * Now contruct the smb_open_mode value from the desired access
1137          * and the share access.
1138          */
1139
1140         if((smb_open_mode = map_share_mode( fname, create_options, &desired_access,
1141                                                 share_access, file_attributes)) == -1)
1142                 return ERROR_DOS(ERRDOS,ERRbadaccess);
1143
1144         oplock_request = (flags & REQUEST_OPLOCK) ? EXCLUSIVE_OPLOCK : 0;
1145         oplock_request |= (flags & REQUEST_BATCH_OPLOCK) ? BATCH_OPLOCK : 0;
1146
1147         /*
1148          * Check if POSIX semantics are wanted.
1149          */
1150
1151         set_posix_case_semantics(file_attributes);
1152     
1153         RESOLVE_DFSPATH(fname, conn, inbuf, outbuf);
1154
1155         unix_convert(fname,conn,0,&bad_path,&sbuf);
1156     
1157         unixmode = unix_mode(conn,smb_attr | aARCH, fname);
1158    
1159         /*
1160          * If it's a request for a directory open, deal with it separately.
1161          */
1162
1163         if(create_options & FILE_DIRECTORY_FILE) {
1164
1165                 oplock_request = 0;
1166
1167                 /*
1168                  * We will get a create directory here if the Win32
1169                  * app specified a security descriptor in the 
1170                  * CreateDirectory() call.
1171                  */
1172
1173                 fsp = open_directory(conn, fname, &sbuf, desired_access, smb_open_mode, smb_ofun, unixmode, &smb_action);
1174
1175                 if(!fsp) {
1176                         restore_case_semantics(file_attributes);
1177                         set_bad_path_error(errno, bad_path);
1178                         return(UNIXERROR(ERRDOS,ERRnoaccess));
1179                 }
1180
1181         } else {
1182
1183                 /*
1184                  * Ordinary file case.
1185                  */
1186
1187                 fsp = open_file_shared1(conn,fname,&sbuf,desired_access,
1188                                                 smb_open_mode,smb_ofun,unixmode,
1189                                                 oplock_request,&rmode,&smb_action);
1190
1191                 if (!fsp) { 
1192
1193                         if(errno == EISDIR) {
1194
1195                                 /*
1196                                  * Fail the open if it was explicitly a non-directory file.
1197                                  */
1198
1199                                 if (create_options & FILE_NON_DIRECTORY_FILE) {
1200                                         restore_case_semantics(file_attributes);
1201                                         SSVAL(outbuf, smb_flg2, SVAL(outbuf,smb_flg2) | FLAGS2_32_BIT_ERROR_CODES);
1202                                         return ERROR_NT(NT_STATUS_FILE_IS_A_DIRECTORY);
1203                                 }
1204         
1205                                 oplock_request = 0;
1206                                 fsp = open_directory(conn, fname, &sbuf, desired_access, smb_open_mode, smb_ofun, unixmode, &smb_action);
1207                                 
1208                                 if(!fsp) {
1209                                         restore_case_semantics(file_attributes);
1210                                         set_bad_path_error(errno, bad_path);
1211                                         return(UNIXERROR(ERRDOS,ERRnoaccess));
1212                                 }
1213                         } else {
1214                                 restore_case_semantics(file_attributes);
1215                                 set_bad_path_error(errno, bad_path);
1216                                 return(UNIXERROR(ERRDOS,ERRnoaccess));
1217                         }
1218                 } 
1219   
1220                 file_len = sbuf.st_size;
1221                 fmode = dos_mode(conn,fname,&sbuf);
1222                 if(fmode == 0)
1223                         fmode = FILE_ATTRIBUTE_NORMAL;
1224
1225                 if (fmode & aDIR) {
1226                         close_file(fsp,False);
1227                         restore_case_semantics(file_attributes);
1228                         return ERROR_DOS(ERRDOS,ERRnoaccess);
1229                 } 
1230
1231                 /* 
1232                  * If the caller set the extended oplock request bit
1233                  * and we granted one (by whatever means) - set the
1234                  * correct bit for extended oplock reply.
1235                  */
1236     
1237                 if (oplock_request && lp_fake_oplocks(SNUM(conn)))
1238                         smb_action |= EXTENDED_OPLOCK_GRANTED;
1239   
1240                 if(oplock_request && EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))
1241                         smb_action |= EXTENDED_OPLOCK_GRANTED;
1242         }
1243
1244         /*
1245          * Now try and apply the desired SD.
1246          */
1247
1248         if (sd_len && !NT_STATUS_IS_OK(nt_status = set_sd( fsp, data, sd_len, ALL_SECURITY_INFORMATION))) {
1249                 close_file(fsp,False);
1250                 restore_case_semantics(file_attributes);
1251                 return ERROR_NT(nt_status);
1252         }
1253         
1254         restore_case_semantics(file_attributes);
1255
1256         /* Realloc the size of parameters and data we will return */
1257         params = Realloc(*ppparams, 69);
1258         if(params == NULL)
1259                 return ERROR_DOS(ERRDOS,ERRnomem);
1260
1261         *ppparams = params;
1262
1263         memset((char *)params,'\0',69);
1264
1265         p = params;
1266         if (smb_action & EXTENDED_OPLOCK_GRANTED)       
1267                 SCVAL(p,0, BATCH_OPLOCK_RETURN);
1268         else if (LEVEL_II_OPLOCK_TYPE(fsp->oplock_type))
1269                 SCVAL(p,0, LEVEL_II_OPLOCK_RETURN);
1270         else
1271                 SCVAL(p,0,NO_OPLOCK_RETURN);
1272         
1273         p += 2;
1274         SSVAL(p,0,fsp->fnum);
1275         p += 2;
1276         SIVAL(p,0,smb_action);
1277         p += 8;
1278
1279         /* Create time. */
1280         c_time = get_create_time(&sbuf,lp_fake_dir_create_times(SNUM(conn)));
1281
1282         if (lp_dos_filetime_resolution(SNUM(conn))) {
1283                 c_time &= ~1;
1284                 sbuf.st_atime &= ~1;
1285                 sbuf.st_mtime &= ~1;
1286                 sbuf.st_mtime &= ~1;
1287         }
1288
1289         put_long_date(p,c_time);
1290         p += 8;
1291         put_long_date(p,sbuf.st_atime); /* access time */
1292         p += 8;
1293         put_long_date(p,sbuf.st_mtime); /* write time */
1294         p += 8;
1295         put_long_date(p,sbuf.st_mtime); /* change time */
1296         p += 8;
1297         SIVAL(p,0,fmode); /* File Attributes. */
1298         p += 4;
1299         SOFF_T(p, 0, SMB_ROUNDUP_ALLOCATION(file_len));
1300         p += 8;
1301         SOFF_T(p,0,file_len);
1302
1303         DEBUG(5,("call_nt_transact_create: open name = %s\n", fname));
1304
1305         /* Send the required number of replies */
1306         send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_OK, params, 69, *ppdata, 0);
1307
1308         return -1;
1309 }
1310
1311 /****************************************************************************
1312  Reply to a NT CANCEL request.
1313 ****************************************************************************/
1314 int reply_ntcancel(connection_struct *conn,
1315                    char *inbuf,char *outbuf,int length,int bufsize)
1316 {
1317         /*
1318          * Go through and cancel any pending change notifies.
1319          */
1320         
1321         int mid = SVAL(inbuf,smb_mid);
1322         START_PROFILE(SMBntcancel);
1323         remove_pending_change_notify_requests_by_mid(mid);
1324         remove_pending_lock_requests_by_mid(mid);
1325         
1326         DEBUG(3,("reply_ntcancel: cancel called on mid = %d.\n", mid));
1327
1328         END_PROFILE(SMBntcancel);
1329         return(-1);
1330 }
1331
1332 /****************************************************************************
1333  Reply to an unsolicited SMBNTtranss - just ignore it!
1334 ****************************************************************************/
1335 int reply_nttranss(connection_struct *conn,
1336                    char *inbuf,char *outbuf,int length,int bufsize)
1337 {
1338         START_PROFILE(SMBnttranss);
1339         DEBUG(4,("Ignoring nttranss of length %d\n",length));
1340         END_PROFILE(SMBnttranss);
1341         return(-1);
1342 }
1343
1344 /****************************************************************************
1345  Reply to a notify change - queue the request and 
1346  don't allow a directory to be opened.
1347 ****************************************************************************/
1348 static int call_nt_transact_notify_change(connection_struct *conn,
1349                                    char *inbuf, char *outbuf, int length,
1350                                    int bufsize, 
1351                                    char **ppsetup, 
1352                                    char **ppparams, char **ppdata)
1353 {
1354         char *setup = *ppsetup;
1355         files_struct *fsp;
1356         uint32 flags;
1357
1358         fsp = file_fsp(setup,4);
1359         flags = IVAL(setup, 0);
1360
1361         DEBUG(3,("call_nt_transact_notify_change\n"));
1362
1363         if(!fsp)
1364                 return ERROR_DOS(ERRDOS,ERRbadfid);
1365
1366         if((!fsp->is_directory) || (conn != fsp->conn))
1367                 return ERROR_DOS(ERRDOS,ERRbadfid);
1368
1369         if (!change_notify_set(inbuf, fsp, conn, flags))
1370                 return(UNIXERROR(ERRDOS,ERRbadfid));
1371
1372         DEBUG(3,("call_nt_transact_notify_change: notify change called on directory \
1373 name = %s\n", fsp->fsp_name ));
1374
1375         return -1;
1376 }
1377
1378 /****************************************************************************
1379  Reply to an NT transact rename command.
1380 ****************************************************************************/
1381
1382 static int call_nt_transact_rename(connection_struct *conn,
1383                                    char *inbuf, char *outbuf, int length, 
1384                                    int bufsize,
1385                                    char **ppsetup, char **ppparams, char **ppdata)
1386 {
1387         char *params = *ppparams;
1388         pstring new_name;
1389         files_struct *fsp = file_fsp(params, 0);
1390         BOOL replace_if_exists = (SVAL(params,2) & RENAME_REPLACE_IF_EXISTS) ? True : False;
1391         NTSTATUS status;
1392
1393         CHECK_FSP(fsp, conn);
1394         srvstr_pull(inbuf, new_name, params+4, sizeof(new_name), -1, STR_TERMINATE);
1395
1396         status = rename_internals(conn, fsp->fsp_name,
1397                                   new_name, replace_if_exists);
1398         if (!NT_STATUS_IS_OK(status))
1399                 return ERROR_NT(status);
1400
1401         /*
1402          * Rename was successful.
1403          */
1404         send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_OK, NULL, 0, NULL, 0);
1405         
1406         DEBUG(3,("nt transact rename from = %s, to = %s succeeded.\n", 
1407                  fsp->fsp_name, new_name));
1408         
1409         /*
1410          * Win2k needs a changenotify request response before it will
1411          * update after a rename..
1412          */
1413         
1414         process_pending_change_notify_queue((time_t)0);
1415
1416         return -1;
1417 }
1418
1419 /******************************************************************************
1420  Fake up a completely empty SD.
1421 *******************************************************************************/
1422
1423 static size_t get_null_nt_acl(TALLOC_CTX *mem_ctx, SEC_DESC **ppsd)
1424 {
1425         extern DOM_SID global_sid_World;
1426         size_t sd_size;
1427
1428         *ppsd = make_standard_sec_desc( mem_ctx, &global_sid_World, &global_sid_World, NULL, &sd_size);
1429         if(!*ppsd) {
1430                 DEBUG(0,("get_null_nt_acl: Unable to malloc space for security descriptor.\n"));
1431                 sd_size = 0;
1432         }
1433
1434         return sd_size;
1435 }
1436
1437 /****************************************************************************
1438  Reply to query a security descriptor - currently this is not implemented (it
1439  is planned to be though). Right now it just returns the same thing NT would
1440  when queried on a FAT filesystem. JRA.
1441 ****************************************************************************/
1442
1443 static int call_nt_transact_query_security_desc(connection_struct *conn,
1444                                                 char *inbuf, char *outbuf, 
1445                                                 int length, int bufsize, 
1446                                                 char **ppsetup, char **ppparams, char **ppdata)
1447 {
1448   uint32 max_data_count = IVAL(inbuf,smb_nt_MaxDataCount);
1449   char *params = *ppparams;
1450   char *data = *ppdata;
1451   prs_struct pd;
1452   SEC_DESC *psd = NULL;
1453   size_t sd_size;
1454   TALLOC_CTX *mem_ctx;
1455
1456   files_struct *fsp = file_fsp(params,0);
1457
1458   if(!fsp)
1459     return ERROR_DOS(ERRDOS,ERRbadfid);
1460
1461   DEBUG(3,("call_nt_transact_query_security_desc: file = %s\n", fsp->fsp_name ));
1462
1463   params = Realloc(*ppparams, 4);
1464   if(params == NULL)
1465     return ERROR_DOS(ERRDOS,ERRnomem);
1466
1467   *ppparams = params;
1468
1469   if ((mem_ctx = talloc_init()) == NULL) {
1470     DEBUG(0,("call_nt_transact_query_security_desc: talloc_init failed.\n"));
1471     return ERROR_DOS(ERRDOS,ERRnomem);
1472   }
1473
1474   /*
1475    * Get the permissions to return.
1476    */
1477
1478   if (!lp_nt_acl_support(SNUM(conn)))
1479     sd_size = get_null_nt_acl(mem_ctx, &psd);
1480   else
1481     sd_size = conn->vfs_ops.fget_nt_acl(fsp, fsp->fd, &psd);
1482
1483   if (sd_size == 0) {
1484     talloc_destroy(mem_ctx);
1485     return(UNIXERROR(ERRDOS,ERRnoaccess));
1486   }
1487
1488   DEBUG(3,("call_nt_transact_query_security_desc: sd_size = %d.\n",(int)sd_size));
1489
1490   SIVAL(params,0,(uint32)sd_size);
1491
1492   if(max_data_count < sd_size) {
1493
1494     send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_BUFFER_TOO_SMALL,
1495                     params, 4, *ppdata, 0);
1496     talloc_destroy(mem_ctx);
1497     return -1;
1498   }
1499
1500   /*
1501    * Allocate the data we will point this at.
1502    */
1503
1504   data = Realloc(*ppdata, sd_size);
1505   if(data == NULL) {
1506     talloc_destroy(mem_ctx);
1507     return ERROR_DOS(ERRDOS,ERRnomem);
1508   }
1509
1510   *ppdata = data;
1511
1512   memset(data, '\0', sd_size);
1513
1514   /*
1515    * Init the parse struct we will marshall into.
1516    */
1517
1518   prs_init(&pd, 0, mem_ctx, MARSHALL);
1519
1520   /*
1521    * Setup the prs_struct to point at the memory we just
1522    * allocated.
1523    */
1524
1525   prs_give_memory( &pd, data, (uint32)sd_size, False);
1526
1527   /*
1528    * Finally, linearize into the outgoing buffer.
1529    */
1530
1531   if(!sec_io_desc( "sd data", &psd, &pd, 1)) {
1532     DEBUG(0,("call_nt_transact_query_security_desc: Error in marshalling \
1533 security descriptor.\n"));
1534     /*
1535      * Return access denied for want of a better error message..
1536      */ 
1537     talloc_destroy(mem_ctx);
1538     return(UNIXERROR(ERRDOS,ERRnoaccess));
1539   }
1540
1541   /*
1542    * Now we can delete the security descriptor.
1543    */
1544
1545   talloc_destroy(mem_ctx);
1546
1547   send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_OK, params, 4, data, (int)sd_size);
1548   return -1;
1549 }
1550
1551 /****************************************************************************
1552  Reply to set a security descriptor. Map to UNIX perms.
1553 ****************************************************************************/
1554
1555 static int call_nt_transact_set_security_desc(connection_struct *conn,
1556                                                                         char *inbuf, char *outbuf, int length,
1557                                                                         int bufsize, char **ppsetup, 
1558                                                                         char **ppparams, char **ppdata)
1559 {
1560         uint32 total_parameter_count = IVAL(inbuf, smb_nts_TotalParameterCount);
1561         char *params= *ppparams;
1562         char *data = *ppdata;
1563         uint32 total_data_count = (uint32)IVAL(inbuf, smb_nts_TotalDataCount);
1564         files_struct *fsp = NULL;
1565         uint32 security_info_sent = 0;
1566         NTSTATUS nt_status;
1567
1568         if(total_parameter_count < 8)
1569                 return ERROR_DOS(ERRDOS,ERRbadfunc);
1570
1571         if((fsp = file_fsp(params,0)) == NULL)
1572                 return ERROR_DOS(ERRDOS,ERRbadfid);
1573
1574         if(!lp_nt_acl_support(SNUM(conn)))
1575                 goto done;
1576
1577         security_info_sent = IVAL(params,4);
1578
1579         DEBUG(3,("call_nt_transact_set_security_desc: file = %s, sent 0x%x\n", fsp->fsp_name,
1580                 (unsigned int)security_info_sent ));
1581
1582         if (total_data_count == 0)
1583                 return ERROR_DOS(ERRDOS, ERRbadaccess);
1584
1585         if (!NT_STATUS_IS_OK(nt_status = set_sd( fsp, data, total_data_count, security_info_sent)))
1586                 return ERROR_NT(nt_status);
1587
1588   done:
1589
1590         send_nt_replies(inbuf, outbuf, bufsize, NT_STATUS_OK, NULL, 0, NULL, 0);
1591         return -1;
1592 }
1593    
1594 /****************************************************************************
1595  Reply to IOCTL - not implemented - no plans.
1596 ****************************************************************************/
1597
1598 static int call_nt_transact_ioctl(connection_struct *conn,
1599                                   char *inbuf, char *outbuf, int length,
1600                                   int bufsize, 
1601                                   char **ppsetup, char **ppparams, char **ppdata)
1602 {
1603         static BOOL logged_message = False;
1604
1605         if(!logged_message) {
1606                 DEBUG(3,("call_nt_transact_ioctl: Currently not implemented.\n"));
1607                 logged_message = True; /* Only print this once... */
1608         }
1609         return ERROR_DOS(ERRSRV,ERRnosupport);
1610 }
1611    
1612 /****************************************************************************
1613  Reply to a SMBNTtrans.
1614 ****************************************************************************/
1615 int reply_nttrans(connection_struct *conn,
1616                   char *inbuf,char *outbuf,int length,int bufsize)
1617 {
1618   int  outsize = 0;
1619 #if 0 /* Not used. */
1620   uint16 max_setup_count = CVAL(inbuf, smb_nt_MaxSetupCount);
1621   uint32 max_parameter_count = IVAL(inbuf, smb_nt_MaxParameterCount);
1622   uint32 max_data_count = IVAL(inbuf,smb_nt_MaxDataCount);
1623 #endif /* Not used. */
1624   uint32 total_parameter_count = IVAL(inbuf, smb_nt_TotalParameterCount);
1625   uint32 total_data_count = IVAL(inbuf, smb_nt_TotalDataCount);
1626   uint32 parameter_count = IVAL(inbuf,smb_nt_ParameterCount);
1627   uint32 parameter_offset = IVAL(inbuf,smb_nt_ParameterOffset);
1628   uint32 data_count = IVAL(inbuf,smb_nt_DataCount);
1629   uint32 data_offset = IVAL(inbuf,smb_nt_DataOffset);
1630   uint16 setup_count = 2*CVAL(inbuf,smb_nt_SetupCount); /* setup count is in *words* */
1631   uint16 function_code = SVAL( inbuf, smb_nt_Function);
1632   char *params = NULL, *data = NULL, *setup = NULL;
1633   uint32 num_params_sofar, num_data_sofar;
1634   START_PROFILE(SMBnttrans);
1635
1636   if(global_oplock_break && (function_code == NT_TRANSACT_CREATE)) {
1637     /*
1638      * Queue this open message as we are the process of an oplock break.
1639      */
1640
1641     DEBUG(2,("reply_nttrans: queueing message NT_TRANSACT_CREATE \
1642 due to being in oplock break state.\n" ));
1643
1644     push_oplock_pending_smb_message( inbuf, length);
1645     END_PROFILE(SMBnttrans);
1646     return -1;
1647   }
1648
1649   if (IS_IPC(conn) && (function_code != NT_TRANSACT_CREATE)) {
1650     END_PROFILE(SMBnttrans);
1651     return ERROR_DOS(ERRSRV,ERRaccess);
1652   }
1653
1654   outsize = set_message(outbuf,0,0,True);
1655
1656   /* 
1657    * All nttrans messages we handle have smb_wct == 19 + setup_count.
1658    * Ensure this is so as a sanity check.
1659    */
1660
1661   if(CVAL(inbuf, smb_wct) != 19 + (setup_count/2)) {
1662     DEBUG(2,("Invalid smb_wct %d in nttrans call (should be %d)\n",
1663           CVAL(inbuf, smb_wct), 19 + (setup_count/2)));
1664     END_PROFILE(SMBnttrans);
1665     return ERROR_DOS(ERRSRV,ERRerror);
1666   }
1667     
1668   /* Allocate the space for the setup, the maximum needed parameters and data */
1669
1670   if(setup_count > 0)
1671     setup = (char *)malloc(setup_count);
1672   if (total_parameter_count > 0)
1673     params = (char *)malloc(total_parameter_count);
1674   if (total_data_count > 0)
1675     data = (char *)malloc(total_data_count);
1676  
1677   if ((total_parameter_count && !params)  || (total_data_count && !data) ||
1678       (setup_count && !setup)) {
1679         SAFE_FREE(setup);
1680         SAFE_FREE(params);
1681         SAFE_FREE(data);
1682     DEBUG(0,("reply_nttrans : Out of memory\n"));
1683     END_PROFILE(SMBnttrans);
1684     return ERROR_DOS(ERRDOS,ERRnomem);
1685   }
1686
1687   /* Copy the param and data bytes sent with this request into
1688      the params buffer */
1689   num_params_sofar = parameter_count;
1690   num_data_sofar = data_count;
1691
1692   if (parameter_count > total_parameter_count || data_count > total_data_count)
1693     exit_server("reply_nttrans: invalid sizes in packet.");
1694
1695   if(setup) {
1696     memcpy( setup, &inbuf[smb_nt_SetupStart], setup_count);
1697     DEBUG(10,("reply_nttrans: setup_count = %d\n", setup_count));
1698     dump_data(10, setup, setup_count);
1699   }
1700   if(params) {
1701     memcpy( params, smb_base(inbuf) + parameter_offset, parameter_count);
1702     DEBUG(10,("reply_nttrans: parameter_count = %d\n", parameter_count));
1703     dump_data(10, params, parameter_count);
1704   }
1705   if(data) {
1706     memcpy( data, smb_base(inbuf) + data_offset, data_count);
1707     DEBUG(10,("reply_nttrans: data_count = %d\n",data_count));
1708     dump_data(10, data, data_count);
1709   }
1710
1711   if(num_data_sofar < total_data_count || num_params_sofar < total_parameter_count) {
1712     /* We need to send an interim response then receive the rest
1713        of the parameter/data bytes */
1714     outsize = set_message(outbuf,0,0,True);
1715     if (!send_smb(smbd_server_fd(),outbuf))
1716       exit_server("reply_nttrans: send_smb failed.");
1717
1718     while( num_data_sofar < total_data_count || num_params_sofar < total_parameter_count) {
1719       BOOL ret;
1720
1721       ret = receive_next_smb(inbuf,bufsize,SMB_SECONDARY_WAIT);
1722
1723       if((ret && (CVAL(inbuf, smb_com) != SMBnttranss)) || !ret) {
1724         outsize = set_message(outbuf,0,0,True);
1725         if(ret) {
1726                 DEBUG(0,("reply_nttrans: Invalid secondary nttrans packet\n"));
1727         } else {
1728                 DEBUG(0,("reply_nttrans: %s in getting secondary nttrans response.\n",
1729                          (smb_read_error == READ_ERROR) ? "error" : "timeout" ));
1730         }
1731         SAFE_FREE(params);
1732         SAFE_FREE(data);
1733         SAFE_FREE(setup);
1734         END_PROFILE(SMBnttrans);
1735         return ERROR_DOS(ERRSRV,ERRerror);
1736       }
1737       
1738       /* Revise total_params and total_data in case they have changed downwards */
1739       total_parameter_count = IVAL(inbuf, smb_nts_TotalParameterCount);
1740       total_data_count = IVAL(inbuf, smb_nts_TotalDataCount);
1741       num_params_sofar += (parameter_count = IVAL(inbuf,smb_nts_ParameterCount));
1742       num_data_sofar += ( data_count = IVAL(inbuf, smb_nts_DataCount));
1743       if (num_params_sofar > total_parameter_count || num_data_sofar > total_data_count)
1744         exit_server("reply_nttrans2: data overflow in secondary nttrans packet");
1745
1746       memcpy( &params[ IVAL(inbuf, smb_nts_ParameterDisplacement)], 
1747               smb_base(inbuf) + IVAL(inbuf, smb_nts_ParameterOffset), parameter_count);
1748       memcpy( &data[IVAL(inbuf, smb_nts_DataDisplacement)],
1749               smb_base(inbuf)+ IVAL(inbuf, smb_nts_DataOffset), data_count);
1750     }
1751   }
1752
1753   if (Protocol >= PROTOCOL_NT1)
1754     SSVAL(outbuf,smb_flg2,SVAL(outbuf,smb_flg2) | FLAGS2_IS_LONG_NAME);
1755
1756   /* Now we must call the relevant NT_TRANS function */
1757   switch(function_code) {
1758     case NT_TRANSACT_CREATE:
1759       START_PROFILE_NESTED(NT_transact_create);
1760       outsize = call_nt_transact_create(conn, inbuf, outbuf, length, bufsize, 
1761                                         &setup, &params, &data);
1762       END_PROFILE_NESTED(NT_transact_create);
1763       break;
1764     case NT_TRANSACT_IOCTL:
1765       START_PROFILE_NESTED(NT_transact_ioctl);
1766       outsize = call_nt_transact_ioctl(conn, 
1767                                        inbuf, outbuf, length, bufsize, 
1768                                        &setup, &params, &data);
1769       END_PROFILE_NESTED(NT_transact_ioctl);
1770       break;
1771     case NT_TRANSACT_SET_SECURITY_DESC:
1772       START_PROFILE_NESTED(NT_transact_set_security_desc);
1773       outsize = call_nt_transact_set_security_desc(conn, inbuf, outbuf, 
1774                                                    length, bufsize, 
1775                                                    &setup, &params, &data);
1776       END_PROFILE_NESTED(NT_transact_set_security_desc);
1777       break;
1778     case NT_TRANSACT_NOTIFY_CHANGE:
1779       START_PROFILE_NESTED(NT_transact_notify_change);
1780       outsize = call_nt_transact_notify_change(conn, inbuf, outbuf, 
1781                                                length, bufsize, 
1782                                                &setup, &params, &data);
1783       END_PROFILE_NESTED(NT_transact_notify_change);
1784       break;
1785     case NT_TRANSACT_RENAME:
1786       START_PROFILE_NESTED(NT_transact_rename);
1787       outsize = call_nt_transact_rename(conn, inbuf, outbuf, length, 
1788                                         bufsize, 
1789                                         &setup, &params, &data);
1790       END_PROFILE_NESTED(NT_transact_rename);
1791       break;
1792
1793     case NT_TRANSACT_QUERY_SECURITY_DESC:
1794       START_PROFILE_NESTED(NT_transact_query_security_desc);
1795       outsize = call_nt_transact_query_security_desc(conn, inbuf, outbuf, 
1796                                                      length, bufsize, 
1797                                                      &setup, &params, &data);
1798       END_PROFILE_NESTED(NT_transact_query_security_desc);
1799       break;
1800   default:
1801           /* Error in request */
1802           DEBUG(0,("reply_nttrans: Unknown request %d in nttrans call\n", function_code));
1803           SAFE_FREE(setup);
1804           SAFE_FREE(params);
1805           SAFE_FREE(data);
1806           END_PROFILE(SMBnttrans);
1807           return ERROR_DOS(ERRSRV,ERRerror);
1808   }
1809
1810   /* As we do not know how many data packets will need to be
1811      returned here the various call_nt_transact_xxxx calls
1812      must send their own. Thus a call_nt_transact_xxxx routine only
1813      returns a value other than -1 when it wants to send
1814      an error packet. 
1815   */
1816
1817   SAFE_FREE(setup);
1818   SAFE_FREE(params);
1819   SAFE_FREE(data);
1820   END_PROFILE(SMBnttrans);
1821   return outsize; /* If a correct response was needed the call_nt_transact_xxxx 
1822                      calls have already sent it. If outsize != -1 then it is
1823                      returning an error packet. */
1824 }