1 /*
2 Unix SMB/CIFS implementation.
3
4 endpoint server for the srvsvc pipe
5
6 Copyright (C) Stefan (metze) Metzmacher 2004-2006
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 */
22
23 #include "includes.h"
24 #include "ntvfs/ntvfs.h"
25 #include "rpc_server/dcerpc_server.h"
26 #include "librpc/gen_ndr/ndr_srvsvc.h"
27 #include "rpc_server/common/common.h"
28 #include "auth/auth.h"
29 #include "libcli/security/security.h"
30 #include "system/time.h"
31 #include "rpc_server/srvsvc/proto.h"
32
33 #define SRVSVC_CHECK_ADMIN_ACCESS do { \
34 struct security_token *t = dce_call->conn->auth_state.session_info->security_token; \
35 if (!security_token_has_builtin_administrators(t) && \
36 !security_token_has_sid_string(t, SID_BUILTIN_SERVER_OPERATORS)) { \
37 return WERR_ACCESS_DENIED; \
38 } \
39 } while (0)
40
41 /*
42 srvsvc_NetCharDevEnum
43 */
srvsvc_NetCharDevEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevEnum * r)44 static WERROR srvsvc_NetCharDevEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
45 struct srvsvc_NetCharDevEnum *r)
46 {
47 r->out.level = r->in.level;
48 r->out.totalentries = 0;
49 r->out.resume_handle = NULL;
50
51 switch (r->in.level) {
52 case 0:
53 r->out.ctr.ctr0 = talloc(mem_ctx, struct srvsvc_NetCharDevCtr0);
54 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr0);
55
56 r->out.ctr.ctr0->count = 0;
57 r->out.ctr.ctr0->array = NULL;
58
59 return WERR_NOT_SUPPORTED;
60
61 case 1:
62 r->out.ctr.ctr1 = talloc(mem_ctx, struct srvsvc_NetCharDevCtr1);
63 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr1);
64
65 r->out.ctr.ctr1->count = 0;
66 r->out.ctr.ctr1->array = NULL;
67
68 return WERR_NOT_SUPPORTED;
69
70 default:
71 return WERR_UNKNOWN_LEVEL;
72 }
73
74 return WERR_OK;
75 }
76
77
78 /*
79 srvsvc_NetCharDevGetInfo
80 */
srvsvc_NetCharDevGetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevGetInfo * r)81 static WERROR srvsvc_NetCharDevGetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
82 struct srvsvc_NetCharDevGetInfo *r)
83 {
84 ZERO_STRUCT(r->out);
85
86 switch (r->in.level) {
87 case 0:
88 {
89 return WERR_NOT_SUPPORTED;
90 }
91 case 1:
92 {
93 return WERR_NOT_SUPPORTED;
94 }
95 default:
96 return WERR_UNKNOWN_LEVEL;
97 }
98
99 return WERR_UNKNOWN_LEVEL;
100 }
101
102
103 /*
104 srvsvc_NetCharDevControl
105 */
srvsvc_NetCharDevControl(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevControl * r)106 static WERROR srvsvc_NetCharDevControl(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
107 struct srvsvc_NetCharDevControl *r)
108 {
109 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
110 }
111
112
113 /*
114 srvsvc_NetCharDevQEnum
115 */
srvsvc_NetCharDevQEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevQEnum * r)116 static WERROR srvsvc_NetCharDevQEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
117 struct srvsvc_NetCharDevQEnum *r)
118 {
119 r->out.level = r->in.level;
120 r->out.totalentries = 0;
121 r->out.resume_handle = NULL;
122
123 switch (r->in.level) {
124 case 0:
125 {
126 r->out.ctr.ctr0 = talloc(mem_ctx, struct srvsvc_NetCharDevQCtr0);
127 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr0);
128
129 r->out.ctr.ctr0->count = 0;
130 r->out.ctr.ctr0->array = NULL;
131
132 return WERR_NOT_SUPPORTED;
133 }
134 case 1:
135 {
136 r->out.ctr.ctr1 = talloc(mem_ctx, struct srvsvc_NetCharDevQCtr1);
137 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr1);
138
139 r->out.ctr.ctr1->count = 0;
140 r->out.ctr.ctr1->array = NULL;
141
142 return WERR_NOT_SUPPORTED;
143 }
144 default:
145 return WERR_UNKNOWN_LEVEL;
146 }
147
148 return WERR_UNKNOWN_LEVEL;
149 }
150
151
152 /*
153 srvsvc_NetCharDevQGetInfo
154 */
srvsvc_NetCharDevQGetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevQGetInfo * r)155 static WERROR srvsvc_NetCharDevQGetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
156 struct srvsvc_NetCharDevQGetInfo *r)
157 {
158 ZERO_STRUCT(r->out);
159
160 switch (r->in.level) {
161 case 0:
162 {
163 return WERR_NOT_SUPPORTED;
164 }
165 case 1:
166 {
167 return WERR_NOT_SUPPORTED;
168 }
169 default:
170 return WERR_UNKNOWN_LEVEL;
171 }
172
173 return WERR_UNKNOWN_LEVEL;
174 }
175
176
177 /*
178 srvsvc_NetCharDevQSetInfo
179 */
srvsvc_NetCharDevQSetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevQSetInfo * r)180 static WERROR srvsvc_NetCharDevQSetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
181 struct srvsvc_NetCharDevQSetInfo *r)
182 {
183 switch (r->in.level) {
184 case 0:
185 {
186 if (r->in.parm_error) {
187 r->out.parm_error = r->in.parm_error;
188 }
189 return WERR_NOT_SUPPORTED;
190 }
191 case 1:
192 {
193 if (r->in.parm_error) {
194 r->out.parm_error = r->in.parm_error;
195 }
196 return WERR_NOT_SUPPORTED;
197 }
198 default:
199 return WERR_UNKNOWN_LEVEL;
200 }
201
202 return WERR_UNKNOWN_LEVEL;
203 }
204
205
206 /*
207 srvsvc_NetCharDevQPurge
208 */
srvsvc_NetCharDevQPurge(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevQPurge * r)209 static WERROR srvsvc_NetCharDevQPurge(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
210 struct srvsvc_NetCharDevQPurge *r)
211 {
212 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
213 }
214
215
216 /*
217 srvsvc_NetCharDevQPurgeSelf
218 */
srvsvc_NetCharDevQPurgeSelf(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetCharDevQPurgeSelf * r)219 static WERROR srvsvc_NetCharDevQPurgeSelf(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
220 struct srvsvc_NetCharDevQPurgeSelf *r)
221 {
222 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
223 }
224
225
226 /*
227 srvsvc_NetConnEnum
228 */
srvsvc_NetConnEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetConnEnum * r)229 static WERROR srvsvc_NetConnEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
230 struct srvsvc_NetConnEnum *r)
231 {
232 r->out.level = r->in.level;
233 r->out.totalentries = 0;
234 r->out.resume_handle = NULL;
235
236 switch (r->in.level) {
237 case 0:
238 {
239 r->out.ctr.ctr0 = talloc(mem_ctx, struct srvsvc_NetConnCtr0);
240 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr0);
241
242 r->out.ctr.ctr0->count = 0;
243 r->out.ctr.ctr0->array = NULL;
244
245 return WERR_NOT_SUPPORTED;
246 }
247 case 1:
248 {
249 r->out.ctr.ctr1 = talloc(mem_ctx, struct srvsvc_NetConnCtr1);
250 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr1);
251
252 r->out.ctr.ctr1->count = 0;
253 r->out.ctr.ctr1->array = NULL;
254
255 return WERR_NOT_SUPPORTED;
256 }
257 default:
258 return WERR_UNKNOWN_LEVEL;
259 }
260
261 return WERR_UNKNOWN_LEVEL;
262 }
263
264
265 /*
266 srvsvc_NetFileEnum
267 */
srvsvc_NetFileEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetFileEnum * r)268 static WERROR srvsvc_NetFileEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
269 struct srvsvc_NetFileEnum *r)
270 {
271 r->out.level = r->in.level;
272 r->out.totalentries = 0;
273 r->out.resume_handle = NULL;
274
275 switch (r->in.level) {
276 case 2:
277 {
278 r->out.ctr.ctr2 = talloc(mem_ctx, struct srvsvc_NetFileCtr2);
279 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr2);
280
281 r->out.ctr.ctr2->count = 0;
282 r->out.ctr.ctr2->array = NULL;
283
284 return WERR_NOT_SUPPORTED;
285 }
286 case 3:
287 {
288 r->out.ctr.ctr3 = talloc(mem_ctx, struct srvsvc_NetFileCtr3);
289 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr3);
290
291 r->out.ctr.ctr3->count = 0;
292 r->out.ctr.ctr3->array = NULL;
293
294 return WERR_NOT_SUPPORTED;
295 }
296 default:
297 return WERR_UNKNOWN_LEVEL;
298 }
299
300 return WERR_UNKNOWN_LEVEL;
301 }
302
303
304 /*
305 srvsvc_NetFileGetInfo
306 */
srvsvc_NetFileGetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetFileGetInfo * r)307 static WERROR srvsvc_NetFileGetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
308 struct srvsvc_NetFileGetInfo *r)
309 {
310 ZERO_STRUCT(r->out);
311
312 switch (r->in.level) {
313 case 2:
314 {
315 return WERR_NOT_SUPPORTED;
316 }
317 case 3:
318 {
319 return WERR_NOT_SUPPORTED;
320 }
321 default:
322 return WERR_UNKNOWN_LEVEL;
323 }
324
325 return WERR_UNKNOWN_LEVEL;
326 }
327
328
329 /*
330 srvsvc_NetFileClose
331 */
srvsvc_NetFileClose(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetFileClose * r)332 static WERROR srvsvc_NetFileClose(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
333 struct srvsvc_NetFileClose *r)
334 {
335 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
336 }
337
338
339 /*
340 srvsvc_NetSessEnum
341 */
srvsvc_NetSessEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSessEnum * r)342 static WERROR srvsvc_NetSessEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
343 struct srvsvc_NetSessEnum *r)
344 {
345 r->out.level = r->in.level;
346 r->out.totalentries = 0;
347 r->out.resume_handle = NULL;
348
349 switch (r->in.level) {
350 case 0:
351 {
352 r->out.ctr.ctr0 = talloc(mem_ctx, struct srvsvc_NetSessCtr0);
353 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr0);
354
355 r->out.ctr.ctr0->count = 0;
356 r->out.ctr.ctr0->array = NULL;
357
358 return WERR_NOT_SUPPORTED;
359 }
360 case 1:
361 {
362 r->out.ctr.ctr1 = talloc(mem_ctx, struct srvsvc_NetSessCtr1);
363 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr1);
364
365 r->out.ctr.ctr1->count = 0;
366 r->out.ctr.ctr1->array = NULL;
367
368 return WERR_NOT_SUPPORTED;
369 }
370 case 2:
371 {
372 r->out.ctr.ctr2 = talloc(mem_ctx, struct srvsvc_NetSessCtr2);
373 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr2);
374
375 r->out.ctr.ctr2->count = 0;
376 r->out.ctr.ctr2->array = NULL;
377
378 return WERR_NOT_SUPPORTED;
379 }
380 case 10:
381 {
382 r->out.ctr.ctr10 = talloc(mem_ctx, struct srvsvc_NetSessCtr10);
383 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr10);
384
385 r->out.ctr.ctr2->count = 0;
386 r->out.ctr.ctr2->array = NULL;
387
388 return WERR_NOT_SUPPORTED;
389 }
390 case 502:
391 {
392 r->out.ctr.ctr502 = talloc(mem_ctx, struct srvsvc_NetSessCtr502);
393 W_ERROR_HAVE_NO_MEMORY(r->out.ctr.ctr502);
394
395 r->out.ctr.ctr2->count = 0;
396 r->out.ctr.ctr2->array = NULL;
397
398 return WERR_NOT_SUPPORTED;
399 }
400 default:
401 return WERR_UNKNOWN_LEVEL;
402 }
403
404 return WERR_UNKNOWN_LEVEL;
405 }
406
407
408 /*
409 srvsvc_NetSessDel
410 */
srvsvc_NetSessDel(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSessDel * r)411 static WERROR srvsvc_NetSessDel(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
412 struct srvsvc_NetSessDel *r)
413 {
414 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
415 }
416
417
418 /*
419 srvsvc_NetShareAdd
420 */
srvsvc_NetShareAdd(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareAdd * r)421 static WERROR srvsvc_NetShareAdd(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
422 struct srvsvc_NetShareAdd *r)
423 {
424 switch (r->in.level) {
425 case 0:
426 {
427 if (r->in.parm_error) {
428 r->out.parm_error = r->in.parm_error;
429 }
430 return WERR_NOT_SUPPORTED;
431 }
432 case 1:
433 {
434 if (r->in.parm_error) {
435 r->out.parm_error = r->in.parm_error;
436 }
437 return WERR_NOT_SUPPORTED;
438 }
439 case 2:
440 {
441 NTSTATUS nterr;
442 struct share_info *info;
443 struct share_context *sctx;
444 int count = 8;
445 int i;
446
447 nterr = share_get_context(mem_ctx, &sctx);
448 if (!NT_STATUS_IS_OK(nterr)) {
449 return ntstatus_to_werror(nterr);
450 }
451
452 /* there are no more than 8 options in struct srvsvc_NetShareInfo2 */
453 info = talloc_array(mem_ctx, struct share_info, count);
454 W_ERROR_HAVE_NO_MEMORY(info);
455
456 i = 0;
457
458 info[i].name = SHARE_TYPE;
459 info[i].type = SHARE_INFO_STRING;
460 switch (r->in.info.info2->type) {
461 case 0x00:
462 info[i].value = talloc_strdup(info, "DISK");
463 break;
464 case 0x01:
465 info[i].value = talloc_strdup(info, "PRINTER");
466 break;
467 case 0x03:
468 info[i].value = talloc_strdup(info, "IPC");
469 break;
470 default:
471 return WERR_INVALID_PARAM;
472 }
473 W_ERROR_HAVE_NO_MEMORY(info[i].value);
474 i++;
475
476 if (r->in.info.info2->path && r->in.info.info2->path[0]) {
477 info[i].name = SHARE_PATH;
478 info[i].type = SHARE_INFO_STRING;
479
480 /* Windows will send a path in a form of C:\example\path */
481 if (r->in.info.info2->path[1] == ':') {
482 info[i].value = talloc_strdup(info, &r->in.info.info2->path[2]);
483 } else {
484 /* very strange let's try to set as is */
485 info[i].value = talloc_strdup(info, r->in.info.info2->path);
486 }
487 W_ERROR_HAVE_NO_MEMORY(info[i].value);
488 all_string_sub((char *)info[i].value, "\\", "/", 0);
489
490 i++;
491 }
492
493 if (r->in.info.info2->comment && r->in.info.info2->comment[0]) {
494 info[i].name = SHARE_COMMENT;
495 info[i].type = SHARE_INFO_STRING;
496 info[i].value = talloc_strdup(info, r->in.info.info2->comment);
497 W_ERROR_HAVE_NO_MEMORY(info[i].value);
498
499 i++;
500 }
501
502 if (r->in.info.info2->password && r->in.info.info2->password[0]) {
503 info[i].name = SHARE_PASSWORD;
504 info[i].type = SHARE_INFO_STRING;
505 info[i].value = talloc_strdup(info, r->in.info.info502->password);
506 W_ERROR_HAVE_NO_MEMORY(info[i].value);
507
508 i++;
509 }
510
511 info[i].name = SHARE_MAX_CONNECTIONS;
512 info[i].type = SHARE_INFO_INT;
513 info[i].value = talloc(info, int);
514 *((int *)info[i].value) = r->in.info.info2->max_users;
515 i++;
516
517 /* TODO: security descriptor */
518
519 nterr = share_create(sctx, r->in.info.info2->name, info, i);
520 if (!NT_STATUS_IS_OK(nterr)) {
521 return ntstatus_to_werror(nterr);
522 }
523
524 if (r->in.parm_error) {
525 r->out.parm_error = r->in.parm_error;
526 }
527
528 return WERR_OK;
529 }
530 case 501:
531 {
532 if (r->in.parm_error) {
533 r->out.parm_error = r->in.parm_error;
534 }
535 return WERR_NOT_SUPPORTED;
536 }
537 case 502:
538 {
539 NTSTATUS nterr;
540 struct share_info *info;
541 struct share_context *sctx;
542 int count = 10;
543 int i;
544
545 nterr = share_get_context(mem_ctx, &sctx);
546 if (!NT_STATUS_IS_OK(nterr)) {
547 return ntstatus_to_werror(nterr);
548 }
549
550 /* there are no more than 10 options in struct srvsvc_NetShareInfo502 */
551 info = talloc_array(mem_ctx, struct share_info, count);
552 W_ERROR_HAVE_NO_MEMORY(info);
553
554 i = 0;
555
556 info[i].name = SHARE_TYPE;
557 info[i].type = SHARE_INFO_STRING;
558 switch (r->in.info.info502->type) {
559 case 0x00:
560 info[i].value = talloc_strdup(info, "DISK");
561 break;
562 case 0x01:
563 info[i].value = talloc_strdup(info, "PRINTER");
564 break;
565 case 0x03:
566 info[i].value = talloc_strdup(info, "IPC");
567 break;
568 default:
569 return WERR_INVALID_PARAM;
570 }
571 W_ERROR_HAVE_NO_MEMORY(info[i].value);
572 i++;
573
574 if (r->in.info.info502->path && r->in.info.info502->path[0]) {
575 info[i].name = SHARE_PATH;
576 info[i].type = SHARE_INFO_STRING;
577
578 /* Windows will send a path in a form of C:\example\path */
579 if (r->in.info.info2->path[1] == ':') {
580 info[i].value = talloc_strdup(info, &r->in.info.info502->path[2]);
581 } else {
582 /* very strange let's try to set as is */
583 info[i].value = talloc_strdup(info, r->in.info.info502->path);
584 }
585 W_ERROR_HAVE_NO_MEMORY(info[i].value);
586 all_string_sub((char *)info[i].value, "\\", "/", 0);
587
588 i++;
589 }
590
591 if (r->in.info.info502->comment && r->in.info.info502->comment[0]) {
592 info[i].name = SHARE_COMMENT;
593 info[i].type = SHARE_INFO_STRING;
594 info[i].value = talloc_strdup(info, r->in.info.info502->comment);
595 W_ERROR_HAVE_NO_MEMORY(info[i].value);
596
597 i++;
598 }
599
600 if (r->in.info.info502->password && r->in.info.info502->password[0]) {
601 info[i].name = SHARE_PASSWORD;
602 info[i].type = SHARE_INFO_STRING;
603 info[i].value = talloc_strdup(info, r->in.info.info502->password);
604 W_ERROR_HAVE_NO_MEMORY(info[i].value);
605
606 i++;
607 }
608
609 info[i].name = SHARE_MAX_CONNECTIONS;
610 info[i].type = SHARE_INFO_INT;
611 info[i].value = talloc(info, int);
612 *((int *)info[i].value) = r->in.info.info502->max_users;
613 i++;
614
615 /* TODO: security descriptor */
616
617 nterr = share_create(sctx, r->in.info.info502->name, info, i);
618 if (!NT_STATUS_IS_OK(nterr)) {
619 return ntstatus_to_werror(nterr);
620 }
621
622 if (r->in.parm_error) {
623 r->out.parm_error = r->in.parm_error;
624 }
625
626 return WERR_OK;
627 }
628 default:
629 return WERR_UNKNOWN_LEVEL;
630 }
631
632 return WERR_UNKNOWN_LEVEL;
633 }
634
srvsvc_fiel_ShareInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct share_config * scfg,uint32_t level,union srvsvc_NetShareInfo * info)635 static WERROR srvsvc_fiel_ShareInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
636 struct share_config *scfg, uint32_t level,
637 union srvsvc_NetShareInfo *info)
638 {
639 struct dcesrv_context *dce_ctx = dce_call->conn->dce_ctx;
640
641 switch (level) {
642 case 0:
643 {
644 info->info0->name = talloc_strdup(mem_ctx, scfg->name);
645 W_ERROR_HAVE_NO_MEMORY(info->info0->name);
646
647 return WERR_OK;
648 }
649 case 1:
650 {
651 info->info1->name = talloc_strdup(mem_ctx, scfg->name);
652 W_ERROR_HAVE_NO_MEMORY(info->info1->name);
653 info->info1->type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
654 info->info1->comment = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_COMMENT, ""));
655 W_ERROR_HAVE_NO_MEMORY(info->info1->comment);
656
657 return WERR_OK;
658 }
659 case 2:
660 {
661 info->info2->name = talloc_strdup(mem_ctx, scfg->name);
662 W_ERROR_HAVE_NO_MEMORY(info->info2->name);
663 info->info2->type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
664 info->info2->comment = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_COMMENT, ""));
665 W_ERROR_HAVE_NO_MEMORY(info->info2->comment);
666 info->info2->permissions = dcesrv_common_get_share_permissions(mem_ctx, dce_ctx, scfg);
667 info->info2->max_users = share_int_option(scfg, SHARE_MAX_CONNECTIONS, SHARE_MAX_CONNECTIONS_DEFAULT);
668 info->info2->current_users = dcesrv_common_get_share_current_users(mem_ctx, dce_ctx, scfg);
669 info->info2->path = dcesrv_common_get_share_path(mem_ctx, dce_ctx, scfg);
670 W_ERROR_HAVE_NO_MEMORY(info->info2->path);
671 info->info2->password = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_PASSWORD, NULL));
672
673 return WERR_OK;
674 }
675 case 501:
676 {
677 info->info501->name = talloc_strdup(mem_ctx, scfg->name);
678 W_ERROR_HAVE_NO_MEMORY(info->info501->name);
679 info->info501->type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
680 info->info501->comment = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_COMMENT, ""));
681 W_ERROR_HAVE_NO_MEMORY(info->info501->comment);
682 info->info501->csc_policy = share_int_option(scfg, SHARE_CSC_POLICY, SHARE_CSC_POLICY_DEFAULT);
683
684 return WERR_OK;
685 }
686 case 502:
687 {
688 info->info502->name = talloc_strdup(mem_ctx, scfg->name);
689 W_ERROR_HAVE_NO_MEMORY(info->info502->name);
690 info->info502->type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
691 info->info502->comment = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_COMMENT, ""));
692 W_ERROR_HAVE_NO_MEMORY(info->info502->comment);
693 info->info502->permissions = dcesrv_common_get_share_permissions(mem_ctx, dce_ctx, scfg);
694 info->info502->max_users = share_int_option(scfg, SHARE_MAX_CONNECTIONS, SHARE_MAX_CONNECTIONS_DEFAULT);
695 info->info502->current_users = dcesrv_common_get_share_current_users(mem_ctx, dce_ctx, scfg);
696 info->info502->path = dcesrv_common_get_share_path(mem_ctx, dce_ctx, scfg);
697 W_ERROR_HAVE_NO_MEMORY(info->info502->path);
698 info->info502->password = talloc_strdup(mem_ctx, share_string_option(scfg, SHARE_PASSWORD, NULL));
699 info->info502->unknown = dcesrv_common_get_share_unknown(mem_ctx, dce_ctx, scfg);
700 info->info502->sd = dcesrv_common_get_security_descriptor(mem_ctx, dce_ctx, scfg);
701
702 return WERR_OK;
703 }
704 case 1005:
705 {
706 info->info1005->dfs_flags = dcesrv_common_get_share_dfs_flags(mem_ctx, dce_ctx, scfg);
707
708 return WERR_OK;
709 }
710 default:
711 return WERR_UNKNOWN_LEVEL;
712 }
713
714 return WERR_UNKNOWN_LEVEL;
715 }
716
717 /*
718 srvsvc_NetShareEnumAll
719 */
srvsvc_NetShareEnumAll(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareEnumAll * r)720 static WERROR srvsvc_NetShareEnumAll(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
721 struct srvsvc_NetShareEnumAll *r)
722 {
723 NTSTATUS nterr;
724 int numshares = 0;
725 const char **snames;
726 struct share_context *sctx;
727 struct share_config *scfg;
728
729 r->out.level = r->in.level;
730 ZERO_STRUCT(r->out.ctr);
731 r->out.totalentries = 0;
732 r->out.resume_handle = NULL;
733
734 /* TODO: - paging of results
735 */
736
737 nterr = share_get_context(mem_ctx, &sctx);
738 if (!NT_STATUS_IS_OK(nterr)) {
739 return ntstatus_to_werror(nterr);
740 }
741
742 nterr = share_list_all(mem_ctx, sctx, &numshares, &snames);
743 if (!NT_STATUS_IS_OK(nterr)) {
744 return ntstatus_to_werror(nterr);
745 }
746
747 switch (r->in.level) {
748 case 0:
749 {
750 int i;
751 struct srvsvc_NetShareCtr0 *ctr0;
752
753 ctr0 = talloc(mem_ctx, struct srvsvc_NetShareCtr0);
754 W_ERROR_HAVE_NO_MEMORY(ctr0);
755
756 ctr0->count = numshares;
757 ctr0->array = NULL;
758
759 if (ctr0->count == 0) {
760 r->out.ctr.ctr0 = ctr0;
761 return WERR_OK;
762 }
763
764 ctr0->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo0, ctr0->count);
765 W_ERROR_HAVE_NO_MEMORY(ctr0->array);
766
767 for (i = 0; i < ctr0->count; i++) {
768 WERROR status;
769 union srvsvc_NetShareInfo info;
770
771 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
772 if (!NT_STATUS_IS_OK(nterr)) {
773 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
774 return WERR_GENERAL_FAILURE;
775 }
776 info.info0 = &ctr0->array[i];
777 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
778 if (!W_ERROR_IS_OK(status)) {
779 return status;
780 }
781 talloc_free(scfg);
782 }
783 talloc_free(snames);
784
785 r->out.ctr.ctr0 = ctr0;
786 r->out.totalentries = r->out.ctr.ctr0->count;
787 return WERR_OK;
788 }
789 case 1:
790 {
791 int i;
792 struct srvsvc_NetShareCtr1 *ctr1;
793
794 ctr1 = talloc(mem_ctx, struct srvsvc_NetShareCtr1);
795 W_ERROR_HAVE_NO_MEMORY(ctr1);
796
797 ctr1->count = numshares;
798 ctr1->array = NULL;
799
800 if (ctr1->count == 0) {
801 r->out.ctr.ctr1 = ctr1;
802 return WERR_OK;
803 }
804
805 ctr1->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo1, ctr1->count);
806 W_ERROR_HAVE_NO_MEMORY(ctr1->array);
807
808 for (i=0; i < ctr1->count; i++) {
809 WERROR status;
810 union srvsvc_NetShareInfo info;
811
812 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
813 if (!NT_STATUS_IS_OK(nterr)) {
814 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
815 return WERR_GENERAL_FAILURE;
816 }
817 info.info1 = &ctr1->array[i];
818 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
819 if (!W_ERROR_IS_OK(status)) {
820 return status;
821 }
822 talloc_free(scfg);
823 }
824 talloc_free(snames);
825
826 r->out.ctr.ctr1 = ctr1;
827 r->out.totalentries = r->out.ctr.ctr1->count;
828 return WERR_OK;
829 }
830 case 2:
831 {
832 int i;
833 struct srvsvc_NetShareCtr2 *ctr2;
834
835 SRVSVC_CHECK_ADMIN_ACCESS;
836
837 ctr2 = talloc(mem_ctx, struct srvsvc_NetShareCtr2);
838 W_ERROR_HAVE_NO_MEMORY(ctr2);
839
840 ctr2->count = numshares;
841 ctr2->array = NULL;
842
843 if (ctr2->count == 0) {
844 r->out.ctr.ctr2 = ctr2;
845 return WERR_OK;
846 }
847
848 ctr2->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo2, ctr2->count);
849 W_ERROR_HAVE_NO_MEMORY(ctr2->array);
850
851 for (i=0; i < ctr2->count; i++) {
852 WERROR status;
853 union srvsvc_NetShareInfo info;
854
855 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
856 if (!NT_STATUS_IS_OK(nterr)) {
857 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
858 return WERR_GENERAL_FAILURE;
859 }
860 info.info2 = &ctr2->array[i];
861 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
862 if (!W_ERROR_IS_OK(status)) {
863 return status;
864 }
865 talloc_free(scfg);
866 }
867 talloc_free(snames);
868
869 r->out.ctr.ctr2 = ctr2;
870 r->out.totalentries = r->out.ctr.ctr2->count;
871 return WERR_OK;
872 }
873 case 501:
874 {
875 int i;
876 struct srvsvc_NetShareCtr501 *ctr501;
877
878 SRVSVC_CHECK_ADMIN_ACCESS;
879
880 ctr501 = talloc(mem_ctx, struct srvsvc_NetShareCtr501);
881 W_ERROR_HAVE_NO_MEMORY(ctr501);
882
883 ctr501->count = numshares;
884 ctr501->array = NULL;
885
886 if (ctr501->count == 0) {
887 r->out.ctr.ctr501 = ctr501;
888 return WERR_OK;
889 }
890
891 ctr501->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo501, ctr501->count);
892 W_ERROR_HAVE_NO_MEMORY(ctr501->array);
893
894 for (i=0; i < ctr501->count; i++) {
895 WERROR status;
896 union srvsvc_NetShareInfo info;
897
898 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
899 if (!NT_STATUS_IS_OK(nterr)) {
900 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
901 return WERR_GENERAL_FAILURE;
902 }
903 info.info501 = &ctr501->array[i];
904 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
905 if (!W_ERROR_IS_OK(status)) {
906 return status;
907 }
908 talloc_free(scfg);
909 }
910 talloc_free(snames);
911
912 r->out.ctr.ctr501 = ctr501;
913 r->out.totalentries = r->out.ctr.ctr501->count;
914 return WERR_OK;
915 }
916 case 502:
917 {
918 int i;
919 struct srvsvc_NetShareCtr502 *ctr502;
920
921 SRVSVC_CHECK_ADMIN_ACCESS;
922
923 ctr502 = talloc(mem_ctx, struct srvsvc_NetShareCtr502);
924 W_ERROR_HAVE_NO_MEMORY(ctr502);
925
926 ctr502->count = numshares;
927 ctr502->array = NULL;
928
929 if (ctr502->count == 0) {
930 r->out.ctr.ctr502 = ctr502;
931 return WERR_OK;
932 }
933
934 ctr502->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo502, ctr502->count);
935 W_ERROR_HAVE_NO_MEMORY(ctr502->array);
936
937 for (i=0; i < ctr502->count; i++) {
938 WERROR status;
939 union srvsvc_NetShareInfo info;
940
941 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
942 if (!NT_STATUS_IS_OK(nterr)) {
943 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
944 return WERR_GENERAL_FAILURE;
945 }
946 info.info502 = &ctr502->array[i];
947 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
948 if (!W_ERROR_IS_OK(status)) {
949 return status;
950 }
951 talloc_free(scfg);
952 }
953 talloc_free(snames);
954
955 r->out.ctr.ctr502 = ctr502;
956 r->out.totalentries = r->out.ctr.ctr502->count;
957 return WERR_OK;
958 }
959 default:
960 return WERR_UNKNOWN_LEVEL;
961 }
962
963 return WERR_UNKNOWN_LEVEL;
964 }
965
966
967 /*
968 srvsvc_NetShareGetInfo
969 */
srvsvc_NetShareGetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareGetInfo * r)970 static WERROR srvsvc_NetShareGetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
971 struct srvsvc_NetShareGetInfo *r)
972 {
973 NTSTATUS nterr;
974 struct share_context *sctx = NULL;
975 struct share_config *scfg = NULL;
976
977 ZERO_STRUCT(r->out);
978
979 /* TODO: - access check
980 */
981
982 if (strcmp("", r->in.share_name) == 0) {
983 return WERR_INVALID_PARAM;
984 }
985
986 nterr = share_get_context(mem_ctx, &sctx);
987 if (!NT_STATUS_IS_OK(nterr)) {
988 return ntstatus_to_werror(nterr);
989 }
990
991 nterr = share_get_config(mem_ctx, sctx, r->in.share_name, &scfg);
992 if (!NT_STATUS_IS_OK(nterr)) {
993 return ntstatus_to_werror(nterr);
994 }
995
996 switch (r->in.level) {
997 case 0:
998 {
999 WERROR status;
1000 union srvsvc_NetShareInfo info;
1001
1002 info.info0 = talloc(mem_ctx, struct srvsvc_NetShareInfo0);
1003 W_ERROR_HAVE_NO_MEMORY(info.info0);
1004
1005 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1006 if (!W_ERROR_IS_OK(status)) {
1007 return status;
1008 }
1009
1010 r->out.info.info0 = info.info0;
1011 return WERR_OK;
1012 }
1013 case 1:
1014 {
1015 WERROR status;
1016 union srvsvc_NetShareInfo info;
1017
1018 info.info1 = talloc(mem_ctx, struct srvsvc_NetShareInfo1);
1019 W_ERROR_HAVE_NO_MEMORY(info.info1);
1020
1021 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1022 if (!W_ERROR_IS_OK(status)) {
1023 return status;
1024 }
1025
1026 r->out.info.info1 = info.info1;
1027 return WERR_OK;
1028 }
1029 case 2:
1030 {
1031 WERROR status;
1032 union srvsvc_NetShareInfo info;
1033
1034 SRVSVC_CHECK_ADMIN_ACCESS;
1035
1036 info.info2 = talloc(mem_ctx, struct srvsvc_NetShareInfo2);
1037 W_ERROR_HAVE_NO_MEMORY(info.info2);
1038
1039 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1040 if (!W_ERROR_IS_OK(status)) {
1041 return status;
1042 }
1043
1044 r->out.info.info2 = info.info2;
1045 return WERR_OK;
1046 }
1047 case 501:
1048 {
1049 WERROR status;
1050 union srvsvc_NetShareInfo info;
1051
1052 info.info501 = talloc(mem_ctx, struct srvsvc_NetShareInfo501);
1053 W_ERROR_HAVE_NO_MEMORY(info.info501);
1054
1055 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1056 if (!W_ERROR_IS_OK(status)) {
1057 return status;
1058 }
1059
1060 r->out.info.info501 = info.info501;
1061 return WERR_OK;
1062 }
1063 case 502:
1064 {
1065 WERROR status;
1066 union srvsvc_NetShareInfo info;
1067
1068 SRVSVC_CHECK_ADMIN_ACCESS;
1069
1070 info.info502 = talloc(mem_ctx, struct srvsvc_NetShareInfo502);
1071 W_ERROR_HAVE_NO_MEMORY(info.info502);
1072
1073 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1074 if (!W_ERROR_IS_OK(status)) {
1075 return status;
1076 }
1077
1078 r->out.info.info502 = info.info502;
1079 return WERR_OK;
1080 }
1081 case 1005:
1082 {
1083 WERROR status;
1084 union srvsvc_NetShareInfo info;
1085
1086 info.info1005 = talloc(mem_ctx, struct srvsvc_NetShareInfo1005);
1087 W_ERROR_HAVE_NO_MEMORY(info.info1005);
1088
1089 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1090 if (!W_ERROR_IS_OK(status)) {
1091 return status;
1092 }
1093
1094 r->out.info.info1005 = info.info1005;
1095 return WERR_OK;
1096 }
1097 default:
1098 return WERR_UNKNOWN_LEVEL;
1099 }
1100
1101 return WERR_UNKNOWN_LEVEL;
1102 }
1103
srvsvc_fill_share_info(struct share_info * info,int * count,const char * share_name,int level,const char * name,const char * path,const char * comment,const char * password,enum srvsvc_ShareType type,int32_t max_users,uint32_t csc_policy,struct security_descriptor * sd)1104 static WERROR srvsvc_fill_share_info(struct share_info *info, int *count,
1105 const char *share_name, int level,
1106 const char *name,
1107 const char *path,
1108 const char *comment,
1109 const char *password,
1110 enum srvsvc_ShareType type,
1111 int32_t max_users,
1112 uint32_t csc_policy,
1113 struct security_descriptor *sd)
1114 {
1115 int i = 0;
1116
1117 if (level == 501) {
1118 info[i].name = SHARE_CSC_POLICY;
1119 info[i].type = SHARE_INFO_INT;
1120 info[i].value = talloc(info, int);
1121 *((int *)info[i].value) = csc_policy;
1122 i++;
1123 }
1124
1125 switch(level) {
1126
1127 case 502:
1128 /* TODO: check if unknown is csc_policy */
1129
1130 /* TODO: security descriptor */
1131
1132 case 2:
1133 if (path && path[0]) {
1134 info[i].name = SHARE_PATH;
1135 info[i].type = SHARE_INFO_STRING;
1136
1137 /* Windows will send a path in a form of C:\example\path */
1138 if (path[1] == ':') {
1139 info[i].value = talloc_strdup(info, &path[2]);
1140 } else {
1141 /* very strange let's try to set as is */
1142 info[i].value = talloc_strdup(info, path);
1143 }
1144 W_ERROR_HAVE_NO_MEMORY(info[i].value);
1145 all_string_sub((char *)info[i].value, "\\", "/", 0);
1146
1147 i++;
1148 }
1149
1150 if (password && password[0]) {
1151 info[i].name = SHARE_PASSWORD;
1152 info[i].type = SHARE_INFO_STRING;
1153 info[i].value = talloc_strdup(info, password);
1154 W_ERROR_HAVE_NO_MEMORY(info[i].value);
1155
1156 i++;
1157 }
1158
1159 info[i].name = SHARE_MAX_CONNECTIONS;
1160 info[i].type = SHARE_INFO_INT;
1161 info[i].value = talloc(info, int);
1162 *((int *)info[i].value) = max_users;
1163 i++;
1164
1165 case 501:
1166 case 1:
1167 info[i].name = SHARE_TYPE;
1168 info[i].type = SHARE_INFO_STRING;
1169 switch (type) {
1170 case 0x00:
1171 info[i].value = talloc_strdup(info, "DISK");
1172 break;
1173 case 0x01:
1174 info[i].value = talloc_strdup(info, "PRINTER");
1175 break;
1176 case 0x03:
1177 info[i].value = talloc_strdup(info, "IPC");
1178 break;
1179 default:
1180 return WERR_INVALID_PARAM;
1181 }
1182 W_ERROR_HAVE_NO_MEMORY(info[i].value);
1183 i++;
1184
1185 case 1004:
1186 if (comment) {
1187 info[i].name = SHARE_COMMENT;
1188 info[i].type = SHARE_INFO_STRING;
1189 info[i].value = talloc_strdup(info, comment);
1190 W_ERROR_HAVE_NO_MEMORY(info[i].value);
1191
1192 i++;
1193 }
1194 case 0:
1195 if (name &&
1196 strcasecmp(share_name, name) != 0) {
1197 info[i].name = SHARE_NAME;
1198 info[i].type = SHARE_INFO_STRING;
1199 info[i].value = talloc_strdup(info, name);
1200 W_ERROR_HAVE_NO_MEMORY(info[i].value);
1201 i++;
1202 }
1203
1204 break;
1205
1206 default:
1207 return WERR_UNKNOWN_LEVEL;
1208 }
1209
1210 *count = i;
1211
1212 return WERR_OK;
1213 }
1214
1215 /*
1216 srvsvc_NetShareSetInfo
1217 */
srvsvc_NetShareSetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareSetInfo * r)1218 static WERROR srvsvc_NetShareSetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1219 struct srvsvc_NetShareSetInfo *r)
1220 {
1221 NTSTATUS nterr;
1222 WERROR status;
1223 struct share_context *sctx = NULL;
1224 struct share_info *info;
1225 int count;
1226
1227 /* TODO: - access check
1228 */
1229
1230 /* there are no more than 10 options in all struct srvsvc_NetShareInfoXXX */
1231 info = talloc_array(mem_ctx, struct share_info, 10);
1232 W_ERROR_HAVE_NO_MEMORY(info);
1233
1234 ZERO_STRUCT(r->out);
1235
1236 if (strcmp("", r->in.share_name) == 0) {
1237 return WERR_INVALID_PARAM;
1238 }
1239
1240 nterr = share_get_context(mem_ctx, &sctx);
1241 if (!NT_STATUS_IS_OK(nterr)) {
1242 return ntstatus_to_werror(nterr);
1243 }
1244
1245 switch (r->in.level) {
1246 case 0:
1247 {
1248 status = srvsvc_fill_share_info(info, &count,
1249 r->in.share_name, r->in.level,
1250 r->in.info.info0->name,
1251 NULL,
1252 NULL,
1253 NULL,
1254 0,
1255 0,
1256 0,
1257 NULL);
1258 if (W_ERROR_EQUAL(status, WERR_OK)) {
1259 return status;
1260 }
1261 break;
1262 }
1263 case 1:
1264 {
1265 status = srvsvc_fill_share_info(info, &count,
1266 r->in.share_name, r->in.level,
1267 r->in.info.info1->name,
1268 NULL,
1269 r->in.info.info1->comment,
1270 NULL,
1271 r->in.info.info1->type,
1272 0,
1273 0,
1274 NULL);
1275 if (W_ERROR_EQUAL(status, WERR_OK)) {
1276 return status;
1277 }
1278 break;
1279 }
1280 case 2:
1281 {
1282 status = srvsvc_fill_share_info(info, &count,
1283 r->in.share_name, r->in.level,
1284 r->in.info.info2->name,
1285 r->in.info.info2->path,
1286 r->in.info.info2->comment,
1287 r->in.info.info2->password,
1288 r->in.info.info2->type,
1289 r->in.info.info2->max_users,
1290 0,
1291 NULL);
1292 if (W_ERROR_EQUAL(status, WERR_OK)) {
1293 return status;
1294 }
1295 break;
1296 }
1297 case 501:
1298 {
1299 status = srvsvc_fill_share_info(info, &count,
1300 r->in.share_name, r->in.level,
1301 r->in.info.info501->name,
1302 NULL,
1303 r->in.info.info501->comment,
1304 NULL,
1305 r->in.info.info501->type,
1306 0,
1307 r->in.info.info501->csc_policy,
1308 NULL);
1309 if (W_ERROR_EQUAL(status, WERR_OK)) {
1310 return status;
1311 }
1312 break;
1313 }
1314 case 502:
1315 {
1316 status = srvsvc_fill_share_info(info, &count,
1317 r->in.share_name, r->in.level,
1318 r->in.info.info502->name,
1319 r->in.info.info502->path,
1320 r->in.info.info502->comment,
1321 r->in.info.info502->password,
1322 r->in.info.info502->type,
1323 r->in.info.info502->max_users,
1324 0,
1325 r->in.info.info502->sd);
1326 if (W_ERROR_EQUAL(status, WERR_OK)) {
1327 return status;
1328 }
1329 break;
1330 }
1331 case 1004:
1332 {
1333 status = srvsvc_fill_share_info(info, &count,
1334 r->in.share_name, r->in.level,
1335 NULL,
1336 NULL,
1337 r->in.info.info1004->comment,
1338 NULL,
1339 0,
1340 0,
1341 0,
1342 NULL);
1343 if (W_ERROR_EQUAL(status, WERR_OK)) {
1344 return status;
1345 }
1346 break;
1347 }
1348 case 1005:
1349 {
1350 /* r->in.info.dfs_flags; */
1351
1352 if (r->in.parm_error) {
1353 r->out.parm_error = r->in.parm_error;
1354 }
1355
1356 return WERR_OK;
1357 }
1358 default:
1359 return WERR_UNKNOWN_LEVEL;
1360 }
1361
1362 nterr = share_set(sctx, r->in.share_name, info, count);
1363 if (!NT_STATUS_IS_OK(nterr)) {
1364 return ntstatus_to_werror(nterr);
1365 }
1366
1367 if (r->in.parm_error) {
1368 r->out.parm_error = r->in.parm_error;
1369 }
1370
1371 return WERR_OK;
1372 }
1373
1374
1375 /*
1376 srvsvc_NetShareDelSticky
1377 */
srvsvc_NetShareDelSticky(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareDelSticky * r)1378 static WERROR srvsvc_NetShareDelSticky(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1379 struct srvsvc_NetShareDelSticky *r)
1380 {
1381 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1382 }
1383
1384
1385 /*
1386 srvsvc_NetShareCheck
1387 */
srvsvc_NetShareCheck(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareCheck * r)1388 static WERROR srvsvc_NetShareCheck(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1389 struct srvsvc_NetShareCheck *r)
1390 {
1391 NTSTATUS nterr;
1392 struct share_context *sctx = NULL;
1393 struct share_config *scfg = NULL;
1394 char *device;
1395 const char **names;
1396 int count, i;
1397
1398 ZERO_STRUCT(r->out);
1399
1400 /* TODO: - access check
1401 */
1402
1403 if (strcmp("", r->in.device_name) == 0) {
1404 r->out.type = STYPE_IPC;
1405 return WERR_OK;
1406 }
1407
1408 /* copy the path skipping C:\ */
1409 if (strncasecmp(r->in.device_name, "C:", 2) == 0) {
1410 device = talloc_strdup(mem_ctx, &r->in.device_name[2]);
1411 } else {
1412 /* no chance we have a share that doesn't start with C:\ */
1413 return WERR_DEVICE_NOT_SHARED;
1414 }
1415 all_string_sub(device, "\\", "/", 0);
1416
1417 nterr = share_get_context(mem_ctx, &sctx);
1418 if (!NT_STATUS_IS_OK(nterr)) {
1419 return ntstatus_to_werror(nterr);
1420 }
1421
1422 nterr = share_list_all(mem_ctx, sctx, &count, &names);
1423 if (!NT_STATUS_IS_OK(nterr)) {
1424 return ntstatus_to_werror(nterr);
1425 }
1426
1427 for (i = 0; i < count; i++) {
1428 const char *path;
1429 const char *type;
1430
1431 nterr = share_get_config(mem_ctx, sctx, names[i], &scfg);
1432 if (!NT_STATUS_IS_OK(nterr)) {
1433 return ntstatus_to_werror(nterr);
1434 }
1435 path = share_string_option(scfg, SHARE_PATH, NULL);
1436 if (!path) continue;
1437
1438 if (strcmp(device, path) == 0) {
1439 type = share_string_option(scfg, SHARE_TYPE, NULL);
1440 if (!type) continue;
1441
1442 if (strcmp(type, "DISK") == 0) {
1443 r->out.type = STYPE_DISKTREE;
1444 return WERR_OK;
1445 }
1446
1447 if (strcmp(type, "IPC") == 0) {
1448 r->out.type = STYPE_IPC;
1449 return WERR_OK;
1450 }
1451
1452 if (strcmp(type, "PRINTER") == 0) {
1453 r->out.type = STYPE_PRINTQ;
1454 return WERR_OK;
1455 }
1456 }
1457 }
1458
1459 return WERR_DEVICE_NOT_SHARED;
1460 }
1461
1462
1463 /*
1464 srvsvc_NetSrvGetInfo
1465 */
srvsvc_NetSrvGetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSrvGetInfo * r)1466 static WERROR srvsvc_NetSrvGetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1467 struct srvsvc_NetSrvGetInfo *r)
1468 {
1469 struct dcesrv_context *dce_ctx = dce_call->conn->dce_ctx;
1470
1471 ZERO_STRUCT(r->out);
1472
1473 switch (r->in.level) {
1474 case 100:
1475 {
1476 struct srvsvc_NetSrvInfo100 *info100;
1477
1478 info100 = talloc(mem_ctx, struct srvsvc_NetSrvInfo100);
1479 W_ERROR_HAVE_NO_MEMORY(info100);
1480
1481 info100->platform_id = dcesrv_common_get_platform_id(mem_ctx, dce_ctx);
1482 info100->server_name = dcesrv_common_get_server_name(mem_ctx, dce_ctx, r->in.server_unc);
1483 W_ERROR_HAVE_NO_MEMORY(info100->server_name);
1484
1485 r->out.info.info100 = info100;
1486 return WERR_OK;
1487 }
1488 case 101:
1489 {
1490 struct srvsvc_NetSrvInfo101 *info101;
1491
1492 info101 = talloc(mem_ctx, struct srvsvc_NetSrvInfo101);
1493 W_ERROR_HAVE_NO_MEMORY(info101);
1494
1495 info101->platform_id = dcesrv_common_get_platform_id(mem_ctx, dce_ctx);
1496 info101->server_name = dcesrv_common_get_server_name(mem_ctx, dce_ctx, r->in.server_unc);
1497 W_ERROR_HAVE_NO_MEMORY(info101->server_name);
1498
1499 info101->version_major = dcesrv_common_get_version_major(mem_ctx, dce_ctx);
1500 info101->version_minor = dcesrv_common_get_version_minor(mem_ctx, dce_ctx);
1501 info101->server_type = dcesrv_common_get_server_type(mem_ctx, dce_ctx);
1502 info101->comment = talloc_strdup(mem_ctx, lp_serverstring());
1503 W_ERROR_HAVE_NO_MEMORY(info101->comment);
1504
1505 r->out.info.info101 = info101;
1506 return WERR_OK;
1507 }
1508 case 102:
1509 {
1510 struct srvsvc_NetSrvInfo102 *info102;
1511
1512 info102 = talloc(mem_ctx, struct srvsvc_NetSrvInfo102);
1513 W_ERROR_HAVE_NO_MEMORY(info102);
1514
1515 info102->platform_id = dcesrv_common_get_platform_id(mem_ctx, dce_ctx);
1516 info102->server_name = dcesrv_common_get_server_name(mem_ctx, dce_ctx, r->in.server_unc);
1517 W_ERROR_HAVE_NO_MEMORY(info102->server_name);
1518
1519 info102->version_major = dcesrv_common_get_version_major(mem_ctx, dce_ctx);
1520 info102->version_minor = dcesrv_common_get_version_minor(mem_ctx, dce_ctx);
1521 info102->server_type = dcesrv_common_get_server_type(mem_ctx, dce_ctx);
1522 info102->comment = talloc_strdup(mem_ctx, lp_serverstring());
1523 W_ERROR_HAVE_NO_MEMORY(info102->comment);
1524
1525 info102->users = dcesrv_common_get_users(mem_ctx, dce_ctx);
1526 info102->disc = dcesrv_common_get_disc(mem_ctx, dce_ctx);
1527 info102->hidden = dcesrv_common_get_hidden(mem_ctx, dce_ctx);
1528 info102->announce = dcesrv_common_get_announce(mem_ctx, dce_ctx);
1529 info102->anndelta = dcesrv_common_get_anndelta(mem_ctx, dce_ctx);
1530 info102->licenses = dcesrv_common_get_licenses(mem_ctx, dce_ctx);
1531 info102->userpath = dcesrv_common_get_userpath(mem_ctx, dce_ctx);
1532 W_ERROR_HAVE_NO_MEMORY(info102->userpath);
1533
1534 r->out.info.info102 = info102;
1535 return WERR_OK;
1536 }
1537 default:
1538 return WERR_UNKNOWN_LEVEL;
1539 }
1540
1541 return WERR_UNKNOWN_LEVEL;
1542 }
1543
1544
1545 /*
1546 srvsvc_NetSrvSetInfo
1547 */
srvsvc_NetSrvSetInfo(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSrvSetInfo * r)1548 static WERROR srvsvc_NetSrvSetInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1549 struct srvsvc_NetSrvSetInfo *r)
1550 {
1551 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1552 }
1553
1554
1555 /*
1556 srvsvc_NetDiskEnum
1557 */
srvsvc_NetDiskEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetDiskEnum * r)1558 static WERROR srvsvc_NetDiskEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1559 struct srvsvc_NetDiskEnum *r)
1560 {
1561 r->out.info.disks = NULL;
1562 r->out.info.count = 0;
1563 r->out.totalentries = 0;
1564 r->out.resume_handle = NULL;
1565
1566 switch (r->in.level) {
1567 case 0:
1568 {
1569 /* we can safely hardcode the reply and report we have only one disk (C:) */
1570 /* for some reason Windows wants 2 entries with the second being empty */
1571 r->out.info.disks = talloc_array(mem_ctx, struct srvsvc_NetDiskInfo0, 2);
1572 W_ERROR_HAVE_NO_MEMORY(r->out.info.disks);
1573 r->out.info.count = 2;
1574
1575 r->out.info.disks[0].disk = talloc_strdup(mem_ctx, "C:");
1576 W_ERROR_HAVE_NO_MEMORY(r->out.info.disks[0].disk);
1577
1578 r->out.info.disks[1].disk = talloc_strdup(mem_ctx, "");
1579 W_ERROR_HAVE_NO_MEMORY(r->out.info.disks[1].disk);
1580
1581 r->out.totalentries = 1;
1582 r->out.resume_handle = r->in.resume_handle;
1583
1584 return WERR_OK;
1585 }
1586 default:
1587 return WERR_UNKNOWN_LEVEL;
1588 }
1589
1590 return WERR_UNKNOWN_LEVEL;
1591 }
1592
1593
1594 /*
1595 srvsvc_NetServerStatisticsGet
1596 */
srvsvc_NetServerStatisticsGet(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetServerStatisticsGet * r)1597 static WERROR srvsvc_NetServerStatisticsGet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1598 struct srvsvc_NetServerStatisticsGet *r)
1599 {
1600 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1601 }
1602
1603
1604 /*
1605 srvsvc_NetTransportAdd
1606 */
srvsvc_NetTransportAdd(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetTransportAdd * r)1607 static WERROR srvsvc_NetTransportAdd(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1608 struct srvsvc_NetTransportAdd *r)
1609 {
1610 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1611 }
1612
1613
1614 /*
1615 srvsvc_NetTransportEnum
1616 */
srvsvc_NetTransportEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetTransportEnum * r)1617 static WERROR srvsvc_NetTransportEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1618 struct srvsvc_NetTransportEnum *r)
1619 {
1620 r->out.level = r->in.level;
1621 r->out.totalentries = 0;
1622 r->out.resume_handle = NULL;
1623
1624 switch (r->in.level) {
1625 case 0:
1626 {
1627 r->out.transports.ctr0 = talloc(mem_ctx, struct srvsvc_NetTransportCtr0);
1628 W_ERROR_HAVE_NO_MEMORY(r->out.transports.ctr0);
1629
1630 r->out.transports.ctr0->count = 0;
1631 r->out.transports.ctr0->array = NULL;
1632
1633 return WERR_NOT_SUPPORTED;
1634 }
1635 case 1:
1636 {
1637 r->out.transports.ctr1 = talloc(mem_ctx, struct srvsvc_NetTransportCtr1);
1638 W_ERROR_HAVE_NO_MEMORY(r->out.transports.ctr1);
1639
1640 r->out.transports.ctr1->count = 0;
1641 r->out.transports.ctr1->array = NULL;
1642
1643 return WERR_NOT_SUPPORTED;
1644 }
1645 case 2:
1646 {
1647 r->out.transports.ctr2 = talloc(mem_ctx, struct srvsvc_NetTransportCtr2);
1648 W_ERROR_HAVE_NO_MEMORY(r->out.transports.ctr2);
1649
1650 r->out.transports.ctr2->count = 0;
1651 r->out.transports.ctr2->array = NULL;
1652
1653 return WERR_NOT_SUPPORTED;
1654 }
1655 case 3:
1656 {
1657 r->out.transports.ctr3 = talloc(mem_ctx, struct srvsvc_NetTransportCtr3);
1658 W_ERROR_HAVE_NO_MEMORY(r->out.transports.ctr3);
1659
1660 r->out.transports.ctr3->count = 0;
1661 r->out.transports.ctr3->array = NULL;
1662
1663 return WERR_NOT_SUPPORTED;
1664 }
1665 default:
1666 return WERR_UNKNOWN_LEVEL;
1667 }
1668
1669 return WERR_UNKNOWN_LEVEL;
1670 }
1671
1672 /*
1673 srvsvc_NetTransportDel
1674 */
srvsvc_NetTransportDel(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetTransportDel * r)1675 static WERROR srvsvc_NetTransportDel(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1676 struct srvsvc_NetTransportDel *r)
1677 {
1678 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1679 }
1680
1681
1682 /*
1683 srvsvc_NetRemoteTOD
1684 */
srvsvc_NetRemoteTOD(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetRemoteTOD * r)1685 static WERROR srvsvc_NetRemoteTOD(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1686 struct srvsvc_NetRemoteTOD *r)
1687 {
1688 struct timeval tval;
1689 time_t t;
1690 struct tm tm;
1691
1692 r->out.info = talloc(mem_ctx, struct srvsvc_NetRemoteTODInfo);
1693 W_ERROR_HAVE_NO_MEMORY(r->out.info);
1694
1695 GetTimeOfDay(&tval);
1696 t = tval.tv_sec;
1697
1698 gmtime_r(&t, &tm);
1699
1700 r->out.info->elapsed = t;
1701 /* TODO: fake the uptime: just return the milliseconds till 0:00:00 today */
1702 r->out.info->msecs = (tm.tm_hour*60*60*1000)
1703 + (tm.tm_min*60*1000)
1704 + (tm.tm_sec*1000)
1705 + (tval.tv_usec/1000);
1706 r->out.info->hours = tm.tm_hour;
1707 r->out.info->mins = tm.tm_min;
1708 r->out.info->secs = tm.tm_sec;
1709 r->out.info->hunds = tval.tv_usec/10000;
1710 r->out.info->timezone = get_time_zone(t)/60;
1711 r->out.info->tinterval = 310; /* just return the same as windows */
1712 r->out.info->day = tm.tm_mday;
1713 r->out.info->month = tm.tm_mon + 1;
1714 r->out.info->year = tm.tm_year + 1900;
1715 r->out.info->weekday = tm.tm_wday;
1716
1717 return WERR_OK;
1718 }
1719
1720 /*
1721 srvsvc_NetPathType
1722 */
srvsvc_NetPathType(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetPathType * r)1723 static WERROR srvsvc_NetPathType(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1724 struct srvsvc_NetPathType *r)
1725 {
1726 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1727 }
1728
1729
1730 /*
1731 srvsvc_NetPathCanonicalize
1732 */
srvsvc_NetPathCanonicalize(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetPathCanonicalize * r)1733 static WERROR srvsvc_NetPathCanonicalize(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1734 struct srvsvc_NetPathCanonicalize *r)
1735 {
1736 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1737 }
1738
1739
1740 /*
1741 srvsvc_NetPathCompare
1742 */
srvsvc_NetPathCompare(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetPathCompare * r)1743 static WERROR srvsvc_NetPathCompare(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1744 struct srvsvc_NetPathCompare *r)
1745 {
1746 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1747 }
1748
1749
1750 /*
1751 srvsvc_NetNameValidate
1752 */
srvsvc_NetNameValidate(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetNameValidate * r)1753 static WERROR srvsvc_NetNameValidate(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1754 struct srvsvc_NetNameValidate *r)
1755 {
1756 int len;
1757
1758 if ((r->in.flags != 0x0) && (r->in.flags != 0x80000000)) {
1759 return WERR_INVALID_NAME;
1760 }
1761
1762 switch (r->in.name_type) {
1763 case 1:
1764 case 2:
1765 case 3:
1766 case 4:
1767 case 5:
1768 case 6:
1769 case 7:
1770 case 8:
1771 return WERR_NOT_SUPPORTED;
1772
1773 case 9: /* validate share name */
1774
1775 len = strlen_m(r->in.name);
1776 if ((r->in.flags == 0x0) && (len > 81)) {
1777 return WERR_INVALID_NAME;
1778 }
1779 if ((r->in.flags == 0x80000000) && (len > 13)) {
1780 return WERR_INVALID_NAME;
1781 }
1782 if (! dcesrv_common_validate_share_name(mem_ctx, r->in.name)) {
1783 return WERR_INVALID_NAME;
1784 }
1785 return WERR_OK;
1786
1787 case 10:
1788 case 11:
1789 case 12:
1790 case 13:
1791 return WERR_NOT_SUPPORTED;
1792 default:
1793 return WERR_INVALID_PARAM;
1794 }
1795
1796 return WERR_INVALID_PARAM;
1797 }
1798
1799
1800 /*
1801 srvsvc_NetPRNameCompare
1802 */
srvsvc_NetPRNameCompare(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetPRNameCompare * r)1803 static WERROR srvsvc_NetPRNameCompare(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1804 struct srvsvc_NetPRNameCompare *r)
1805 {
1806 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1807 }
1808
1809
1810 /*
1811 srvsvc_NetShareEnum
1812 */
srvsvc_NetShareEnum(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareEnum * r)1813 static WERROR srvsvc_NetShareEnum(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1814 struct srvsvc_NetShareEnum *r)
1815 {
1816 NTSTATUS nterr;
1817 int numshares = 0;
1818 const char **snames;
1819 struct share_context *sctx;
1820 struct share_config *scfg;
1821 struct dcesrv_context *dce_ctx = dce_call->conn->dce_ctx;
1822
1823 r->out.level = r->in.level;
1824 ZERO_STRUCT(r->out.ctr);
1825 r->out.totalentries = 0;
1826 r->out.resume_handle = NULL;
1827
1828 /* TODO: - paging of results
1829 */
1830
1831 nterr = share_get_context(mem_ctx, &sctx);
1832 if (!NT_STATUS_IS_OK(nterr)) {
1833 return ntstatus_to_werror(nterr);
1834 }
1835
1836 nterr = share_list_all(mem_ctx, sctx, &numshares, &snames);
1837 if (!NT_STATUS_IS_OK(nterr)) {
1838 return ntstatus_to_werror(nterr);
1839 }
1840
1841 switch (r->in.level) {
1842 case 0:
1843 {
1844 int i, y = 0;
1845 int count;
1846 struct srvsvc_NetShareCtr0 *ctr0;
1847
1848 ctr0 = talloc(mem_ctx, struct srvsvc_NetShareCtr0);
1849 W_ERROR_HAVE_NO_MEMORY(ctr0);
1850
1851 count = numshares;
1852 ctr0->count = count;
1853 ctr0->array = NULL;
1854
1855 if (ctr0->count == 0) {
1856 r->out.ctr.ctr0 = ctr0;
1857 return WERR_OK;
1858 }
1859
1860 ctr0->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo0, count);
1861 W_ERROR_HAVE_NO_MEMORY(ctr0->array);
1862
1863 for (i=0; i < count; i++) {
1864 WERROR status;
1865 union srvsvc_NetShareInfo info;
1866 enum srvsvc_ShareType type;
1867
1868 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
1869 if (!NT_STATUS_IS_OK(nterr)) {
1870 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
1871 return WERR_GENERAL_FAILURE;
1872 }
1873
1874 type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
1875 if (type & STYPE_HIDDEN) {
1876 ctr0->count--;
1877 talloc_free(scfg);
1878 continue;
1879 }
1880
1881 info.info0 = &ctr0->array[y];
1882 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1883 W_ERROR_NOT_OK_RETURN(status);
1884 talloc_free(scfg);
1885 y++;
1886 }
1887 talloc_free(snames);
1888
1889 r->out.ctr.ctr0 = ctr0;
1890 r->out.totalentries = r->out.ctr.ctr0->count;
1891 return WERR_OK;
1892 }
1893 case 1:
1894 {
1895 int i, y = 0;
1896 int count;
1897 struct srvsvc_NetShareCtr1 *ctr1;
1898
1899 ctr1 = talloc(mem_ctx, struct srvsvc_NetShareCtr1);
1900 W_ERROR_HAVE_NO_MEMORY(ctr1);
1901
1902 count = numshares;
1903 ctr1->count = count;
1904 ctr1->array = NULL;
1905
1906 if (ctr1->count == 0) {
1907 r->out.ctr.ctr1 = ctr1;
1908 return WERR_OK;
1909 }
1910
1911 ctr1->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo1, count);
1912 W_ERROR_HAVE_NO_MEMORY(ctr1->array);
1913
1914 for (i=0; i < count; i++) {
1915 WERROR status;
1916 union srvsvc_NetShareInfo info;
1917 enum srvsvc_ShareType type;
1918
1919 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
1920 if (!NT_STATUS_IS_OK(nterr)) {
1921 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
1922 return WERR_GENERAL_FAILURE;
1923 }
1924
1925 type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
1926 if (type & STYPE_HIDDEN) {
1927 ctr1->count--;
1928 talloc_free(scfg);
1929 continue;
1930 }
1931
1932 info.info1 = &ctr1->array[y];
1933 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1934 W_ERROR_NOT_OK_RETURN(status);
1935 talloc_free(scfg);
1936 y++;
1937 }
1938 talloc_free(snames);
1939
1940 r->out.ctr.ctr1 = ctr1;
1941 r->out.totalentries = r->out.ctr.ctr1->count;
1942 return WERR_OK;
1943 }
1944 case 2:
1945 {
1946 int i, y = 0;
1947 int count;
1948 struct srvsvc_NetShareCtr2 *ctr2;
1949
1950 SRVSVC_CHECK_ADMIN_ACCESS;
1951
1952 ctr2 = talloc(mem_ctx, struct srvsvc_NetShareCtr2);
1953 W_ERROR_HAVE_NO_MEMORY(ctr2);
1954
1955 count = numshares;
1956 ctr2->count = count;
1957 ctr2->array = NULL;
1958
1959 if (ctr2->count == 0) {
1960 r->out.ctr.ctr2 = ctr2;
1961 return WERR_OK;
1962 }
1963
1964 ctr2->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo2, count);
1965 W_ERROR_HAVE_NO_MEMORY(ctr2->array);
1966
1967 for (i=0; i < count; i++) {
1968 WERROR status;
1969 union srvsvc_NetShareInfo info;
1970 enum srvsvc_ShareType type;
1971
1972 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
1973 if (!NT_STATUS_IS_OK(nterr)) {
1974 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
1975 return WERR_GENERAL_FAILURE;
1976 }
1977
1978 type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
1979 if (type & STYPE_HIDDEN) {
1980 ctr2->count--;
1981 talloc_free(scfg);
1982 continue;
1983 }
1984
1985 info.info2 = &ctr2->array[y];
1986 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
1987 W_ERROR_NOT_OK_RETURN(status);
1988 talloc_free(scfg);
1989 y++;
1990 }
1991 talloc_free(snames);
1992
1993 r->out.ctr.ctr2 = ctr2;
1994 r->out.totalentries = r->out.ctr.ctr2->count;
1995 return WERR_OK;
1996 }
1997 case 502:
1998 {
1999 int i, y = 0;
2000 int count;
2001 struct srvsvc_NetShareCtr502 *ctr502;
2002
2003 SRVSVC_CHECK_ADMIN_ACCESS;
2004
2005 ctr502 = talloc(mem_ctx, struct srvsvc_NetShareCtr502);
2006 W_ERROR_HAVE_NO_MEMORY(ctr502);
2007
2008 count = numshares;
2009 ctr502->count = count;
2010 ctr502->array = NULL;
2011
2012 if (ctr502->count == 0) {
2013 r->out.ctr.ctr502 = ctr502;
2014 return WERR_OK;
2015 }
2016
2017 ctr502->array = talloc_array(mem_ctx, struct srvsvc_NetShareInfo502, count);
2018 W_ERROR_HAVE_NO_MEMORY(ctr502->array);
2019
2020 for (i=0; i < count; i++) {
2021 WERROR status;
2022 union srvsvc_NetShareInfo info;
2023 enum srvsvc_ShareType type;
2024
2025 nterr = share_get_config(mem_ctx, sctx, snames[i], &scfg);
2026 if (!NT_STATUS_IS_OK(nterr)) {
2027 DEBUG(1, ("ERROR: Service [%s] disappeared after enumeration", snames[i]));
2028 return WERR_GENERAL_FAILURE;
2029 }
2030
2031 type = dcesrv_common_get_share_type(mem_ctx, dce_ctx, scfg);
2032 if (type & STYPE_HIDDEN) {
2033 ctr502->count--;
2034 talloc_free(scfg);
2035 continue;
2036 }
2037
2038 info.info502 = &ctr502->array[y];
2039 status = srvsvc_fiel_ShareInfo(dce_call, mem_ctx, scfg, r->in.level, &info);
2040 W_ERROR_NOT_OK_RETURN(status);
2041 talloc_free(scfg);
2042 y++;
2043 }
2044 talloc_free(snames);
2045
2046 r->out.ctr.ctr502 = ctr502;
2047 r->out.totalentries = r->out.ctr.ctr502->count;
2048 return WERR_OK;
2049 }
2050 default:
2051 return WERR_UNKNOWN_LEVEL;
2052 }
2053
2054 return WERR_UNKNOWN_LEVEL;
2055 }
2056
2057
2058 /*
2059 srvsvc_NetShareDelStart
2060 */
srvsvc_NetShareDelStart(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareDelStart * r)2061 static WERROR srvsvc_NetShareDelStart(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2062 struct srvsvc_NetShareDelStart *r)
2063 {
2064 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2065 }
2066
2067
2068 /*
2069 srvsvc_NetShareDelCommit
2070 */
srvsvc_NetShareDelCommit(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareDelCommit * r)2071 static WERROR srvsvc_NetShareDelCommit(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2072 struct srvsvc_NetShareDelCommit *r)
2073 {
2074 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2075 }
2076
2077
2078 /*
2079 srvsvc_NetGetFileSecurity
2080 */
srvsvc_NetGetFileSecurity(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetGetFileSecurity * r)2081 static WERROR srvsvc_NetGetFileSecurity(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2082 struct srvsvc_NetGetFileSecurity *r)
2083 {
2084 struct sec_desc_buf *sd_buf;
2085 struct ntvfs_context *ntvfs_ctx = NULL;
2086 struct ntvfs_request *ntvfs_req;
2087 union smb_fileinfo *io;
2088 NTSTATUS nt_status;
2089
2090 nt_status = srvsvc_create_ntvfs_context(dce_call, mem_ctx, r->in.share, &ntvfs_ctx);
2091 if (!NT_STATUS_IS_OK(nt_status)) return ntstatus_to_werror(nt_status);
2092
2093 ntvfs_req = ntvfs_request_create(ntvfs_ctx, mem_ctx,
2094 dce_call->conn->auth_state.session_info,
2095 0,
2096 dce_call->time,
2097 NULL, NULL, 0);
2098 W_ERROR_HAVE_NO_MEMORY(ntvfs_req);
2099
2100 sd_buf = talloc(mem_ctx, struct sec_desc_buf);
2101 W_ERROR_HAVE_NO_MEMORY(sd_buf);
2102
2103 io = talloc(mem_ctx, union smb_fileinfo);
2104 W_ERROR_HAVE_NO_MEMORY(io);
2105
2106 io->query_secdesc.level = RAW_FILEINFO_SEC_DESC;
2107 io->query_secdesc.in.file.path = r->in.file;
2108 io->query_secdesc.in.secinfo_flags = r->in.securityinformation;
2109
2110 nt_status = ntvfs_qpathinfo(ntvfs_req, io);
2111 if (!NT_STATUS_IS_OK(nt_status)) return ntstatus_to_werror(nt_status);
2112
2113 sd_buf->sd = io->query_secdesc.out.sd;
2114
2115 r->out.sd_buf = sd_buf;
2116 return WERR_OK;
2117 }
2118
2119
2120 /*
2121 srvsvc_NetSetFileSecurity
2122 */
srvsvc_NetSetFileSecurity(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSetFileSecurity * r)2123 static WERROR srvsvc_NetSetFileSecurity(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2124 struct srvsvc_NetSetFileSecurity *r)
2125 {
2126 struct ntvfs_context *ntvfs_ctx;
2127 struct ntvfs_request *ntvfs_req;
2128 union smb_setfileinfo *io;
2129 NTSTATUS nt_status;
2130
2131 nt_status = srvsvc_create_ntvfs_context(dce_call, mem_ctx, r->in.share, &ntvfs_ctx);
2132 if (!NT_STATUS_IS_OK(nt_status)) return ntstatus_to_werror(nt_status);
2133
2134 ntvfs_req = ntvfs_request_create(ntvfs_ctx, mem_ctx,
2135 dce_call->conn->auth_state.session_info,
2136 0,
2137 dce_call->time,
2138 NULL, NULL, 0);
2139 W_ERROR_HAVE_NO_MEMORY(ntvfs_req);
2140
2141 io = talloc(mem_ctx, union smb_setfileinfo);
2142 W_ERROR_HAVE_NO_MEMORY(io);
2143
2144 io->set_secdesc.level = RAW_FILEINFO_SEC_DESC;
2145 io->set_secdesc.in.file.path = r->in.file;
2146 io->set_secdesc.in.secinfo_flags = r->in.securityinformation;
2147 io->set_secdesc.in.sd = r->in.sd_buf.sd;
2148
2149 nt_status = ntvfs_setpathinfo(ntvfs_req, io);
2150 if (!NT_STATUS_IS_OK(nt_status)) return ntstatus_to_werror(nt_status);
2151
2152 return WERR_OK;
2153 }
2154
2155
2156 /*
2157 srvsvc_NetServerTransportAddEx
2158 */
srvsvc_NetServerTransportAddEx(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetServerTransportAddEx * r)2159 static WERROR srvsvc_NetServerTransportAddEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2160 struct srvsvc_NetServerTransportAddEx *r)
2161 {
2162 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2163 }
2164
2165
2166 /*
2167 srvsvc_NetServerSetServiceBitsEx
2168 */
srvsvc_NetServerSetServiceBitsEx(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetServerSetServiceBitsEx * r)2169 static WERROR srvsvc_NetServerSetServiceBitsEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2170 struct srvsvc_NetServerSetServiceBitsEx *r)
2171 {
2172 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2173 }
2174
2175
2176 /*
2177 srvsvc_NETRDFSGETVERSION
2178 */
srvsvc_NETRDFSGETVERSION(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSGETVERSION * r)2179 static WERROR srvsvc_NETRDFSGETVERSION(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2180 struct srvsvc_NETRDFSGETVERSION *r)
2181 {
2182 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2183 }
2184
2185
2186 /*
2187 srvsvc_NETRDFSCREATELOCALPARTITION
2188 */
srvsvc_NETRDFSCREATELOCALPARTITION(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSCREATELOCALPARTITION * r)2189 static WERROR srvsvc_NETRDFSCREATELOCALPARTITION(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2190 struct srvsvc_NETRDFSCREATELOCALPARTITION *r)
2191 {
2192 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2193 }
2194
2195
2196 /*
2197 srvsvc_NETRDFSDELETELOCALPARTITION
2198 */
srvsvc_NETRDFSDELETELOCALPARTITION(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSDELETELOCALPARTITION * r)2199 static WERROR srvsvc_NETRDFSDELETELOCALPARTITION(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2200 struct srvsvc_NETRDFSDELETELOCALPARTITION *r)
2201 {
2202 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2203 }
2204
2205
2206 /*
2207 srvsvc_NETRDFSSETLOCALVOLUMESTATE
2208 */
srvsvc_NETRDFSSETLOCALVOLUMESTATE(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSSETLOCALVOLUMESTATE * r)2209 static WERROR srvsvc_NETRDFSSETLOCALVOLUMESTATE(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2210 struct srvsvc_NETRDFSSETLOCALVOLUMESTATE *r)
2211 {
2212 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2213 }
2214
2215
2216 /*
2217 srvsvc_NETRDFSSETSERVERINFO
2218 */
srvsvc_NETRDFSSETSERVERINFO(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSSETSERVERINFO * r)2219 static WERROR srvsvc_NETRDFSSETSERVERINFO(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2220 struct srvsvc_NETRDFSSETSERVERINFO *r)
2221 {
2222 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2223 }
2224
2225
2226 /*
2227 srvsvc_NETRDFSCREATEEXITPOINT
2228 */
srvsvc_NETRDFSCREATEEXITPOINT(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSCREATEEXITPOINT * r)2229 static WERROR srvsvc_NETRDFSCREATEEXITPOINT(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2230 struct srvsvc_NETRDFSCREATEEXITPOINT *r)
2231 {
2232 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2233 }
2234
2235
2236 /*
2237 srvsvc_NETRDFSDELETEEXITPOINT
2238 */
srvsvc_NETRDFSDELETEEXITPOINT(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSDELETEEXITPOINT * r)2239 static WERROR srvsvc_NETRDFSDELETEEXITPOINT(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2240 struct srvsvc_NETRDFSDELETEEXITPOINT *r)
2241 {
2242 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2243 }
2244
2245
2246 /*
2247 srvsvc_NETRDFSMODIFYPREFIX
2248 */
srvsvc_NETRDFSMODIFYPREFIX(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSMODIFYPREFIX * r)2249 static WERROR srvsvc_NETRDFSMODIFYPREFIX(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2250 struct srvsvc_NETRDFSMODIFYPREFIX *r)
2251 {
2252 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2253 }
2254
2255
2256 /*
2257 srvsvc_NETRDFSFIXLOCALVOLUME
2258 */
srvsvc_NETRDFSFIXLOCALVOLUME(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSFIXLOCALVOLUME * r)2259 static WERROR srvsvc_NETRDFSFIXLOCALVOLUME(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2260 struct srvsvc_NETRDFSFIXLOCALVOLUME *r)
2261 {
2262 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2263 }
2264
2265
2266 /*
2267 srvsvc_NETRDFSMANAGERREPORTSITEINFO
2268 */
srvsvc_NETRDFSMANAGERREPORTSITEINFO(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRDFSMANAGERREPORTSITEINFO * r)2269 static WERROR srvsvc_NETRDFSMANAGERREPORTSITEINFO(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2270 struct srvsvc_NETRDFSMANAGERREPORTSITEINFO *r)
2271 {
2272 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2273 }
2274
2275
2276 /*
2277 srvsvc_NETRSERVERTRANSPORTDELEX
2278 */
srvsvc_NETRSERVERTRANSPORTDELEX(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRSERVERTRANSPORTDELEX * r)2279 static WERROR srvsvc_NETRSERVERTRANSPORTDELEX(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2280 struct srvsvc_NETRSERVERTRANSPORTDELEX *r)
2281 {
2282 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2283 }
2284
2285 /*
2286 srvsvc_NetShareDel
2287 */
srvsvc_NetShareDel(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetShareDel * r)2288 static WERROR srvsvc_NetShareDel(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2289 struct srvsvc_NetShareDel *r)
2290 {
2291 NTSTATUS nterr;
2292 struct share_context *sctx;
2293
2294 nterr = share_get_context(mem_ctx, &sctx);
2295 if (!NT_STATUS_IS_OK(nterr)) {
2296 return ntstatus_to_werror(nterr);
2297 }
2298
2299 nterr = share_remove(sctx, r->in.share_name);
2300 if (!NT_STATUS_IS_OK(nterr)) {
2301 return ntstatus_to_werror(nterr);
2302 }
2303
2304 return WERR_OK;
2305 }
2306
2307 /*
2308 srvsvc_NetSetServiceBits
2309 */
srvsvc_NetSetServiceBits(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NetSetServiceBits * r)2310 static WERROR srvsvc_NetSetServiceBits(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2311 struct srvsvc_NetSetServiceBits *r)
2312 {
2313 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2314 }
2315
2316 /*
2317 srvsvc_NETRPRNAMECANONICALIZE
2318 */
srvsvc_NETRPRNAMECANONICALIZE(struct dcesrv_call_state * dce_call,TALLOC_CTX * mem_ctx,struct srvsvc_NETRPRNAMECANONICALIZE * r)2319 static WERROR srvsvc_NETRPRNAMECANONICALIZE(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
2320 struct srvsvc_NETRPRNAMECANONICALIZE *r)
2321 {
2322 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
2323 }
2324
2325 /* include the generated boilerplate */
2326 #include "librpc/gen_ndr/ndr_srvsvc_s.c"
2327