Use pidl for _srvsvc_NetShareDel and _srvsvc_NetShareDelSticky.
[samba.git] / source3 / rpc_server / srv_srvsvc_nt.c
1 /*
2  *  Unix SMB/CIFS implementation.
3  *  RPC Pipe client / server routines
4  *  Copyright (C) Andrew Tridgell              1992-1997,
5  *  Copyright (C) Jeremy Allison               2001.
6  *  Copyright (C) Nigel Williams               2001.
7  *  Copyright (C) Gerald (Jerry) Carter        2006.
8  *
9  *  This program is free software; you can redistribute it and/or modify
10  *  it under the terms of the GNU General Public License as published by
11  *  the Free Software Foundation; either version 3 of the License, or
12  *  (at your option) any later version.
13  *
14  *  This program is distributed in the hope that it will be useful,
15  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  *  GNU General Public License for more details.
18  *
19  *  You should have received a copy of the GNU General Public License
20  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
21  */
22
23 /* This is the implementation of the srvsvc pipe. */
24
25 #include "includes.h"
26
27 extern const struct generic_mapping file_generic_mapping;
28
29 #undef DBGC_CLASS
30 #define DBGC_CLASS DBGC_RPC_SRV
31
32 /* Use for enumerating connections, pipes, & files */
33
34 struct file_enum_count {
35         TALLOC_CTX *ctx;
36         const char *username;
37         int count;
38         FILE_INFO_3 *info;
39 };
40
41 struct sess_file_count {
42         struct server_id pid;
43         uid_t uid;
44         int count;
45 };
46
47 /****************************************************************************
48  Count the entries belonging to a service in the connection db.
49 ****************************************************************************/
50
51 static int pipe_enum_fn( struct db_record *rec, void *p)
52 {
53         struct pipe_open_rec prec;
54         struct file_enum_count *fenum = (struct file_enum_count *)p;
55         FILE_INFO_3 *f;
56         int i = fenum->count;
57         char *fullpath = NULL;
58         const char *username;
59
60         if (rec->value.dsize != sizeof(struct pipe_open_rec))
61                 return 0;
62
63         memcpy(&prec, rec->value.dptr, sizeof(struct pipe_open_rec));
64
65         if ( !process_exists(prec.pid) ) {
66                 return 0;
67         }
68
69         username = uidtoname(prec.uid);
70
71         if ((fenum->username != NULL)
72             && !strequal(username, fenum->username)) {
73                 return 0;
74         }
75
76         fullpath = talloc_asprintf(fenum->ctx, "\\PIPE\\%s", prec.name );
77         if (!fullpath) {
78                 return 1;
79         }
80
81         f = TALLOC_REALLOC_ARRAY( fenum->ctx, fenum->info, FILE_INFO_3, i+1 );
82         if ( !f ) {
83                 DEBUG(0,("conn_enum_fn: realloc failed for %d items\n", i+1));
84                 return 1;
85         }
86         fenum->info = f;
87
88         init_srv_file_info3(
89                 &fenum->info[i],
90                 (uint32)((procid_to_pid(&prec.pid)<<16) & prec.pnum),
91                 (FILE_READ_DATA|FILE_WRITE_DATA),
92                 0, username, fullpath);
93
94         TALLOC_FREE(fullpath);
95         fenum->count++;
96
97         return 0;
98 }
99
100 /*******************************************************************
101 ********************************************************************/
102
103 static WERROR net_enum_pipes( TALLOC_CTX *ctx, const char *username,
104                               FILE_INFO_3 **info,
105                               uint32 *count, uint32 resume )
106 {
107         struct file_enum_count fenum;
108
109         fenum.ctx = ctx;
110         fenum.username = username;
111         fenum.count = *count;
112         fenum.info = *info;
113
114         if (connections_traverse(pipe_enum_fn, &fenum) == -1) {
115                 DEBUG(0,("net_enum_pipes: traverse of connections.tdb "
116                          "failed\n"));
117                 return WERR_NOMEM;
118         }
119
120         *info  = fenum.info;
121         *count = fenum.count;
122
123         return WERR_OK;
124 }
125
126 /*******************************************************************
127 ********************************************************************/
128
129 static void enum_file_fn( const struct share_mode_entry *e,
130                           const char *sharepath, const char *fname,
131                           void *private_data )
132 {
133         struct file_enum_count *fenum =
134                 (struct file_enum_count *)private_data;
135
136         FILE_INFO_3 *f;
137         int i = fenum->count;
138         files_struct fsp;
139         struct byte_range_lock *brl;
140         int num_locks = 0;
141         char *fullpath = NULL;
142         uint32 permissions;
143         const char *username;
144
145         /* If the pid was not found delete the entry from connections.tdb */
146
147         if ( !process_exists(e->pid) ) {
148                 return;
149         }
150
151         username = uidtoname(e->uid);
152
153         if ((fenum->username != NULL)
154             && !strequal(username, fenum->username)) {
155                 return;
156         }
157
158         f = TALLOC_REALLOC_ARRAY( fenum->ctx, fenum->info, FILE_INFO_3, i+1 );
159         if ( !f ) {
160                 DEBUG(0,("conn_enum_fn: realloc failed for %d items\n", i+1));
161                 return;
162         }
163         fenum->info = f;
164
165         /* need to count the number of locks on a file */
166
167         ZERO_STRUCT( fsp );
168         fsp.file_id = e->id;
169
170         if ( (brl = brl_get_locks(talloc_tos(), &fsp)) != NULL ) {
171                 num_locks = brl->num_locks;
172                 TALLOC_FREE(brl);
173         }
174
175         if ( strcmp( fname, "." ) == 0 ) {
176                 fullpath = talloc_asprintf(fenum->ctx, "C:%s", sharepath );
177         } else {
178                 fullpath = talloc_asprintf(fenum->ctx, "C:%s/%s",
179                                 sharepath, fname );
180         }
181         if (!fullpath) {
182                 return;
183         }
184         string_replace( fullpath, '/', '\\' );
185
186         /* mask out create (what ever that is) */
187         permissions = e->share_access & (FILE_READ_DATA|FILE_WRITE_DATA);
188
189         /* now fill in the FILE_INFO_3 struct */
190         init_srv_file_info3( &fenum->info[i],
191                              e->share_file_id,
192                              permissions,
193                              num_locks,
194                              username,
195                              fullpath );
196
197         TALLOC_FREE(fullpath);
198         fenum->count++;
199 }
200
201 /*******************************************************************
202 ********************************************************************/
203
204 static WERROR net_enum_files( TALLOC_CTX *ctx, const char *username,
205                               FILE_INFO_3 **info,
206                               uint32 *count, uint32 resume )
207 {
208         struct file_enum_count f_enum_cnt;
209
210         f_enum_cnt.ctx = ctx;
211         f_enum_cnt.username = username;
212         f_enum_cnt.count = *count;
213         f_enum_cnt.info = *info;
214
215         share_mode_forall( enum_file_fn, (void *)&f_enum_cnt );
216
217         *info  = f_enum_cnt.info;
218         *count = f_enum_cnt.count;
219
220         return WERR_OK;
221 }
222
223 /*******************************************************************
224  Utility function to get the 'type' of a share from an snum.
225  ********************************************************************/
226 static uint32 get_share_type(int snum)
227 {
228         /* work out the share type */
229         uint32 type = STYPE_DISKTREE;
230
231         if (lp_print_ok(snum))
232                 type = STYPE_PRINTQ;
233         if (strequal(lp_fstype(snum), "IPC"))
234                 type = STYPE_IPC;
235         if (lp_administrative_share(snum))
236                 type |= STYPE_HIDDEN;
237
238         return type;
239 }
240
241 /*******************************************************************
242  Fill in a share info level 0 structure.
243  ********************************************************************/
244
245 static void init_srv_share_info_0(pipes_struct *p, struct srvsvc_NetShareInfo0 *r, int snum)
246 {
247         const char *net_name = lp_servicename(snum);
248
249         init_srvsvc_NetShareInfo0(r, net_name);
250 }
251
252 /*******************************************************************
253  Fill in a share info level 1 structure.
254  ********************************************************************/
255
256 static void init_srv_share_info_1(pipes_struct *p, struct srvsvc_NetShareInfo1 *r, int snum)
257 {
258         char *net_name = lp_servicename(snum);
259         char *remark = talloc_strdup(p->mem_ctx, lp_comment(snum));
260
261         if (remark) {
262                 remark = standard_sub_conn(p->mem_ctx,
263                                 p->conn,
264                                 remark);
265         }
266
267         init_srvsvc_NetShareInfo1(r, net_name,
268                                   get_share_type(snum),
269                                   remark ? remark : "");
270 }
271
272 /*******************************************************************
273  Fill in a share info level 2 structure.
274  ********************************************************************/
275
276 static void init_srv_share_info_2(pipes_struct *p, struct srvsvc_NetShareInfo2 *r, int snum)
277 {
278         char *remark = NULL;
279         char *path = NULL;
280         int max_connections = lp_max_connections(snum);
281         uint32 max_uses = max_connections!=0 ? max_connections : 0xffffffff;
282         int count = 0;
283         char *net_name = lp_servicename(snum);
284
285         remark = talloc_strdup(p->mem_ctx, lp_comment(snum));
286         if (remark) {
287                 remark = standard_sub_conn(p->mem_ctx,
288                                 p->conn,
289                                 remark);
290         }
291         path = talloc_asprintf(p->mem_ctx,
292                         "C:%s", lp_pathname(snum));
293
294         if (path) {
295                 /*
296                  * Change / to \\ so that win2k will see it as a valid path.
297                  * This was added to enable use of browsing in win2k add
298                  * share dialog.
299                  */
300
301                 string_replace(path, '/', '\\');
302         }
303
304         count = count_current_connections(net_name, false);
305
306         init_srvsvc_NetShareInfo2(r, net_name,
307                                   get_share_type(snum),
308                                   remark ? remark : "",
309                                   0,
310                                   max_uses,
311                                   count,
312                                   path ? path : "",
313                                   "");
314 }
315
316 /*******************************************************************
317  Map any generic bits to file specific bits.
318 ********************************************************************/
319
320 static void map_generic_share_sd_bits(SEC_DESC *psd)
321 {
322         int i;
323         SEC_ACL *ps_dacl = NULL;
324
325         if (!psd)
326                 return;
327
328         ps_dacl = psd->dacl;
329         if (!ps_dacl)
330                 return;
331
332         for (i = 0; i < ps_dacl->num_aces; i++) {
333                 SEC_ACE *psa = &ps_dacl->aces[i];
334                 uint32 orig_mask = psa->access_mask;
335
336                 se_map_generic(&psa->access_mask, &file_generic_mapping);
337                 psa->access_mask |= orig_mask;
338         }
339 }
340
341 /*******************************************************************
342  Fill in a share info level 501 structure.
343 ********************************************************************/
344
345 static void init_srv_share_info_501(pipes_struct *p, struct srvsvc_NetShareInfo501 *r, int snum)
346 {
347         const char *net_name = lp_servicename(snum);
348         char *remark = talloc_strdup(p->mem_ctx, lp_comment(snum));
349
350         if (remark) {
351                 remark = standard_sub_conn(p->mem_ctx, p->conn, remark);
352         }
353
354         init_srvsvc_NetShareInfo501(r, net_name,
355                                     get_share_type(snum),
356                                     remark ? remark : "",
357                                     (lp_csc_policy(snum) << 4));
358 }
359
360 /*******************************************************************
361  Fill in a share info level 502 structure.
362  ********************************************************************/
363
364 static void init_srv_share_info_502(pipes_struct *p, struct srvsvc_NetShareInfo502 *r, int snum)
365 {
366         const char *net_name = lp_servicename(snum);
367         char *path = NULL;
368         SEC_DESC *sd = NULL;
369         size_t sd_size = 0;
370         TALLOC_CTX *ctx = p->mem_ctx;
371         char *remark = talloc_strdup(ctx, lp_comment(snum));;
372
373         if (remark) {
374                 remark = standard_sub_conn(ctx, p->conn, remark);
375         }
376         path = talloc_asprintf(ctx, "C:%s", lp_pathname(snum));
377         if (path) {
378                 /*
379                  * Change / to \\ so that win2k will see it as a valid path.  This was added to
380                  * enable use of browsing in win2k add share dialog.
381                  */
382                 string_replace(path, '/', '\\');
383         }
384
385         sd = get_share_security(ctx, lp_servicename(snum), &sd_size);
386
387         init_srvsvc_NetShareInfo502(r, net_name,
388                                     get_share_type(snum),
389                                     remark ? remark : "",
390                                     0,
391                                     0xffffffff,
392                                     1,
393                                     path ? path : "",
394                                     "",
395                                     0,
396                                     sd);
397 }
398
399 /***************************************************************************
400  Fill in a share info level 1004 structure.
401  ***************************************************************************/
402
403 static void init_srv_share_info_1004(pipes_struct *p, struct srvsvc_NetShareInfo1004 *r, int snum)
404 {
405         char *remark = talloc_strdup(p->mem_ctx, lp_comment(snum));
406
407         if (remark) {
408                 remark = standard_sub_conn(p->mem_ctx, p->conn, remark);
409         }
410
411         init_srvsvc_NetShareInfo1004(r, remark ? remark : "");
412 }
413
414 /***************************************************************************
415  Fill in a share info level 1005 structure.
416  ***************************************************************************/
417
418 static void init_srv_share_info_1005(pipes_struct *p, struct srvsvc_NetShareInfo1005 *r, int snum)
419 {
420         uint32_t dfs_flags = 0;
421
422         if (lp_host_msdfs() && lp_msdfs_root(snum)) {
423                 dfs_flags |= SHARE_1005_IN_DFS | SHARE_1005_DFS_ROOT;
424         }
425
426         dfs_flags |= lp_csc_policy(snum) << SHARE_1005_CSC_POLICY_SHIFT;
427
428         init_srvsvc_NetShareInfo1005(r, dfs_flags);
429 }
430
431 /***************************************************************************
432  Fill in a share info level 1006 structure.
433  ***************************************************************************/
434
435 static void init_srv_share_info_1006(pipes_struct *p, struct srvsvc_NetShareInfo1006 *r, int snum)
436 {
437         init_srvsvc_NetShareInfo1006(r, 0xffffffff);
438 }
439
440 /***************************************************************************
441  Fill in a share info level 1007 structure.
442  ***************************************************************************/
443
444 static void init_srv_share_info_1007(pipes_struct *p, struct srvsvc_NetShareInfo1007 *r, int snum)
445 {
446         uint32 flags = 0;
447
448         init_srvsvc_NetShareInfo1007(r, flags, "");
449 }
450
451 /*******************************************************************
452  Fill in a share info level 1501 structure.
453  ********************************************************************/
454
455 static void init_srv_share_info_1501(pipes_struct *p, struct sec_desc_buf *r, int snum)
456 {
457         SEC_DESC *sd;
458         size_t sd_size;
459         TALLOC_CTX *ctx = p->mem_ctx;
460
461         sd = get_share_security(ctx, lp_servicename(snum), &sd_size);
462
463         r = make_sec_desc_buf(p->mem_ctx, sd_size, sd);
464 }
465
466 /*******************************************************************
467  True if it ends in '$'.
468  ********************************************************************/
469
470 static bool is_hidden_share(int snum)
471 {
472         const char *net_name = lp_servicename(snum);
473
474         return (net_name[strlen(net_name) - 1] == '$') ? True : False;
475 }
476
477 /*******************************************************************
478  Fill in a share info structure.
479  ********************************************************************/
480
481 static WERROR init_srv_share_info_ctr(pipes_struct *p,
482                                       struct srvsvc_NetShareInfoCtr *info_ctr,
483                                       uint32_t *resume_handle_p,
484                                       uint32_t *total_entries,
485                                       bool all_shares)
486 {
487         int num_entries = 0;
488         int alloc_entries = 0;
489         int num_services = 0;
490         int snum;
491         TALLOC_CTX *ctx = p->mem_ctx;
492         int i = 0;
493         int valid_share_count = 0;
494         union srvsvc_NetShareCtr ctr;
495         uint32_t resume_handle = resume_handle_p ? *resume_handle_p : 0;
496
497         DEBUG(5,("init_srv_share_info_ctr\n"));
498
499         /* Ensure all the usershares are loaded. */
500         become_root();
501         num_services = load_usershare_shares();
502         load_registry_shares();
503         unbecome_root();
504
505         /* Count the number of entries. */
506         for (snum = 0; snum < num_services; snum++) {
507                 if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) ) {
508                         num_entries++;
509                 }
510         }
511
512         if (!num_entries || (resume_handle >= num_entries)) {
513                 return WERR_OK;
514         }
515
516         /* Calculate alloc entries. */
517         alloc_entries = num_entries - resume_handle;
518         switch (info_ctr->level) {
519         case 0:
520                 ctr.ctr0 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr0);
521                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr0);
522
523                 ctr.ctr0->count = alloc_entries;
524                 ctr.ctr0->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo0, alloc_entries);
525                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr0->array);
526
527                 for (snum = 0; snum < num_services; snum++) {
528                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
529                             (resume_handle <= (i + valid_share_count++)) ) {
530                                 init_srv_share_info_0(p, &ctr.ctr0->array[i++], snum);
531                         }
532                 }
533
534                 break;
535
536         case 1:
537                 ctr.ctr1 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1);
538                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1);
539
540                 ctr.ctr1->count = alloc_entries;
541                 ctr.ctr1->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo1, alloc_entries);
542                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1->array);
543
544                 for (snum = 0; snum < num_services; snum++) {
545                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
546                             (resume_handle <= (i + valid_share_count++)) ) {
547                                 init_srv_share_info_1(p, &ctr.ctr1->array[i++], snum);
548                         }
549                 }
550
551                 break;
552
553         case 2:
554                 ctr.ctr2 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr2);
555                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr2);
556
557                 ctr.ctr2->count = alloc_entries;
558                 ctr.ctr2->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo2, alloc_entries);
559                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr2->array);
560
561                 for (snum = 0; snum < num_services; snum++) {
562                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
563                             (resume_handle <= (i + valid_share_count++)) ) {
564                                 init_srv_share_info_2(p, &ctr.ctr2->array[i++], snum);
565                         }
566                 }
567
568                 break;
569
570         case 501:
571                 ctr.ctr501 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr501);
572                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr501);
573
574                 ctr.ctr501->count = alloc_entries;
575                 ctr.ctr501->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo501, alloc_entries);
576                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr501->array);
577
578                 for (snum = 0; snum < num_services; snum++) {
579                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
580                             (resume_handle <= (i + valid_share_count++)) ) {
581                                 init_srv_share_info_501(p, &ctr.ctr501->array[i++], snum);
582                         }
583                 }
584
585                 break;
586
587         case 502:
588                 ctr.ctr502 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr502);
589                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr502);
590
591                 ctr.ctr502->count = alloc_entries;
592                 ctr.ctr502->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo502, alloc_entries);
593                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr502->array);
594
595                 for (snum = 0; snum < num_services; snum++) {
596                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
597                             (resume_handle <= (i + valid_share_count++)) ) {
598                                 init_srv_share_info_502(p, &ctr.ctr502->array[i++], snum);
599                         }
600                 }
601
602                 break;
603
604         case 1004:
605                 ctr.ctr1004 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1004);
606                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1004);
607
608                 ctr.ctr1004->count = alloc_entries;
609                 ctr.ctr1004->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo1004, alloc_entries);
610                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1004->array);
611
612                 for (snum = 0; snum < num_services; snum++) {
613                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
614                             (resume_handle <= (i + valid_share_count++)) ) {
615                                 init_srv_share_info_1004(p, &ctr.ctr1004->array[i++], snum);
616                         }
617                 }
618
619                 break;
620
621         case 1005:
622                 ctr.ctr1005 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1005);
623                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1005);
624
625                 ctr.ctr1005->count = alloc_entries;
626                 ctr.ctr1005->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo1005, alloc_entries);
627                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1005->array);
628
629                 for (snum = 0; snum < num_services; snum++) {
630                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
631                             (resume_handle <= (i + valid_share_count++)) ) {
632                                 init_srv_share_info_1005(p, &ctr.ctr1005->array[i++], snum);
633                         }
634                 }
635
636                 break;
637
638         case 1006:
639                 ctr.ctr1006 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1006);
640                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1006);
641
642                 ctr.ctr1006->count = alloc_entries;
643                 ctr.ctr1006->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo1006, alloc_entries);
644                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1006->array);
645
646                 for (snum = 0; snum < num_services; snum++) {
647                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
648                             (resume_handle <= (i + valid_share_count++)) ) {
649                                 init_srv_share_info_1006(p, &ctr.ctr1006->array[i++], snum);
650                         }
651                 }
652
653                 break;
654
655         case 1007:
656                 ctr.ctr1007 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1007);
657                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1007);
658
659                 ctr.ctr1007->count = alloc_entries;
660                 ctr.ctr1007->array = TALLOC_ZERO_ARRAY(ctx, struct srvsvc_NetShareInfo1007, alloc_entries);
661                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1007->array);
662
663                 for (snum = 0; snum < num_services; snum++) {
664                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
665                             (resume_handle <= (i + valid_share_count++)) ) {
666                                 init_srv_share_info_1007(p, &ctr.ctr1007->array[i++], snum);
667                         }
668                 }
669
670                 break;
671
672         case 1501:
673                 ctr.ctr1501 = TALLOC_ZERO_P(ctx, struct srvsvc_NetShareCtr1501);
674                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1501);
675
676                 ctr.ctr1501->count = alloc_entries;
677                 ctr.ctr1501->array = TALLOC_ZERO_ARRAY(ctx, struct sec_desc_buf, alloc_entries);
678                 W_ERROR_HAVE_NO_MEMORY(ctr.ctr1501->array);
679
680                 for (snum = 0; snum < num_services; snum++) {
681                         if (lp_browseable(snum) && lp_snum_ok(snum) && (all_shares || !is_hidden_share(snum)) &&
682                             (resume_handle <= (i + valid_share_count++)) ) {
683                                 init_srv_share_info_1501(p, &ctr.ctr1501->array[i++], snum);
684                         }
685                 }
686
687                 break;
688
689         default:
690                 DEBUG(5,("init_srv_share_info_ctr: unsupported switch value %d\n",
691                         info_ctr->level));
692                 return WERR_UNKNOWN_LEVEL;
693         }
694
695         *total_entries = alloc_entries;
696         if (resume_handle_p) {
697                 *resume_handle_p = num_entries;
698         }
699
700         info_ctr->ctr = ctr;
701
702         return WERR_OK;
703 }
704
705 /*******************************************************************
706  fill in a sess info level 0 structure.
707  ********************************************************************/
708
709 static void init_srv_sess_info_0(pipes_struct *p, SRV_SESS_INFO_0 *ss0, uint32 *snum, uint32 *stot)
710 {
711         struct sessionid *session_list;
712         uint32 num_entries = 0;
713         (*stot) = list_sessions(p->mem_ctx, &session_list);
714
715         if (ss0 == NULL) {
716                 if (snum) {
717                         (*snum) = 0;
718                 }
719                 return;
720         }
721
722         DEBUG(5,("init_srv_sess_0_ss0\n"));
723
724         if (snum) {
725                 for (; (*snum) < (*stot) && num_entries < MAX_SESS_ENTRIES; (*snum)++) {
726                         init_srv_sess_info0( &ss0->info_0[num_entries], session_list[(*snum)].remote_machine);
727                         num_entries++;
728                 }
729
730                 ss0->num_entries_read  = num_entries;
731                 ss0->ptr_sess_info     = num_entries > 0 ? 1 : 0;
732                 ss0->num_entries_read2 = num_entries;
733
734                 if ((*snum) >= (*stot)) {
735                         (*snum) = 0;
736                 }
737
738         } else {
739                 ss0->num_entries_read = 0;
740                 ss0->ptr_sess_info = 0;
741                 ss0->num_entries_read2 = 0;
742         }
743 }
744
745 /*******************************************************************
746 ********************************************************************/
747
748 static void sess_file_fn( const struct share_mode_entry *e,
749                           const char *sharepath, const char *fname,
750                           void *data )
751 {
752         struct sess_file_count *sess = (struct sess_file_count *)data;
753
754         if ( procid_equal(&e->pid, &sess->pid) && (sess->uid == e->uid) ) {
755                 sess->count++;
756         }
757
758         return;
759 }
760
761 /*******************************************************************
762 ********************************************************************/
763
764 static int net_count_files( uid_t uid, struct server_id pid )
765 {
766         struct sess_file_count s_file_cnt;
767
768         s_file_cnt.count = 0;
769         s_file_cnt.uid = uid;
770         s_file_cnt.pid = pid;
771
772         share_mode_forall( sess_file_fn, &s_file_cnt );
773
774         return s_file_cnt.count;
775 }
776
777 /*******************************************************************
778  fill in a sess info level 1 structure.
779  ********************************************************************/
780
781 static void init_srv_sess_info_1(pipes_struct *p, SRV_SESS_INFO_1 *ss1, uint32 *snum, uint32 *stot)
782 {
783         struct sessionid *session_list;
784         uint32 num_entries = 0;
785         time_t now = time(NULL);
786
787         if ( !snum ) {
788                 ss1->num_entries_read = 0;
789                 ss1->ptr_sess_info = 0;
790                 ss1->num_entries_read2 = 0;
791
792                 (*stot) = 0;
793
794                 return;
795         }
796
797         if (ss1 == NULL) {
798                 (*snum) = 0;
799                 return;
800         }
801
802         (*stot) = list_sessions(p->mem_ctx, &session_list);
803
804
805         for (; (*snum) < (*stot) && num_entries < MAX_SESS_ENTRIES; (*snum)++) {
806                 uint32 num_files;
807                 uint32 connect_time;
808                 struct passwd *pw = sys_getpwnam(session_list[*snum].username);
809                 bool guest;
810
811                 if ( !pw ) {
812                         DEBUG(10,("init_srv_sess_info_1: failed to find owner: %s\n",
813                                 session_list[*snum].username));
814                         continue;
815                 }
816
817                 connect_time = (uint32)(now - session_list[*snum].connect_start);
818                 num_files = net_count_files(pw->pw_uid, session_list[*snum].pid);
819                 guest = strequal( session_list[*snum].username, lp_guestaccount() );
820
821                 init_srv_sess_info1( &ss1->info_1[num_entries],
822                                      session_list[*snum].remote_machine,
823                                      session_list[*snum].username,
824                                      num_files,
825                                      connect_time,
826                                      0,
827                                      guest);
828                 num_entries++;
829         }
830
831         ss1->num_entries_read  = num_entries;
832         ss1->ptr_sess_info     = num_entries > 0 ? 1 : 0;
833         ss1->num_entries_read2 = num_entries;
834
835         if ((*snum) >= (*stot)) {
836                 (*snum) = 0;
837         }
838
839 }
840
841 /*******************************************************************
842  makes a SRV_R_NET_SESS_ENUM structure.
843 ********************************************************************/
844
845 static WERROR init_srv_sess_info_ctr(pipes_struct *p, SRV_SESS_INFO_CTR *ctr,
846                                 int switch_value, uint32 *resume_hnd, uint32 *total_entries)
847 {
848         WERROR status = WERR_OK;
849         DEBUG(5,("init_srv_sess_info_ctr: %d\n", __LINE__));
850
851         ctr->switch_value = switch_value;
852
853         switch (switch_value) {
854         case 0:
855                 init_srv_sess_info_0(p, &(ctr->sess.info0), resume_hnd, total_entries);
856                 ctr->ptr_sess_ctr = 1;
857                 break;
858         case 1:
859                 init_srv_sess_info_1(p, &(ctr->sess.info1), resume_hnd, total_entries);
860                 ctr->ptr_sess_ctr = 1;
861                 break;
862         default:
863                 DEBUG(5,("init_srv_sess_info_ctr: unsupported switch value %d\n", switch_value));
864                 (*resume_hnd) = 0;
865                 (*total_entries) = 0;
866                 ctr->ptr_sess_ctr = 0;
867                 status = WERR_UNKNOWN_LEVEL;
868                 break;
869         }
870
871         return status;
872 }
873
874 /*******************************************************************
875  makes a SRV_R_NET_SESS_ENUM structure.
876 ********************************************************************/
877
878 static void init_srv_r_net_sess_enum(pipes_struct *p, SRV_R_NET_SESS_ENUM *r_n,
879                                 uint32 resume_hnd, int sess_level, int switch_value)
880 {
881         DEBUG(5,("init_srv_r_net_sess_enum: %d\n", __LINE__));
882
883         r_n->sess_level  = sess_level;
884
885         if (sess_level == -1)
886                 r_n->status = WERR_UNKNOWN_LEVEL;
887         else
888                 r_n->status = init_srv_sess_info_ctr(p, r_n->ctr, switch_value, &resume_hnd, &r_n->total_entries);
889
890         if (!W_ERROR_IS_OK(r_n->status))
891                 resume_hnd = 0;
892
893         init_enum_hnd(&r_n->enum_hnd, resume_hnd);
894 }
895
896 /*******************************************************************
897  fill in a conn info level 0 structure.
898  ********************************************************************/
899
900 static void init_srv_conn_info_0(SRV_CONN_INFO_0 *ss0, uint32 *snum, uint32 *stot)
901 {
902         uint32 num_entries = 0;
903         (*stot) = 1;
904
905         if (ss0 == NULL) {
906                 (*snum) = 0;
907                 return;
908         }
909
910         DEBUG(5,("init_srv_conn_0_ss0\n"));
911
912         if (snum) {
913                 for (; (*snum) < (*stot) && num_entries < MAX_CONN_ENTRIES; (*snum)++) {
914
915                         init_srv_conn_info0(&ss0->info_0[num_entries], (*stot));
916
917                         /* move on to creating next connection */
918                         /* move on to creating next conn */
919                         num_entries++;
920                 }
921
922                 ss0->num_entries_read  = num_entries;
923                 ss0->ptr_conn_info     = num_entries > 0 ? 1 : 0;
924                 ss0->num_entries_read2 = num_entries;
925
926                 if ((*snum) >= (*stot)) {
927                         (*snum) = 0;
928                 }
929
930         } else {
931                 ss0->num_entries_read = 0;
932                 ss0->ptr_conn_info = 0;
933                 ss0->num_entries_read2 = 0;
934
935                 (*stot) = 0;
936         }
937 }
938
939 /*******************************************************************
940  fill in a conn info level 1 structure.
941  ********************************************************************/
942
943 static void init_srv_conn_1_info(CONN_INFO_1 *se1, CONN_INFO_1_STR *str1,
944                                 uint32 id, uint32 type,
945                                 uint32 num_opens, uint32 num_users, uint32 open_time,
946                                 const char *usr_name, const char *net_name)
947 {
948         init_srv_conn_info1(se1 , id, type, num_opens, num_users, open_time, usr_name, net_name);
949         init_srv_conn_info1_str(str1, usr_name, net_name);
950 }
951
952 /*******************************************************************
953  fill in a conn info level 1 structure.
954  ********************************************************************/
955
956 static void init_srv_conn_info_1(SRV_CONN_INFO_1 *ss1, uint32 *snum, uint32 *stot)
957 {
958         uint32 num_entries = 0;
959         (*stot) = 1;
960
961         if (ss1 == NULL) {
962                 (*snum) = 0;
963                 return;
964         }
965
966         DEBUG(5,("init_srv_conn_1_ss1\n"));
967
968         if (snum) {
969                 for (; (*snum) < (*stot) && num_entries < MAX_CONN_ENTRIES; (*snum)++) {
970                         init_srv_conn_1_info(&ss1->info_1[num_entries],
971                                                                  &ss1->info_1_str[num_entries],
972                                              (*stot), 0x3, 1, 1, 3,"dummy_user", "IPC$");
973
974                         /* move on to creating next connection */
975                         /* move on to creating next conn */
976                         num_entries++;
977                 }
978
979                 ss1->num_entries_read  = num_entries;
980                 ss1->ptr_conn_info     = num_entries > 0 ? 1 : 0;
981                 ss1->num_entries_read2 = num_entries;
982
983
984                 if ((*snum) >= (*stot)) {
985                         (*snum) = 0;
986                 }
987
988         } else {
989                 ss1->num_entries_read = 0;
990                 ss1->ptr_conn_info = 0;
991                 ss1->num_entries_read2 = 0;
992
993                 (*stot) = 0;
994         }
995 }
996
997 /*******************************************************************
998  makes a SRV_R_NET_CONN_ENUM structure.
999 ********************************************************************/
1000
1001 static WERROR init_srv_conn_info_ctr(SRV_CONN_INFO_CTR *ctr,
1002                                 int switch_value, uint32 *resume_hnd, uint32 *total_entries)
1003 {
1004         WERROR status = WERR_OK;
1005         DEBUG(5,("init_srv_conn_info_ctr: %d\n", __LINE__));
1006
1007         ctr->switch_value = switch_value;
1008
1009         switch (switch_value) {
1010         case 0:
1011                 init_srv_conn_info_0(&ctr->conn.info0, resume_hnd, total_entries);
1012                 ctr->ptr_conn_ctr = 1;
1013                 break;
1014         case 1:
1015                 init_srv_conn_info_1(&ctr->conn.info1, resume_hnd, total_entries);
1016                 ctr->ptr_conn_ctr = 1;
1017                 break;
1018         default:
1019                 DEBUG(5,("init_srv_conn_info_ctr: unsupported switch value %d\n", switch_value));
1020                 (*resume_hnd = 0);
1021                 (*total_entries) = 0;
1022                 ctr->ptr_conn_ctr = 0;
1023                 status = WERR_UNKNOWN_LEVEL;
1024                 break;
1025         }
1026
1027         return status;
1028 }
1029
1030 /*******************************************************************
1031  makes a SRV_R_NET_CONN_ENUM structure.
1032 ********************************************************************/
1033
1034 static void init_srv_r_net_conn_enum(SRV_R_NET_CONN_ENUM *r_n,
1035                                 uint32 resume_hnd, int conn_level, int switch_value)
1036 {
1037         DEBUG(5,("init_srv_r_net_conn_enum: %d\n", __LINE__));
1038
1039         r_n->conn_level  = conn_level;
1040         if (conn_level == -1)
1041                 r_n->status = WERR_UNKNOWN_LEVEL;
1042         else
1043                 r_n->status = init_srv_conn_info_ctr(r_n->ctr, switch_value, &resume_hnd, &r_n->total_entries);
1044
1045         if (!W_ERROR_IS_OK(r_n->status))
1046                 resume_hnd = 0;
1047
1048         init_enum_hnd(&r_n->enum_hnd, resume_hnd);
1049 }
1050
1051 /*******************************************************************
1052  makes a SRV_R_NET_FILE_ENUM structure.
1053 ********************************************************************/
1054
1055 static WERROR net_file_enum_3( const char *username, SRV_R_NET_FILE_ENUM *r,
1056                                uint32 resume_hnd )
1057 {
1058         TALLOC_CTX *ctx = talloc_tos();
1059         SRV_FILE_INFO_CTR *ctr = &r->ctr;
1060
1061         /* TODO -- Windows enumerates
1062            (b) active pipes
1063            (c) open directories and files */
1064
1065         r->status = net_enum_files( ctx, username, &ctr->file.info3,
1066                                     &ctr->num_entries, resume_hnd );
1067         if ( !W_ERROR_IS_OK(r->status))
1068                 goto done;
1069
1070         r->status = net_enum_pipes( ctx, username, &ctr->file.info3,
1071                                     &ctr->num_entries, resume_hnd );
1072         if ( !W_ERROR_IS_OK(r->status))
1073                 goto done;
1074
1075         r->level = ctr->level = 3;
1076         r->total_entries = ctr->num_entries;
1077         /* ctr->num_entries = r->total_entries - resume_hnd; */
1078         ctr->num_entries2 = ctr->num_entries;
1079         ctr->ptr_file_info = 1;
1080
1081         r->status = WERR_OK;
1082
1083 done:
1084         if ( ctr->num_entries > 0 )
1085                 ctr->ptr_entries = 1;
1086
1087         init_enum_hnd(&r->enum_hnd, 0);
1088
1089         return r->status;
1090 }
1091
1092 /*******************************************************************
1093 *******************************************************************/
1094
1095 WERROR _srv_net_file_enum(pipes_struct *p, SRV_Q_NET_FILE_ENUM *q_u, SRV_R_NET_FILE_ENUM *r_u)
1096 {
1097         const char *username = NULL;
1098
1099         switch ( q_u->level ) {
1100         case 3:
1101                 if (q_u->username) {
1102                         username = rpcstr_pull_unistr2_talloc(
1103                                 p->mem_ctx, q_u->username);
1104                         if (!username) {
1105                                 return WERR_NOMEM;
1106                         }
1107                 }
1108
1109                 return net_file_enum_3(username, r_u,
1110                                        get_enum_hnd(&q_u->enum_hnd));
1111         default:
1112                 return WERR_UNKNOWN_LEVEL;
1113         }
1114
1115         return WERR_OK;
1116 }
1117
1118 /*******************************************************************
1119  _srvsvc_NetSrvGetInfo
1120 ********************************************************************/
1121
1122 WERROR _srvsvc_NetSrvGetInfo(pipes_struct *p,
1123                              struct srvsvc_NetSrvGetInfo *r)
1124 {
1125         WERROR status = WERR_OK;
1126
1127         DEBUG(5,("_srvsvc_NetSrvGetInfo: %d\n", __LINE__));
1128
1129         if (!pipe_access_check(p)) {
1130                 DEBUG(3, ("access denied to _srvsvc_NetSrvGetInfo\n"));
1131                 return WERR_ACCESS_DENIED;
1132         }
1133
1134         switch (r->in.level) {
1135
1136                 /* Technically level 102 should only be available to
1137                    Administrators but there isn't anything super-secret
1138                    here, as most of it is made up. */
1139
1140         case 102: {
1141                 struct srvsvc_NetSrvInfo102 *info102;
1142
1143                 info102 = TALLOC_P(p->mem_ctx, struct srvsvc_NetSrvInfo102);
1144                 if (!info102) {
1145                         return WERR_NOMEM;
1146                 }
1147
1148                 init_srvsvc_NetSrvInfo102(info102,
1149                                           PLATFORM_ID_NT,
1150                                           global_myname(),
1151                                           lp_major_announce_version(),
1152                                           lp_minor_announce_version(),
1153                                           lp_default_server_announce(),
1154                                           string_truncate(lp_serverstring(), MAX_SERVER_STRING_LENGTH),
1155                                           0xffffffff, /* users */
1156                                           0xf, /* disc */
1157                                           0, /* hidden */
1158                                           240, /* announce */
1159                                           3000, /* announce delta */
1160                                           100000, /* licenses */
1161                                           "c:\\"); /* user path */
1162                 r->out.info->info102 = info102;
1163                 break;
1164         }
1165         case 101: {
1166                 struct srvsvc_NetSrvInfo101 *info101;
1167
1168                 info101 = TALLOC_P(p->mem_ctx, struct srvsvc_NetSrvInfo101);
1169                 if (!info101) {
1170                         return WERR_NOMEM;
1171                 }
1172
1173                 init_srvsvc_NetSrvInfo101(info101,
1174                                           PLATFORM_ID_NT,
1175                                           global_myname(),
1176                                           lp_major_announce_version(),
1177                                           lp_minor_announce_version(),
1178                                           lp_default_server_announce(),
1179                                           string_truncate(lp_serverstring(), MAX_SERVER_STRING_LENGTH));
1180                 r->out.info->info101 = info101;
1181                 break;
1182         }
1183         case 100: {
1184                 struct srvsvc_NetSrvInfo100 *info100;
1185
1186                 info100 = TALLOC_P(p->mem_ctx, struct srvsvc_NetSrvInfo100);
1187                 if (!info100) {
1188                         return WERR_NOMEM;
1189                 }
1190
1191                 init_srvsvc_NetSrvInfo100(info100,
1192                                           PLATFORM_ID_NT,
1193                                           global_myname());
1194                 r->out.info->info100 = info100;
1195
1196                 break;
1197         }
1198         default:
1199                 status = WERR_UNKNOWN_LEVEL;
1200                 break;
1201         }
1202
1203         DEBUG(5,("_srvsvc_NetSrvGetInfo: %d\n", __LINE__));
1204
1205         return status;
1206 }
1207
1208 /*******************************************************************
1209  _srvsvc_NetSrvSetInfo
1210 ********************************************************************/
1211
1212 WERROR _srvsvc_NetSrvSetInfo(pipes_struct *p,
1213                              struct srvsvc_NetSrvSetInfo *r)
1214 {
1215         WERROR status = WERR_OK;
1216
1217         DEBUG(5,("_srvsvc_NetSrvSetInfo: %d\n", __LINE__));
1218
1219         /* Set up the net server set info structure. */
1220
1221         DEBUG(5,("_srvsvc_NetSrvSetInfo: %d\n", __LINE__));
1222
1223         return status;
1224 }
1225
1226 /*******************************************************************
1227 net conn enum
1228 ********************************************************************/
1229
1230 WERROR _srv_net_conn_enum(pipes_struct *p, SRV_Q_NET_CONN_ENUM *q_u, SRV_R_NET_CONN_ENUM *r_u)
1231 {
1232         DEBUG(5,("srv_net_conn_enum: %d\n", __LINE__));
1233
1234         r_u->ctr = TALLOC_P(p->mem_ctx, SRV_CONN_INFO_CTR);
1235         if (!r_u->ctr)
1236                 return WERR_NOMEM;
1237
1238         ZERO_STRUCTP(r_u->ctr);
1239
1240         /* set up the */
1241         init_srv_r_net_conn_enum(r_u,
1242                                 get_enum_hnd(&q_u->enum_hnd),
1243                                 q_u->conn_level,
1244                                 q_u->ctr->switch_value);
1245
1246         DEBUG(5,("srv_net_conn_enum: %d\n", __LINE__));
1247
1248         return r_u->status;
1249 }
1250
1251 /*******************************************************************
1252 net sess enum
1253 ********************************************************************/
1254
1255 WERROR _srv_net_sess_enum(pipes_struct *p, SRV_Q_NET_SESS_ENUM *q_u, SRV_R_NET_SESS_ENUM *r_u)
1256 {
1257         DEBUG(5,("_srv_net_sess_enum: %d\n", __LINE__));
1258
1259         r_u->ctr = TALLOC_P(p->mem_ctx, SRV_SESS_INFO_CTR);
1260         if (!r_u->ctr)
1261                 return WERR_NOMEM;
1262
1263         ZERO_STRUCTP(r_u->ctr);
1264
1265         /* set up the */
1266         init_srv_r_net_sess_enum(p, r_u,
1267                                 get_enum_hnd(&q_u->enum_hnd),
1268                                 q_u->sess_level,
1269                                 q_u->ctr->switch_value);
1270
1271         DEBUG(5,("_srv_net_sess_enum: %d\n", __LINE__));
1272
1273         return r_u->status;
1274 }
1275
1276 /*******************************************************************
1277 net sess del
1278 ********************************************************************/
1279
1280 WERROR _srv_net_sess_del(pipes_struct *p, SRV_Q_NET_SESS_DEL *q_u, SRV_R_NET_SESS_DEL *r_u)
1281 {
1282         struct sessionid *session_list;
1283         struct current_user user;
1284         int num_sessions, snum;
1285         fstring username;
1286         fstring machine;
1287         bool not_root = False;
1288
1289         rpcstr_pull_unistr2_fstring(username, &q_u->uni_user_name);
1290         rpcstr_pull_unistr2_fstring(machine, &q_u->uni_cli_name);
1291
1292         /* strip leading backslashes if any */
1293         while (machine[0] == '\\') {
1294                 memmove(machine, &machine[1], strlen(machine));
1295         }
1296
1297         num_sessions = list_sessions(p->mem_ctx, &session_list);
1298
1299         DEBUG(5,("_srv_net_sess_del: %d\n", __LINE__));
1300
1301         r_u->status = WERR_ACCESS_DENIED;
1302
1303         get_current_user(&user, p);
1304
1305         /* fail out now if you are not root or not a domain admin */
1306
1307         if ((user.ut.uid != sec_initial_uid()) &&
1308                 ( ! nt_token_check_domain_rid(p->pipe_user.nt_user_token, DOMAIN_GROUP_RID_ADMINS))) {
1309
1310                 goto done;
1311         }
1312
1313         for (snum = 0; snum < num_sessions; snum++) {
1314
1315                 if ((strequal(session_list[snum].username, username) || username[0] == '\0' ) &&
1316                     strequal(session_list[snum].remote_machine, machine)) {
1317
1318                         NTSTATUS ntstat;
1319
1320                         if (user.ut.uid != sec_initial_uid()) {
1321                                 not_root = True;
1322                                 become_root();
1323                         }
1324
1325                         ntstat = messaging_send(smbd_messaging_context(),
1326                                                 session_list[snum].pid,
1327                                                 MSG_SHUTDOWN, &data_blob_null);
1328
1329                         if (NT_STATUS_IS_OK(ntstat))
1330                                 r_u->status = WERR_OK;
1331
1332                         if (not_root)
1333                                 unbecome_root();
1334                 }
1335         }
1336
1337         DEBUG(5,("_srv_net_sess_del: %d\n", __LINE__));
1338
1339
1340 done:
1341
1342         return r_u->status;
1343 }
1344
1345 /*******************************************************************
1346  _srvsvc_NetShareEnumAll
1347 ********************************************************************/
1348
1349 WERROR _srvsvc_NetShareEnumAll(pipes_struct *p,
1350                                struct srvsvc_NetShareEnumAll *r)
1351 {
1352         WERROR werr;
1353
1354         DEBUG(5,("_srvsvc_NetShareEnumAll: %d\n", __LINE__));
1355
1356         if (!pipe_access_check(p)) {
1357                 DEBUG(3, ("access denied to _srvsvc_NetShareEnumAll\n"));
1358                 return WERR_ACCESS_DENIED;
1359         }
1360
1361         /* Create the list of shares for the response. */
1362         werr = init_srv_share_info_ctr(p,
1363                                        r->in.info_ctr,
1364                                        r->in.resume_handle,
1365                                        r->out.totalentries,
1366                                        true);
1367
1368         DEBUG(5,("_srvsvc_NetShareEnumAll: %d\n", __LINE__));
1369
1370         return werr;
1371 }
1372
1373 /*******************************************************************
1374  _srvsvc_NetShareEnum
1375 ********************************************************************/
1376
1377 WERROR _srvsvc_NetShareEnum(pipes_struct *p,
1378                             struct srvsvc_NetShareEnum *r)
1379 {
1380         WERROR werr;
1381
1382         DEBUG(5,("_srvsvc_NetShareEnum: %d\n", __LINE__));
1383
1384         if (!pipe_access_check(p)) {
1385                 DEBUG(3, ("access denied to _srvsvc_NetShareEnum\n"));
1386                 return WERR_ACCESS_DENIED;
1387         }
1388
1389         /* Create the list of shares for the response. */
1390         werr = init_srv_share_info_ctr(p,
1391                                        r->in.info_ctr,
1392                                        r->in.resume_handle,
1393                                        r->out.totalentries,
1394                                        false);
1395
1396         DEBUG(5,("_srvsvc_NetShareEnum: %d\n", __LINE__));
1397
1398         return werr;
1399 }
1400
1401 /*******************************************************************
1402  _srvsvc_NetShareGetInfo
1403 ********************************************************************/
1404
1405 WERROR _srvsvc_NetShareGetInfo(pipes_struct *p,
1406                                struct srvsvc_NetShareGetInfo *r)
1407 {
1408         WERROR status = WERR_OK;
1409         fstring share_name;
1410         int snum;
1411         union srvsvc_NetShareInfo *info = r->out.info;
1412
1413         DEBUG(5,("_srvsvc_NetShareGetInfo: %d\n", __LINE__));
1414
1415         fstrcpy(share_name, r->in.share_name);
1416
1417         snum = find_service(share_name);
1418         if (snum < 0) {
1419                 return WERR_INVALID_NAME;
1420         }
1421
1422         switch (r->in.level) {
1423                 case 0:
1424                         info->info0 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo0);
1425                         W_ERROR_HAVE_NO_MEMORY(info->info0);
1426                         init_srv_share_info_0(p, info->info0, snum);
1427                         break;
1428                 case 1:
1429                         info->info1 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo1);
1430                         W_ERROR_HAVE_NO_MEMORY(info->info1);
1431                         init_srv_share_info_1(p, info->info1, snum);
1432                         break;
1433                 case 2:
1434                         info->info2 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo2);
1435                         W_ERROR_HAVE_NO_MEMORY(info->info2);
1436                         init_srv_share_info_2(p, info->info2, snum);
1437                         break;
1438                 case 501:
1439                         info->info501 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo501);
1440                         W_ERROR_HAVE_NO_MEMORY(info->info501);
1441                         init_srv_share_info_501(p, info->info501, snum);
1442                         break;
1443                 case 502:
1444                         info->info502 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo502);
1445                         W_ERROR_HAVE_NO_MEMORY(info->info502);
1446                         init_srv_share_info_502(p, info->info502, snum);
1447                         break;
1448                 case 1004:
1449                         info->info1004 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo1004);
1450                         W_ERROR_HAVE_NO_MEMORY(info->info1004);
1451                         init_srv_share_info_1004(p, info->info1004, snum);
1452                         break;
1453                 case 1005:
1454                         info->info1005 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo1005);
1455                         W_ERROR_HAVE_NO_MEMORY(info->info1005);
1456                         init_srv_share_info_1005(p, info->info1005, snum);
1457                         break;
1458                 case 1006:
1459                         info->info1006 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo1006);
1460                         W_ERROR_HAVE_NO_MEMORY(info->info1006);
1461                         init_srv_share_info_1006(p, info->info1006, snum);
1462                         break;
1463                 case 1007:
1464                         info->info1007 = TALLOC_P(p->mem_ctx, struct srvsvc_NetShareInfo1007);
1465                         W_ERROR_HAVE_NO_MEMORY(info->info1007);
1466                         init_srv_share_info_1007(p, info->info1007, snum);
1467                         break;
1468                 case 1501:
1469                         init_srv_share_info_1501(p, info->info1501, snum);
1470                         break;
1471                 default:
1472                         DEBUG(5,("_srvsvc_NetShareGetInfo: unsupported switch value %d\n",
1473                                 r->in.level));
1474                         status = WERR_UNKNOWN_LEVEL;
1475                         break;
1476         }
1477
1478         DEBUG(5,("_srvsvc_NetShareGetInfo: %d\n", __LINE__));
1479
1480         return status;
1481 }
1482
1483 /*******************************************************************
1484  Check a given DOS pathname is valid for a share.
1485 ********************************************************************/
1486
1487 char *valid_share_pathname(TALLOC_CTX *ctx, const char *dos_pathname)
1488 {
1489         char *ptr = NULL;
1490
1491         if (!dos_pathname) {
1492                 return NULL;
1493         }
1494
1495         ptr = talloc_strdup(ctx, dos_pathname);
1496         if (!ptr) {
1497                 return NULL;
1498         }
1499         /* Convert any '\' paths to '/' */
1500         unix_format(ptr);
1501         ptr = unix_clean_name(ctx, ptr);
1502         if (!ptr) {
1503                 return NULL;
1504         }
1505
1506         /* NT is braindead - it wants a C: prefix to a pathname ! So strip it. */
1507         if (strlen(ptr) > 2 && ptr[1] == ':' && ptr[0] != '/')
1508                 ptr += 2;
1509
1510         /* Only absolute paths allowed. */
1511         if (*ptr != '/')
1512                 return NULL;
1513
1514         return ptr;
1515 }
1516
1517 /*******************************************************************
1518  _srvsvc_NetShareSetInfo. Modify share details.
1519 ********************************************************************/
1520
1521 WERROR _srvsvc_NetShareSetInfo(pipes_struct *p,
1522                                struct srvsvc_NetShareSetInfo *r)
1523 {
1524         struct current_user user;
1525         char *command = NULL;
1526         char *share_name = NULL;
1527         char *comment = NULL;
1528         const char *pathname = NULL;
1529         int type;
1530         int snum;
1531         int ret;
1532         char *path = NULL;
1533         SEC_DESC *psd = NULL;
1534         SE_PRIV se_diskop = SE_DISK_OPERATOR;
1535         bool is_disk_op = False;
1536         int max_connections = 0;
1537         TALLOC_CTX *ctx = p->mem_ctx;
1538         union srvsvc_NetShareInfo *info = r->in.info;
1539
1540         DEBUG(5,("_srvsvc_NetShareSetInfo: %d\n", __LINE__));
1541
1542         share_name = talloc_strdup(p->mem_ctx, r->in.share_name);
1543         if (!share_name) {
1544                 return WERR_NOMEM;
1545         }
1546
1547         *r->out.parm_error = 0;
1548
1549         if ( strequal(share_name,"IPC$")
1550                 || ( lp_enable_asu_support() && strequal(share_name,"ADMIN$") )
1551                 || strequal(share_name,"global") )
1552         {
1553                 return WERR_ACCESS_DENIED;
1554         }
1555
1556         snum = find_service(share_name);
1557
1558         /* Does this share exist ? */
1559         if (snum < 0)
1560                 return WERR_NET_NAME_NOT_FOUND;
1561
1562         /* No change to printer shares. */
1563         if (lp_print_ok(snum))
1564                 return WERR_ACCESS_DENIED;
1565
1566         get_current_user(&user,p);
1567
1568         is_disk_op = user_has_privileges( p->pipe_user.nt_user_token, &se_diskop );
1569
1570         /* fail out now if you are not root and not a disk op */
1571
1572         if ( user.ut.uid != sec_initial_uid() && !is_disk_op )
1573                 return WERR_ACCESS_DENIED;
1574
1575         switch (r->in.level) {
1576         case 1:
1577                 pathname = talloc_strdup(ctx, lp_pathname(snum));
1578                 comment = talloc_strdup(ctx, info->info2->comment);
1579                 type = info->info2->type;
1580                 psd = NULL;
1581                 break;
1582         case 2:
1583                 comment = talloc_strdup(ctx, info->info2->comment);
1584                 pathname = info->info2->path;
1585                 type = info->info2->type;
1586                 max_connections = (info->info2->max_users == 0xffffffff) ?
1587                         0 : info->info2->max_users;
1588                 psd = NULL;
1589                 break;
1590 #if 0
1591                 /* not supported on set but here for completeness */
1592         case 501:
1593                 comment = talloc_strdup(ctx, info->info501->comment);
1594                 type = info->info501->type;
1595                 psd = NULL;
1596                 break;
1597 #endif
1598         case 502:
1599                 comment = talloc_strdup(ctx, info->info502->comment);
1600                 pathname = info->info502->path;
1601                 type = info->info502->type;
1602                 psd = info->info502->sd;
1603                 map_generic_share_sd_bits(psd);
1604                 break;
1605         case 1004:
1606                 pathname = talloc_strdup(ctx, lp_pathname(snum));
1607                 comment = talloc_strdup(ctx, info->info1004->comment);
1608                 type = STYPE_DISKTREE;
1609                 break;
1610         case 1005:
1611                 /* XP re-sets the csc policy even if it wasn't changed by the
1612                    user, so we must compare it to see if it's what is set in
1613                    smb.conf, so that we can contine other ops like setting
1614                    ACLs on a share */
1615                 if (((info->info1005->dfs_flags &
1616                       SHARE_1005_CSC_POLICY_MASK) >>
1617                      SHARE_1005_CSC_POLICY_SHIFT) == lp_csc_policy(snum))
1618                         return WERR_OK;
1619                 else {
1620                         DEBUG(3, ("_srvsvc_NetShareSetInfo: client is trying to change csc policy from the network; must be done with smb.conf\n"));
1621                         return WERR_ACCESS_DENIED;
1622                 }
1623         case 1006:
1624         case 1007:
1625                 return WERR_ACCESS_DENIED;
1626         case 1501:
1627                 pathname = talloc_strdup(ctx, lp_pathname(snum));
1628                 comment = talloc_strdup(ctx, lp_comment(snum));
1629                 psd = info->info1501->sd;
1630                 map_generic_share_sd_bits(psd);
1631                 type = STYPE_DISKTREE;
1632                 break;
1633         default:
1634                 DEBUG(5,("_srvsvc_NetShareSetInfo: unsupported switch value %d\n",
1635                         r->in.level));
1636                 return WERR_UNKNOWN_LEVEL;
1637         }
1638
1639         /* We can only modify disk shares. */
1640         if (type != STYPE_DISKTREE)
1641                 return WERR_ACCESS_DENIED;
1642
1643         /* Check if the pathname is valid. */
1644         if (!(path = valid_share_pathname(p->mem_ctx, pathname )))
1645                 return WERR_OBJECT_PATH_INVALID;
1646
1647         /* Ensure share name, pathname and comment don't contain '"' characters. */
1648         string_replace(share_name, '"', ' ');
1649         string_replace(path, '"', ' ');
1650         if (comment) {
1651                 string_replace(comment, '"', ' ');
1652         }
1653
1654         DEBUG(10,("_srvsvc_NetShareSetInfo: change share command = %s\n",
1655                 lp_change_share_cmd() ? lp_change_share_cmd() : "NULL" ));
1656
1657         /* Only call modify function if something changed. */
1658
1659         if (strcmp(path, lp_pathname(snum)) || strcmp(comment, lp_comment(snum))
1660                         || (lp_max_connections(snum) != max_connections)) {
1661                 if (!lp_change_share_cmd() || !*lp_change_share_cmd()) {
1662                         DEBUG(10,("_srvsvc_NetShareSetInfo: No change share command\n"));
1663                         return WERR_ACCESS_DENIED;
1664                 }
1665
1666                 command = talloc_asprintf(p->mem_ctx,
1667                                 "%s \"%s\" \"%s\" \"%s\" \"%s\" %d",
1668                                 lp_change_share_cmd(),
1669                                 get_dyn_CONFIGFILE(),
1670                                 share_name,
1671                                 path,
1672                                 comment ? comment : "",
1673                                 max_connections);
1674                 if (!command) {
1675                         return WERR_NOMEM;
1676                 }
1677
1678                 DEBUG(10,("_srvsvc_NetShareSetInfo: Running [%s]\n", command ));
1679
1680                 /********* BEGIN SeDiskOperatorPrivilege BLOCK *********/
1681
1682                 if (is_disk_op)
1683                         become_root();
1684
1685                 if ( (ret = smbrun(command, NULL)) == 0 ) {
1686                         /* Tell everyone we updated smb.conf. */
1687                         message_send_all(smbd_messaging_context(),
1688                                          MSG_SMB_CONF_UPDATED, NULL, 0,
1689                                          NULL);
1690                 }
1691
1692                 if ( is_disk_op )
1693                         unbecome_root();
1694
1695                 /********* END SeDiskOperatorPrivilege BLOCK *********/
1696
1697                 DEBUG(3,("_srvsvc_NetShareSetInfo: Running [%s] returned (%d)\n",
1698                         command, ret ));
1699
1700                 TALLOC_FREE(command);
1701
1702                 if ( ret != 0 )
1703                         return WERR_ACCESS_DENIED;
1704         } else {
1705                 DEBUG(10,("_srvsvc_NetShareSetInfo: No change to share name (%s)\n",
1706                         share_name ));
1707         }
1708
1709         /* Replace SD if changed. */
1710         if (psd) {
1711                 SEC_DESC *old_sd;
1712                 size_t sd_size;
1713
1714                 old_sd = get_share_security(p->mem_ctx, lp_servicename(snum), &sd_size);
1715
1716                 if (old_sd && !sec_desc_equal(old_sd, psd)) {
1717                         if (!set_share_security(share_name, psd))
1718                                 DEBUG(0,("_srvsvc_NetShareSetInfo: Failed to change security info in share %s.\n",
1719                                         share_name ));
1720                 }
1721         }
1722
1723         DEBUG(5,("_srvsvc_NetShareSetInfo: %d\n", __LINE__));
1724
1725         return WERR_OK;
1726 }
1727
1728 /*******************************************************************
1729  Net share add. Call 'add_share_command "sharename" "pathname"
1730  "comment" "max connections = "
1731 ********************************************************************/
1732
1733 WERROR _srv_net_share_add(pipes_struct *p, SRV_Q_NET_SHARE_ADD *q_u, SRV_R_NET_SHARE_ADD *r_u)
1734 {
1735         struct current_user user;
1736         char *command = NULL;
1737         char *share_name = NULL;
1738         char *comment = NULL;
1739         char *pathname = NULL;
1740         int type;
1741         int snum;
1742         int ret;
1743         char *path;
1744         SEC_DESC *psd = NULL;
1745         SE_PRIV se_diskop = SE_DISK_OPERATOR;
1746         bool is_disk_op;
1747         int max_connections = 0;
1748         TALLOC_CTX *ctx = p->mem_ctx;
1749
1750         DEBUG(5,("_srv_net_share_add: %d\n", __LINE__));
1751
1752         r_u->parm_error = 0;
1753
1754         get_current_user(&user,p);
1755
1756         is_disk_op = user_has_privileges( p->pipe_user.nt_user_token, &se_diskop );
1757
1758         if (user.ut.uid != sec_initial_uid()  && !is_disk_op )
1759                 return WERR_ACCESS_DENIED;
1760
1761         if (!lp_add_share_cmd() || !*lp_add_share_cmd()) {
1762                 DEBUG(10,("_srv_net_share_add: No add share command\n"));
1763                 return WERR_ACCESS_DENIED;
1764         }
1765
1766         switch (q_u->info_level) {
1767         case 0:
1768                 /* No path. Not enough info in a level 0 to do anything. */
1769                 return WERR_ACCESS_DENIED;
1770         case 1:
1771                 /* Not enough info in a level 1 to do anything. */
1772                 return WERR_ACCESS_DENIED;
1773         case 2:
1774                 share_name = unistr2_to_ascii_talloc(ctx,
1775                                 &q_u->info.share.info2.info_2_str.uni_netname);
1776                 comment = unistr2_to_ascii_talloc(ctx,
1777                                 &q_u->info.share.info2.info_2_str.uni_remark);
1778                 pathname = unistr2_to_ascii_talloc(ctx,
1779                                 &q_u->info.share.info2.info_2_str.uni_path);
1780                 max_connections = (q_u->info.share.info2.info_2.max_uses == 0xffffffff) ? 0 : q_u->info.share.info2.info_2.max_uses;
1781                 type = q_u->info.share.info2.info_2.type;
1782                 break;
1783         case 501:
1784                 /* No path. Not enough info in a level 501 to do anything. */
1785                 return WERR_ACCESS_DENIED;
1786         case 502:
1787                 share_name = unistr2_to_ascii_talloc(ctx,
1788                                 &q_u->info.share.info502.info_502_str.uni_netname);
1789                 comment = unistr2_to_ascii_talloc(ctx,
1790                                 &q_u->info.share.info502.info_502_str.uni_remark);
1791                 pathname = unistr2_to_ascii_talloc(ctx,
1792                                 &q_u->info.share.info502.info_502_str.uni_path);
1793                 type = q_u->info.share.info502.info_502.type;
1794                 psd = q_u->info.share.info502.info_502_str.sd;
1795                 map_generic_share_sd_bits(psd);
1796                 break;
1797
1798                 /* none of the following contain share names.  NetShareAdd does not have a separate parameter for the share name */
1799
1800         case 1004:
1801         case 1005:
1802         case 1006:
1803         case 1007:
1804                 return WERR_ACCESS_DENIED;
1805         case 1501:
1806                 /* DFS only level. */
1807                 return WERR_ACCESS_DENIED;
1808         default:
1809                 DEBUG(5,("_srv_net_share_add: unsupported switch value %d\n", q_u->info_level));
1810                 return WERR_UNKNOWN_LEVEL;
1811         }
1812
1813         /* check for invalid share names */
1814
1815         if (!share_name || !validate_net_name(share_name,
1816                                 INVALID_SHARENAME_CHARS,
1817                                 strlen(share_name))) {
1818                 DEBUG(5,("_srv_net_name_validate: Bad sharename \"%s\"\n",
1819                                         share_name ? share_name : ""));
1820                 return WERR_INVALID_NAME;
1821         }
1822
1823         if (strequal(share_name,"IPC$") || strequal(share_name,"global")
1824                         || (lp_enable_asu_support() &&
1825                                         strequal(share_name,"ADMIN$"))) {
1826                 return WERR_ACCESS_DENIED;
1827         }
1828
1829         snum = find_service(share_name);
1830
1831         /* Share already exists. */
1832         if (snum >= 0) {
1833                 return WERR_ALREADY_EXISTS;
1834         }
1835
1836         /* We can only add disk shares. */
1837         if (type != STYPE_DISKTREE) {
1838                 return WERR_ACCESS_DENIED;
1839         }
1840
1841         /* Check if the pathname is valid. */
1842         if (!(path = valid_share_pathname(p->mem_ctx, pathname))) {
1843                 return WERR_OBJECT_PATH_INVALID;
1844         }
1845
1846         /* Ensure share name, pathname and comment don't contain '"' characters. */
1847         string_replace(share_name, '"', ' ');
1848         string_replace(path, '"', ' ');
1849         if (comment) {
1850                 string_replace(comment, '"', ' ');
1851         }
1852
1853         command = talloc_asprintf(ctx,
1854                         "%s \"%s\" \"%s\" \"%s\" \"%s\" %d",
1855                         lp_add_share_cmd(),
1856                         get_dyn_CONFIGFILE(),
1857                         share_name,
1858                         path,
1859                         comment ? comment : "",
1860                         max_connections);
1861         if (!command) {
1862                 return WERR_NOMEM;
1863         }
1864
1865         DEBUG(10,("_srv_net_share_add: Running [%s]\n", command ));
1866
1867         /********* BEGIN SeDiskOperatorPrivilege BLOCK *********/
1868
1869         if ( is_disk_op )
1870                 become_root();
1871
1872         if ( (ret = smbrun(command, NULL)) == 0 ) {
1873                 /* Tell everyone we updated smb.conf. */
1874                 message_send_all(smbd_messaging_context(),
1875                                  MSG_SMB_CONF_UPDATED, NULL, 0, NULL);
1876         }
1877
1878         if ( is_disk_op )
1879                 unbecome_root();
1880
1881         /********* END SeDiskOperatorPrivilege BLOCK *********/
1882
1883         DEBUG(3,("_srv_net_share_add: Running [%s] returned (%d)\n", command, ret ));
1884
1885         TALLOC_FREE(command);
1886
1887         if ( ret != 0 )
1888                 return WERR_ACCESS_DENIED;
1889
1890         if (psd) {
1891                 if (!set_share_security(share_name, psd)) {
1892                         DEBUG(0,("_srv_net_share_add: Failed to add security info to share %s.\n", share_name ));
1893                 }
1894         }
1895
1896         /*
1897          * We don't call reload_services() here, the message will
1898          * cause this to be done before the next packet is read
1899          * from the client. JRA.
1900          */
1901
1902         DEBUG(5,("_srv_net_share_add: %d\n", __LINE__));
1903
1904         return WERR_OK;
1905 }
1906
1907 /*******************************************************************
1908  _srvsvc_NetShareDel
1909  Call "delete share command" with the share name as
1910  a parameter.
1911 ********************************************************************/
1912
1913 WERROR _srvsvc_NetShareDel(pipes_struct *p,
1914                            struct srvsvc_NetShareDel *r)
1915 {
1916         struct current_user user;
1917         char *command = NULL;
1918         char *share_name = NULL;
1919         int ret;
1920         int snum;
1921         SE_PRIV se_diskop = SE_DISK_OPERATOR;
1922         bool is_disk_op;
1923         struct share_params *params;
1924         TALLOC_CTX *ctx = p->mem_ctx;
1925
1926         DEBUG(5,("_srvsvc_NetShareDel: %d\n", __LINE__));
1927
1928         share_name = talloc_strdup(p->mem_ctx, r->in.share_name);
1929         if (!share_name) {
1930                 return WERR_NET_NAME_NOT_FOUND;
1931         }
1932         if ( strequal(share_name,"IPC$")
1933                 || ( lp_enable_asu_support() && strequal(share_name,"ADMIN$") )
1934                 || strequal(share_name,"global") )
1935         {
1936                 return WERR_ACCESS_DENIED;
1937         }
1938
1939         if (!(params = get_share_params(p->mem_ctx, share_name))) {
1940                 return WERR_NO_SUCH_SHARE;
1941         }
1942
1943         snum = find_service(share_name);
1944
1945         /* No change to printer shares. */
1946         if (lp_print_ok(snum))
1947                 return WERR_ACCESS_DENIED;
1948
1949         get_current_user(&user,p);
1950
1951         is_disk_op = user_has_privileges( p->pipe_user.nt_user_token, &se_diskop );
1952
1953         if (user.ut.uid != sec_initial_uid()  && !is_disk_op )
1954                 return WERR_ACCESS_DENIED;
1955
1956         if (!lp_delete_share_cmd() || !*lp_delete_share_cmd()) {
1957                 DEBUG(10,("_srvsvc_NetShareDel: No delete share command\n"));
1958                 return WERR_ACCESS_DENIED;
1959         }
1960
1961         command = talloc_asprintf(ctx,
1962                         "%s \"%s\" \"%s\"",
1963                         lp_delete_share_cmd(),
1964                         get_dyn_CONFIGFILE(),
1965                         lp_servicename(snum));
1966         if (!command) {
1967                 return WERR_NOMEM;
1968         }
1969
1970         DEBUG(10,("_srvsvc_NetShareDel: Running [%s]\n", command ));
1971
1972         /********* BEGIN SeDiskOperatorPrivilege BLOCK *********/
1973
1974         if ( is_disk_op )
1975                 become_root();
1976
1977         if ( (ret = smbrun(command, NULL)) == 0 ) {
1978                 /* Tell everyone we updated smb.conf. */
1979                 message_send_all(smbd_messaging_context(),
1980                                  MSG_SMB_CONF_UPDATED, NULL, 0, NULL);
1981         }
1982
1983         if ( is_disk_op )
1984                 unbecome_root();
1985
1986         /********* END SeDiskOperatorPrivilege BLOCK *********/
1987
1988         DEBUG(3,("_srvsvc_NetShareDel: Running [%s] returned (%d)\n", command, ret ));
1989
1990         if ( ret != 0 )
1991                 return WERR_ACCESS_DENIED;
1992
1993         /* Delete the SD in the database. */
1994         delete_share_security(lp_servicename(params->service));
1995
1996         lp_killservice(params->service);
1997
1998         return WERR_OK;
1999 }
2000
2001 /*******************************************************************
2002  _srvsvc_NetShareDelSticky
2003 ********************************************************************/
2004
2005 WERROR _srvsvc_NetShareDelSticky(pipes_struct *p,
2006                                  struct srvsvc_NetShareDelSticky *r)
2007 {
2008         struct srvsvc_NetShareDel q;
2009
2010         DEBUG(5,("_srvsvc_NetShareDelSticky: %d\n", __LINE__));
2011
2012         q.in.server_unc         = r->in.server_unc;
2013         q.in.share_name         = r->in.share_name;
2014         q.in.reserved           = r->in.reserved;
2015
2016         return _srvsvc_NetShareDel(p, &q);
2017 }
2018
2019 /*******************************************************************
2020  _srvsvc_NetRemoteTOD
2021 ********************************************************************/
2022
2023 WERROR _srvsvc_NetRemoteTOD(pipes_struct *p,
2024                             struct srvsvc_NetRemoteTOD *r)
2025 {
2026         struct srvsvc_NetRemoteTODInfo *tod;
2027         struct tm *t;
2028         time_t unixdate = time(NULL);
2029
2030         /* We do this call first as if we do it *after* the gmtime call
2031            it overwrites the pointed-to values. JRA */
2032
2033         uint32 zone = get_time_zone(unixdate)/60;
2034
2035         DEBUG(5,("_srvsvc_NetRemoteTOD: %d\n", __LINE__));
2036
2037         if ( !(tod = TALLOC_ZERO_P(p->mem_ctx, struct srvsvc_NetRemoteTODInfo)) )
2038                 return WERR_NOMEM;
2039
2040         *r->out.info = tod;
2041
2042         DEBUG(5,("_srvsvc_NetRemoteTOD: %d\n", __LINE__));
2043
2044         t = gmtime(&unixdate);
2045
2046         /* set up the */
2047         init_srvsvc_NetRemoteTODInfo(tod,
2048                                      unixdate,
2049                                      0,
2050                                      t->tm_hour,
2051                                      t->tm_min,
2052                                      t->tm_sec,
2053                                      0,
2054                                      zone,
2055                                      10000,
2056                                      t->tm_mday,
2057                                      t->tm_mon + 1,
2058                                      1900+t->tm_year,
2059                                      t->tm_wday);
2060
2061         DEBUG(5,("_srvsvc_NetRemoteTOD: %d\n", __LINE__));
2062
2063         return WERR_OK;
2064 }
2065
2066 /***********************************************************************************
2067  Win9x NT tools get security descriptor.
2068 ***********************************************************************************/
2069
2070 WERROR _srv_net_file_query_secdesc(pipes_struct *p, SRV_Q_NET_FILE_QUERY_SECDESC *q_u,
2071                         SRV_R_NET_FILE_QUERY_SECDESC *r_u)
2072 {
2073         SEC_DESC *psd = NULL;
2074         size_t sd_size;
2075         DATA_BLOB null_pw;
2076         char *filename_in = NULL;
2077         char *filename = NULL;
2078         char *qualname = NULL;
2079         SMB_STRUCT_STAT st;
2080         NTSTATUS nt_status;
2081         struct current_user user;
2082         connection_struct *conn = NULL;
2083         bool became_user = False;
2084         TALLOC_CTX *ctx = p->mem_ctx;
2085
2086         ZERO_STRUCT(st);
2087
2088         r_u->status = WERR_OK;
2089
2090         qualname = unistr2_to_ascii_talloc(ctx, &q_u->uni_qual_name);
2091         if (!qualname) {
2092                 r_u->status = WERR_ACCESS_DENIED;
2093                 goto error_exit;
2094         }
2095
2096         /* Null password is ok - we are already an authenticated user... */
2097         null_pw = data_blob_null;
2098
2099         get_current_user(&user, p);
2100
2101         become_root();
2102         conn = make_connection(qualname, null_pw, "A:", user.vuid, &nt_status);
2103         unbecome_root();
2104
2105         if (conn == NULL) {
2106                 DEBUG(3,("_srv_net_file_query_secdesc: Unable to connect to %s\n", qualname));
2107                 r_u->status = ntstatus_to_werror(nt_status);
2108                 goto error_exit;
2109         }
2110
2111         if (!become_user(conn, conn->vuid)) {
2112                 DEBUG(0,("_srv_net_file_query_secdesc: Can't become connected user!\n"));
2113                 r_u->status = WERR_ACCESS_DENIED;
2114                 goto error_exit;
2115         }
2116         became_user = True;
2117
2118         filename_in = unistr2_to_ascii_talloc(ctx, &q_u->uni_file_name);
2119         if (!filename_in) {
2120                 r_u->status = WERR_ACCESS_DENIED;
2121                 goto error_exit;
2122         }
2123
2124         nt_status = unix_convert(ctx, conn, filename_in, False, &filename, NULL, &st);
2125         if (!NT_STATUS_IS_OK(nt_status)) {
2126                 DEBUG(3,("_srv_net_file_query_secdesc: bad pathname %s\n", filename));
2127                 r_u->status = WERR_ACCESS_DENIED;
2128                 goto error_exit;
2129         }
2130
2131         nt_status = check_name(conn, filename);
2132         if (!NT_STATUS_IS_OK(nt_status)) {
2133                 DEBUG(3,("_srv_net_file_query_secdesc: can't access %s\n", filename));
2134                 r_u->status = WERR_ACCESS_DENIED;
2135                 goto error_exit;
2136         }
2137
2138         nt_status = SMB_VFS_GET_NT_ACL(conn, filename,
2139                                        (OWNER_SECURITY_INFORMATION
2140                                         |GROUP_SECURITY_INFORMATION
2141                                         |DACL_SECURITY_INFORMATION), &psd);
2142
2143         if (!NT_STATUS_IS_OK(nt_status)) {
2144                 DEBUG(3,("_srv_net_file_query_secdesc: Unable to get NT ACL for file %s\n", filename));
2145                 r_u->status = ntstatus_to_werror(nt_status);
2146                 goto error_exit;
2147         }
2148
2149         sd_size = ndr_size_security_descriptor(psd, 0);
2150
2151         r_u->ptr_response = 1;
2152         r_u->size_response = sd_size;
2153         r_u->ptr_secdesc = 1;
2154         r_u->size_secdesc = sd_size;
2155         r_u->sec_desc = psd;
2156
2157         psd->dacl->revision = NT4_ACL_REVISION;
2158
2159         unbecome_user();
2160         close_cnum(conn, user.vuid);
2161         return r_u->status;
2162
2163 error_exit:
2164
2165         if (became_user)
2166                 unbecome_user();
2167
2168         if (conn)
2169                 close_cnum(conn, user.vuid);
2170
2171         return r_u->status;
2172 }
2173
2174 /***********************************************************************************
2175  Win9x NT tools set security descriptor.
2176 ***********************************************************************************/
2177
2178 WERROR _srv_net_file_set_secdesc(pipes_struct *p, SRV_Q_NET_FILE_SET_SECDESC *q_u,
2179                                                                         SRV_R_NET_FILE_SET_SECDESC *r_u)
2180 {
2181         char *filename_in = NULL;
2182         char *filename = NULL;
2183         char *qualname = NULL;
2184         DATA_BLOB null_pw;
2185         files_struct *fsp = NULL;
2186         SMB_STRUCT_STAT st;
2187         NTSTATUS nt_status;
2188         struct current_user user;
2189         connection_struct *conn = NULL;
2190         bool became_user = False;
2191         TALLOC_CTX *ctx = p->mem_ctx;
2192
2193         ZERO_STRUCT(st);
2194
2195         r_u->status = WERR_OK;
2196
2197         qualname = unistr2_to_ascii_talloc(ctx, &q_u->uni_qual_name);
2198         if (!qualname) {
2199                 r_u->status = WERR_ACCESS_DENIED;
2200                 goto error_exit;
2201         }
2202
2203         /* Null password is ok - we are already an authenticated user... */
2204         null_pw = data_blob_null;
2205
2206         get_current_user(&user, p);
2207
2208         become_root();
2209         conn = make_connection(qualname, null_pw, "A:", user.vuid, &nt_status);
2210         unbecome_root();
2211
2212         if (conn == NULL) {
2213                 DEBUG(3,("_srv_net_file_set_secdesc: Unable to connect to %s\n", qualname));
2214                 r_u->status = ntstatus_to_werror(nt_status);
2215                 goto error_exit;
2216         }
2217
2218         if (!become_user(conn, conn->vuid)) {
2219                 DEBUG(0,("_srv_net_file_set_secdesc: Can't become connected user!\n"));
2220                 r_u->status = WERR_ACCESS_DENIED;
2221                 goto error_exit;
2222         }
2223         became_user = True;
2224
2225         filename_in= unistr2_to_ascii_talloc(ctx, &q_u->uni_file_name);
2226         if (!filename_in) {
2227                 r_u->status = WERR_ACCESS_DENIED;
2228                 goto error_exit;
2229         }
2230
2231         nt_status = unix_convert(ctx, conn, filename, False, &filename, NULL, &st);
2232         if (!NT_STATUS_IS_OK(nt_status)) {
2233                 DEBUG(3,("_srv_net_file_set_secdesc: bad pathname %s\n", filename));
2234                 r_u->status = WERR_ACCESS_DENIED;
2235                 goto error_exit;
2236         }
2237
2238         nt_status = check_name(conn, filename);
2239         if (!NT_STATUS_IS_OK(nt_status)) {
2240                 DEBUG(3,("_srv_net_file_set_secdesc: can't access %s\n", filename));
2241                 r_u->status = WERR_ACCESS_DENIED;
2242                 goto error_exit;
2243         }
2244
2245         nt_status = open_file_stat(conn, NULL, filename, &st, &fsp);
2246
2247         if ( !NT_STATUS_IS_OK(nt_status) ) {
2248                 /* Perhaps it is a directory */
2249                 if (NT_STATUS_EQUAL(nt_status, NT_STATUS_FILE_IS_A_DIRECTORY))
2250                         nt_status = open_directory(conn, NULL, filename, &st,
2251                                                 FILE_READ_ATTRIBUTES,
2252                                                 FILE_SHARE_READ|FILE_SHARE_WRITE,
2253                                                 FILE_OPEN,
2254                                                 0,
2255                                                 FILE_ATTRIBUTE_DIRECTORY,
2256                                                 NULL, &fsp);
2257
2258                 if ( !NT_STATUS_IS_OK(nt_status) ) {
2259                         DEBUG(3,("_srv_net_file_set_secdesc: Unable to open file %s\n", filename));
2260                         r_u->status = ntstatus_to_werror(nt_status);
2261                         goto error_exit;
2262                 }
2263         }
2264
2265         nt_status = SMB_VFS_SET_NT_ACL(fsp, fsp->fsp_name, q_u->sec_info, q_u->sec_desc);
2266
2267         if (!NT_STATUS_IS_OK(nt_status) ) {
2268                 DEBUG(3,("_srv_net_file_set_secdesc: Unable to set NT ACL on file %s\n", filename));
2269                 r_u->status = WERR_ACCESS_DENIED;
2270                 goto error_exit;
2271         }
2272
2273         close_file(fsp, NORMAL_CLOSE);
2274         unbecome_user();
2275         close_cnum(conn, user.vuid);
2276         return r_u->status;
2277
2278 error_exit:
2279
2280         if(fsp) {
2281                 close_file(fsp, NORMAL_CLOSE);
2282         }
2283
2284         if (became_user) {
2285                 unbecome_user();
2286         }
2287
2288         if (conn) {
2289                 close_cnum(conn, user.vuid);
2290         }
2291
2292         return r_u->status;
2293 }
2294
2295 /***********************************************************************************
2296  It may be that we want to limit users to creating shares on certain areas of the UNIX file area.
2297  We could define areas by mapping Windows style disks to points on the UNIX directory hierarchy.
2298  These disks would the disks listed by this function.
2299  Users could then create shares relative to these disks.  Watch out for moving these disks around.
2300  "Nigel Williams" <nigel@veritas.com>.
2301 ***********************************************************************************/
2302
2303 static const char *server_disks[] = {"C:"};
2304
2305 static uint32 get_server_disk_count(void)
2306 {
2307         return sizeof(server_disks)/sizeof(server_disks[0]);
2308 }
2309
2310 static uint32 init_server_disk_enum(uint32 *resume)
2311 {
2312         uint32 server_disk_count = get_server_disk_count();
2313
2314         /*resume can be an offset into the list for now*/
2315
2316         if(*resume & 0x80000000)
2317                 *resume = 0;
2318
2319         if(*resume > server_disk_count)
2320                 *resume = server_disk_count;
2321
2322         return server_disk_count - *resume;
2323 }
2324
2325 static const char *next_server_disk_enum(uint32 *resume)
2326 {
2327         const char *disk;
2328
2329         if(init_server_disk_enum(resume) == 0)
2330                 return NULL;
2331
2332         disk = server_disks[*resume];
2333
2334         (*resume)++;
2335
2336         DEBUG(10, ("next_server_disk_enum: reporting disk %s. resume handle %d.\n", disk, *resume));
2337
2338         return disk;
2339 }
2340
2341 WERROR _srv_net_disk_enum(pipes_struct *p, SRV_Q_NET_DISK_ENUM *q_u, SRV_R_NET_DISK_ENUM *r_u)
2342 {
2343         uint32 i;
2344         const char *disk_name;
2345         TALLOC_CTX *ctx = p->mem_ctx;
2346         uint32 resume=get_enum_hnd(&q_u->enum_hnd);
2347
2348         r_u->status=WERR_OK;
2349
2350         r_u->total_entries = init_server_disk_enum(&resume);
2351
2352         r_u->disk_enum_ctr.unknown = 0;
2353
2354         if(!(r_u->disk_enum_ctr.disk_info =  TALLOC_ARRAY(ctx, DISK_INFO, MAX_SERVER_DISK_ENTRIES))) {
2355                 return WERR_NOMEM;
2356         }
2357
2358         r_u->disk_enum_ctr.disk_info_ptr = r_u->disk_enum_ctr.disk_info ? 1 : 0;
2359
2360         /*allow one DISK_INFO for null terminator*/
2361
2362         for(i = 0; i < MAX_SERVER_DISK_ENTRIES -1 && (disk_name = next_server_disk_enum(&resume)); i++) {
2363
2364                 r_u->disk_enum_ctr.entries_read++;
2365
2366                 /*copy disk name into a unicode string*/
2367
2368                 init_unistr3(&r_u->disk_enum_ctr.disk_info[i].disk_name, disk_name);
2369         }
2370
2371         /* add a terminating null string.  Is this there if there is more data to come? */
2372
2373         r_u->disk_enum_ctr.entries_read++;
2374
2375         init_unistr3(&r_u->disk_enum_ctr.disk_info[i].disk_name, "");
2376
2377         init_enum_hnd(&r_u->enum_hnd, resume);
2378
2379         return r_u->status;
2380 }
2381
2382 /********************************************************************
2383 ********************************************************************/
2384
2385 WERROR _srv_net_name_validate(pipes_struct *p, SRV_Q_NET_NAME_VALIDATE *q_u, SRV_R_NET_NAME_VALIDATE *r_u)
2386 {
2387         fstring sharename;
2388
2389         switch ( q_u->type ) {
2390         case 0x9:
2391                 rpcstr_pull(sharename, q_u->sharename.buffer, sizeof(sharename), q_u->sharename.uni_str_len*2, 0);
2392                 if ( !validate_net_name( sharename, INVALID_SHARENAME_CHARS, sizeof(sharename) ) ) {
2393                         DEBUG(5,("_srv_net_name_validate: Bad sharename \"%s\"\n", sharename));
2394                         return WERR_INVALID_NAME;
2395                 }
2396                 break;
2397
2398         default:
2399                 return WERR_UNKNOWN_LEVEL;
2400         }
2401
2402         return WERR_OK;
2403 }
2404
2405
2406 /********************************************************************
2407 ********************************************************************/
2408
2409 WERROR _srvsvc_NetFileClose(pipes_struct *p, struct srvsvc_NetFileClose *r)
2410 {
2411         return WERR_ACCESS_DENIED;
2412 }
2413
2414
2415 /********************************************************************
2416 ********************************************************************/
2417
2418 WERROR _srvsvc_NetCharDevEnum(pipes_struct *p, struct srvsvc_NetCharDevEnum *r)
2419 {
2420         p->rng_fault_state = True;
2421         return WERR_NOT_SUPPORTED;
2422 }
2423
2424 WERROR _srvsvc_NetCharDevGetInfo(pipes_struct *p, struct srvsvc_NetCharDevGetInfo *r)
2425 {
2426         p->rng_fault_state = True;
2427         return WERR_NOT_SUPPORTED;
2428 }
2429
2430 WERROR _srvsvc_NetCharDevControl(pipes_struct *p, struct srvsvc_NetCharDevControl *r)
2431 {
2432         p->rng_fault_state = True;
2433         return WERR_NOT_SUPPORTED;
2434 }
2435
2436 WERROR _srvsvc_NetCharDevQEnum(pipes_struct *p, struct srvsvc_NetCharDevQEnum *r)
2437 {
2438         p->rng_fault_state = True;
2439         return WERR_NOT_SUPPORTED;
2440 }
2441
2442 WERROR _srvsvc_NetCharDevQGetInfo(pipes_struct *p, struct srvsvc_NetCharDevQGetInfo *r)
2443 {
2444         p->rng_fault_state = True;
2445         return WERR_NOT_SUPPORTED;
2446 }
2447
2448 WERROR _srvsvc_NetCharDevQSetInfo(pipes_struct *p, struct srvsvc_NetCharDevQSetInfo *r)
2449 {
2450         p->rng_fault_state = True;
2451         return WERR_NOT_SUPPORTED;
2452 }
2453
2454 WERROR _srvsvc_NetCharDevQPurge(pipes_struct *p, struct srvsvc_NetCharDevQPurge *r)
2455 {
2456         p->rng_fault_state = True;
2457         return WERR_NOT_SUPPORTED;
2458 }
2459
2460 WERROR _srvsvc_NetCharDevQPurgeSelf(pipes_struct *p, struct srvsvc_NetCharDevQPurgeSelf *r)
2461 {
2462         p->rng_fault_state = True;
2463         return WERR_NOT_SUPPORTED;
2464 }
2465
2466 WERROR _srvsvc_NetConnEnum(pipes_struct *p, struct srvsvc_NetConnEnum *r)
2467 {
2468         p->rng_fault_state = True;
2469         return WERR_NOT_SUPPORTED;
2470 }
2471
2472 WERROR _srvsvc_NetFileEnum(pipes_struct *p, struct srvsvc_NetFileEnum *r)
2473 {
2474         p->rng_fault_state = True;
2475         return WERR_NOT_SUPPORTED;
2476 }
2477
2478 WERROR _srvsvc_NetFileGetInfo(pipes_struct *p, struct srvsvc_NetFileGetInfo *r)
2479 {
2480         p->rng_fault_state = True;
2481         return WERR_NOT_SUPPORTED;
2482 }
2483
2484 WERROR _srvsvc_NetSessEnum(pipes_struct *p, struct srvsvc_NetSessEnum *r)
2485 {
2486         p->rng_fault_state = True;
2487         return WERR_NOT_SUPPORTED;
2488 }
2489
2490 WERROR _srvsvc_NetSessDel(pipes_struct *p, struct srvsvc_NetSessDel *r)
2491 {
2492         p->rng_fault_state = True;
2493         return WERR_NOT_SUPPORTED;
2494 }
2495
2496 WERROR _srvsvc_NetShareAdd(pipes_struct *p, struct srvsvc_NetShareAdd *r)
2497 {
2498         p->rng_fault_state = True;
2499         return WERR_NOT_SUPPORTED;
2500 }
2501
2502 WERROR _srvsvc_NetShareCheck(pipes_struct *p, struct srvsvc_NetShareCheck *r)
2503 {
2504         p->rng_fault_state = True;
2505         return WERR_NOT_SUPPORTED;
2506 }
2507
2508 WERROR _srvsvc_NetDiskEnum(pipes_struct *p, struct srvsvc_NetDiskEnum *r)
2509 {
2510         p->rng_fault_state = True;
2511         return WERR_NOT_SUPPORTED;
2512 }
2513
2514 WERROR _srvsvc_NetServerStatisticsGet(pipes_struct *p, struct srvsvc_NetServerStatisticsGet *r)
2515 {
2516         p->rng_fault_state = True;
2517         return WERR_NOT_SUPPORTED;
2518 }
2519
2520 WERROR _srvsvc_NetTransportAdd(pipes_struct *p, struct srvsvc_NetTransportAdd *r)
2521 {
2522         p->rng_fault_state = True;
2523         return WERR_NOT_SUPPORTED;
2524 }
2525
2526 WERROR _srvsvc_NetTransportEnum(pipes_struct *p, struct srvsvc_NetTransportEnum *r)
2527 {
2528         p->rng_fault_state = True;
2529         return WERR_NOT_SUPPORTED;
2530 }
2531
2532 WERROR _srvsvc_NetTransportDel(pipes_struct *p, struct srvsvc_NetTransportDel *r)
2533 {
2534         p->rng_fault_state = True;
2535         return WERR_NOT_SUPPORTED;
2536 }
2537
2538 WERROR _srvsvc_NetSetServiceBits(pipes_struct *p, struct srvsvc_NetSetServiceBits *r)
2539 {
2540         p->rng_fault_state = True;
2541         return WERR_NOT_SUPPORTED;
2542 }
2543
2544 WERROR _srvsvc_NetPathType(pipes_struct *p, struct srvsvc_NetPathType *r)
2545 {
2546         p->rng_fault_state = True;
2547         return WERR_NOT_SUPPORTED;
2548 }
2549
2550 WERROR _srvsvc_NetPathCanonicalize(pipes_struct *p, struct srvsvc_NetPathCanonicalize *r)
2551 {
2552         p->rng_fault_state = True;
2553         return WERR_NOT_SUPPORTED;
2554 }
2555
2556 WERROR _srvsvc_NetPathCompare(pipes_struct *p, struct srvsvc_NetPathCompare *r)
2557 {
2558         p->rng_fault_state = True;
2559         return WERR_NOT_SUPPORTED;
2560 }
2561
2562 WERROR _srvsvc_NetNameValidate(pipes_struct *p, struct srvsvc_NetNameValidate *r)
2563 {
2564         p->rng_fault_state = True;
2565         return WERR_NOT_SUPPORTED;
2566 }
2567
2568 WERROR _srvsvc_NETRPRNAMECANONICALIZE(pipes_struct *p, struct srvsvc_NETRPRNAMECANONICALIZE *r)
2569 {
2570         p->rng_fault_state = True;
2571         return WERR_NOT_SUPPORTED;
2572 }
2573
2574 WERROR _srvsvc_NetPRNameCompare(pipes_struct *p, struct srvsvc_NetPRNameCompare *r)
2575 {
2576         p->rng_fault_state = True;
2577         return WERR_NOT_SUPPORTED;
2578 }
2579
2580 WERROR _srvsvc_NetShareDelStart(pipes_struct *p, struct srvsvc_NetShareDelStart *r)
2581 {
2582         p->rng_fault_state = True;
2583         return WERR_NOT_SUPPORTED;
2584 }
2585
2586 WERROR _srvsvc_NetShareDelCommit(pipes_struct *p, struct srvsvc_NetShareDelCommit *r)
2587 {
2588         p->rng_fault_state = True;
2589         return WERR_NOT_SUPPORTED;
2590 }
2591
2592 WERROR _srvsvc_NetGetFileSecurity(pipes_struct *p, struct srvsvc_NetGetFileSecurity *r)
2593 {
2594         p->rng_fault_state = True;
2595         return WERR_NOT_SUPPORTED;
2596 }
2597
2598 WERROR _srvsvc_NetSetFileSecurity(pipes_struct *p, struct srvsvc_NetSetFileSecurity *r)
2599 {
2600         p->rng_fault_state = True;
2601         return WERR_NOT_SUPPORTED;
2602 }
2603
2604 WERROR _srvsvc_NetServerTransportAddEx(pipes_struct *p, struct srvsvc_NetServerTransportAddEx *r)
2605 {
2606         p->rng_fault_state = True;
2607         return WERR_NOT_SUPPORTED;
2608 }
2609
2610 WERROR _srvsvc_NetServerSetServiceBitsEx(pipes_struct *p, struct srvsvc_NetServerSetServiceBitsEx *r)
2611 {
2612         p->rng_fault_state = True;
2613         return WERR_NOT_SUPPORTED;
2614 }
2615
2616 WERROR _srvsvc_NETRDFSGETVERSION(pipes_struct *p, struct srvsvc_NETRDFSGETVERSION *r)
2617 {
2618         p->rng_fault_state = True;
2619         return WERR_NOT_SUPPORTED;
2620 }
2621
2622 WERROR _srvsvc_NETRDFSCREATELOCALPARTITION(pipes_struct *p, struct srvsvc_NETRDFSCREATELOCALPARTITION *r)
2623 {
2624         p->rng_fault_state = True;
2625         return WERR_NOT_SUPPORTED;
2626 }
2627
2628 WERROR _srvsvc_NETRDFSDELETELOCALPARTITION(pipes_struct *p, struct srvsvc_NETRDFSDELETELOCALPARTITION *r)
2629 {
2630         p->rng_fault_state = True;
2631         return WERR_NOT_SUPPORTED;
2632 }
2633
2634 WERROR _srvsvc_NETRDFSSETLOCALVOLUMESTATE(pipes_struct *p, struct srvsvc_NETRDFSSETLOCALVOLUMESTATE *r)
2635 {
2636         p->rng_fault_state = True;
2637         return WERR_NOT_SUPPORTED;
2638 }
2639
2640 WERROR _srvsvc_NETRDFSSETSERVERINFO(pipes_struct *p, struct srvsvc_NETRDFSSETSERVERINFO *r)
2641 {
2642         p->rng_fault_state = True;
2643         return WERR_NOT_SUPPORTED;
2644 }
2645
2646 WERROR _srvsvc_NETRDFSCREATEEXITPOINT(pipes_struct *p, struct srvsvc_NETRDFSCREATEEXITPOINT *r)
2647 {
2648         p->rng_fault_state = True;
2649         return WERR_NOT_SUPPORTED;
2650 }
2651
2652 WERROR _srvsvc_NETRDFSDELETEEXITPOINT(pipes_struct *p, struct srvsvc_NETRDFSDELETEEXITPOINT *r)
2653 {
2654         p->rng_fault_state = True;
2655         return WERR_NOT_SUPPORTED;
2656 }
2657
2658 WERROR _srvsvc_NETRDFSMODIFYPREFIX(pipes_struct *p, struct srvsvc_NETRDFSMODIFYPREFIX *r)
2659 {
2660         p->rng_fault_state = True;
2661         return WERR_NOT_SUPPORTED;
2662 }
2663
2664 WERROR _srvsvc_NETRDFSFIXLOCALVOLUME(pipes_struct *p, struct srvsvc_NETRDFSFIXLOCALVOLUME *r)
2665 {
2666         p->rng_fault_state = True;
2667         return WERR_NOT_SUPPORTED;
2668 }
2669
2670 WERROR _srvsvc_NETRDFSMANAGERREPORTSITEINFO(pipes_struct *p, struct srvsvc_NETRDFSMANAGERREPORTSITEINFO *r)
2671 {
2672         p->rng_fault_state = True;
2673         return WERR_NOT_SUPPORTED;
2674 }
2675
2676 WERROR _srvsvc_NETRSERVERTRANSPORTDELEX(pipes_struct *p, struct srvsvc_NETRSERVERTRANSPORTDELEX *r)
2677 {
2678         p->rng_fault_state = True;
2679         return WERR_NOT_SUPPORTED;
2680 }
2681