s3: piddir creation fix part 2.
[ira/wip.git] / source4 / rpc_server / spoolss / dcesrv_spoolss.c
1 /* 
2    Unix SMB/CIFS implementation.
3
4    endpoint server for the spoolss pipe
5
6    Copyright (C) Tim Potter 2004
7    Copyright (C) Stefan Metzmacher 2005
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 #include "includes.h"
24 #include "rpc_server/dcerpc_server.h"
25 #include "librpc/gen_ndr/ndr_spoolss.h"
26 #include "ntptr/ntptr.h"
27 #include "lib/tsocket/tsocket.h"
28 #include "librpc/gen_ndr/ndr_spoolss_c.h"
29 #include "auth/credentials/credentials.h"
30 #include "param/param.h"
31
32 enum spoolss_handle {
33         SPOOLSS_NOTIFY
34 };
35
36 #define SPOOLSS_BUFFER_UNION(fn,info,level) \
37         ((info)?ndr_size_##fn(info, level, 0):0)
38
39 #define SPOOLSS_BUFFER_UNION_ARRAY(fn,info,level,count) \
40         ((info)?ndr_size_##fn##_info(dce_call, level, count, info):0)
41
42 #define SPOOLSS_BUFFER_OK(val_true,val_false) ((r->in.offered >= *r->out.needed)?val_true:val_false)
43
44 static WERROR dcesrv_spoolss_parse_printer_name(TALLOC_CTX *mem_ctx, const char *name,
45                                          const char **_server_name,
46                                          const char **_object_name,
47                                          enum ntptr_HandleType *_object_type)
48 {
49         char *p;
50         char *server = NULL;
51         char *server_unc = NULL;
52         const char *object = name;
53
54         /* no printername is there it's like open server */
55         if (!name) {
56                 *_server_name = NULL;
57                 *_object_name = NULL;
58                 *_object_type = NTPTR_HANDLE_SERVER;
59                 return WERR_OK;
60         }
61
62         /* just "\\" is invalid */
63         if (strequal("\\\\", name)) {
64                 return WERR_INVALID_PRINTER_NAME;
65         }
66
67         if (strncmp("\\\\", name, 2) == 0) {
68                 server_unc = talloc_strdup(mem_ctx, name);
69                 W_ERROR_HAVE_NO_MEMORY(server_unc);
70                 server = server_unc + 2;
71
72                 /* here we know we have "\\" in front not followed
73                  * by '\0', now see if we have another "\" in the string
74                  */
75                 p = strchr_m(server, '\\');
76                 if (!p) {
77                         /* there's no other "\", so it's ("\\%s",server)
78                          */
79                         *_server_name = server_unc;
80                         *_object_name = NULL;
81                         *_object_type = NTPTR_HANDLE_SERVER;
82                         return WERR_OK;
83                 }
84                 /* here we know that we have ("\\%s\",server),
85                  * if we have '\0' as next then it's an invalid name
86                  * otherwise the printer_name
87                  */
88                 p[0] = '\0';
89                 /* everything that follows is the printer name */
90                 p++;
91                 object = p;
92
93                 /* just "" as server is invalid */
94                 if (strequal(server, "")) {
95                         return WERR_INVALID_PRINTER_NAME;
96                 }
97         }
98
99         /* just "" is invalid */
100         if (strequal(object, "")) {
101                 return WERR_INVALID_PRINTER_NAME;
102         }
103
104 #define XCV_PORT ",XcvPort "
105 #define XCV_MONITOR ",XcvMonitor "
106         if (strncmp(object, XCV_PORT, strlen(XCV_PORT)) == 0) {
107                 object += strlen(XCV_PORT);
108
109                 /* just "" is invalid */
110                 if (strequal(object, "")) {
111                         return WERR_INVALID_PRINTER_NAME;
112                 }
113
114                 *_server_name = server_unc;
115                 *_object_name = object;
116                 *_object_type = NTPTR_HANDLE_PORT;
117                 return WERR_OK;
118         } else if (strncmp(object, XCV_MONITOR, strlen(XCV_MONITOR)) == 0) {
119                 object += strlen(XCV_MONITOR);
120
121                 /* just "" is invalid */
122                 if (strequal(object, "")) {
123                         return WERR_INVALID_PRINTER_NAME;
124                 }
125
126                 *_server_name = server_unc;
127                 *_object_name = object;
128                 *_object_type = NTPTR_HANDLE_MONITOR;
129                 return WERR_OK;
130         }
131
132         *_server_name = server_unc;
133         *_object_name = object;
134         *_object_type = NTPTR_HANDLE_PRINTER;
135         return WERR_OK;
136 }
137
138 /*
139  * Check server_name is:
140  * -  "" , functions that don't allow "",
141  *         should check that on their own, before calling this function
142  * -  our name (only netbios yet, TODO: need to test dns name!)
143  * -  our ip address of the current use socket
144  * otherwise return WERR_INVALID_PRINTER_NAME
145  */
146 static WERROR dcesrv_spoolss_check_server_name(struct dcesrv_call_state *dce_call, 
147                                         TALLOC_CTX *mem_ctx,
148                                         const char *server_name)
149 {
150         bool ret;
151         const struct tsocket_address *local_address;
152         char *myaddr;
153         const char **aliases;
154         const char *dnsdomain;
155         unsigned int i;
156
157         /* NULL is ok */
158         if (!server_name) return WERR_OK;
159
160         /* "" is ok */
161         ret = strequal("",server_name);
162         if (ret) return WERR_OK;
163
164         /* just "\\" is invalid */
165         if (strequal("\\\\", server_name)) {
166                 return WERR_INVALID_PRINTER_NAME;
167         }
168
169         /* then we need "\\" */
170         if (strncmp("\\\\", server_name, 2) != 0) {
171                 return WERR_INVALID_PRINTER_NAME;
172         }
173
174         server_name += 2;
175
176         /* NETBIOS NAME is ok */
177         ret = strequal(lpcfg_netbios_name(dce_call->conn->dce_ctx->lp_ctx), server_name);
178         if (ret) return WERR_OK;
179
180         aliases = lpcfg_netbios_aliases(dce_call->conn->dce_ctx->lp_ctx);
181
182         for (i=0; aliases && aliases[i]; i++) {
183                 if (strequal(aliases[i], server_name)) {
184                         return WERR_OK;
185                 }
186         }
187
188         /* DNS NAME is ok
189          * TODO: we need to check if aliases are also ok
190          */
191         dnsdomain = lpcfg_dnsdomain(dce_call->conn->dce_ctx->lp_ctx);
192         if (dnsdomain != NULL) {
193                 char *str;
194
195                 str = talloc_asprintf(mem_ctx, "%s.%s",
196                                                 lpcfg_netbios_name(dce_call->conn->dce_ctx->lp_ctx),
197                                                 dnsdomain);
198                 W_ERROR_HAVE_NO_MEMORY(str);
199
200                 ret = strequal(str, server_name);
201                 talloc_free(str);
202                 if (ret) return WERR_OK;
203         }
204
205         local_address = dcesrv_connection_get_local_address(dce_call->conn);
206
207         myaddr = tsocket_address_inet_addr_string(local_address, mem_ctx);
208         W_ERROR_HAVE_NO_MEMORY(myaddr);
209
210         ret = strequal(myaddr, server_name);
211         talloc_free(myaddr);
212         if (ret) return WERR_OK;
213
214         return WERR_INVALID_PRINTER_NAME;
215 }
216
217 static NTSTATUS dcerpc_spoolss_bind(struct dcesrv_call_state *dce_call, const struct dcesrv_interface *iface)
218 {
219         NTSTATUS status;
220         struct ntptr_context *ntptr;
221
222         status = ntptr_init_context(dce_call->context, dce_call->conn->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
223                                     lpcfg_ntptr_providor(dce_call->conn->dce_ctx->lp_ctx), &ntptr);
224         NT_STATUS_NOT_OK_RETURN(status);
225
226         dce_call->context->private_data = ntptr;
227
228         return NT_STATUS_OK;
229 }
230
231 #define DCESRV_INTERFACE_SPOOLSS_BIND dcerpc_spoolss_bind
232
233 /* 
234   spoolss_EnumPrinters 
235 */
236 static WERROR dcesrv_spoolss_EnumPrinters(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
237                        struct spoolss_EnumPrinters *r)
238 {
239         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
240         WERROR status;
241
242         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.server);
243         W_ERROR_NOT_OK_RETURN(status);
244
245         status = ntptr_EnumPrinters(ntptr, mem_ctx, r);
246         W_ERROR_NOT_OK_RETURN(status);
247
248         *r->out.needed  = SPOOLSS_BUFFER_UNION_ARRAY(spoolss_EnumPrinters, *r->out.info, r->in.level, *r->out.count);
249         *r->out.info    = SPOOLSS_BUFFER_OK(*r->out.info, NULL);
250         *r->out.count   = SPOOLSS_BUFFER_OK(*r->out.count, 0);
251         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
252 }
253
254 static WERROR dcesrv_spoolss_OpenPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
255                        struct spoolss_OpenPrinterEx *r);
256 /* 
257   spoolss_OpenPrinter 
258 */
259 static WERROR dcesrv_spoolss_OpenPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
260                        struct spoolss_OpenPrinter *r)
261 {
262         WERROR status;
263         struct spoolss_OpenPrinterEx *r2;
264
265         r2 = talloc(mem_ctx, struct spoolss_OpenPrinterEx);
266         W_ERROR_HAVE_NO_MEMORY(r2);
267
268         r2->in.printername      = r->in.printername;
269         r2->in.datatype         = r->in.datatype;
270         r2->in.devmode_ctr      = r->in.devmode_ctr;
271         r2->in.access_mask      = r->in.access_mask;
272         r2->in.level            = 1;
273         r2->in.userlevel.level1 = NULL;
274
275         r2->out.handle          = r->out.handle;
276
277         /* TODO: we should take care about async replies here,
278                  if spoolss_OpenPrinterEx() would be async!
279          */
280         status = dcesrv_spoolss_OpenPrinterEx(dce_call, mem_ctx, r2);
281
282         r->out.handle           = r2->out.handle;
283
284         return status;
285 }
286
287
288 /* 
289   spoolss_SetJob 
290 */
291 static WERROR dcesrv_spoolss_SetJob(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
292                        struct spoolss_SetJob *r)
293 {
294         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
295 }
296
297
298 /* 
299   spoolss_GetJob 
300 */
301 static WERROR dcesrv_spoolss_GetJob(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
302                        struct spoolss_GetJob *r)
303 {
304         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
305 }
306
307
308 /* 
309   spoolss_EnumJobs 
310 */
311 static WERROR dcesrv_spoolss_EnumJobs(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
312                        struct spoolss_EnumJobs *r)
313 {
314         return WERR_OK;
315 }
316
317
318 /* 
319   spoolss_AddPrinter 
320 */
321 static WERROR dcesrv_spoolss_AddPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
322                        struct spoolss_AddPrinter *r)
323 {
324         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
325 }
326
327
328 /* 
329   spoolss_DeletePrinter 
330 */
331 static WERROR dcesrv_spoolss_DeletePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
332                        struct spoolss_DeletePrinter *r)
333 {
334         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
335 }
336
337
338 /* 
339   spoolss_SetPrinter 
340 */
341 static WERROR dcesrv_spoolss_SetPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
342                        struct spoolss_SetPrinter *r)
343 {
344         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
345 }
346
347
348 /* 
349   spoolss_GetPrinter 
350 */
351 static WERROR dcesrv_spoolss_GetPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
352                        struct spoolss_GetPrinter *r)
353 {
354         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
355 }
356
357
358 /* 
359   spoolss_AddPrinterDriver 
360 */
361 static WERROR dcesrv_spoolss_AddPrinterDriver(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
362                        struct spoolss_AddPrinterDriver *r)
363 {
364         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
365 }
366
367
368 /* 
369   spoolss_EnumPrinterDrivers 
370 */
371 static WERROR dcesrv_spoolss_EnumPrinterDrivers(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
372                        struct spoolss_EnumPrinterDrivers *r)
373 {
374         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
375         WERROR status;
376
377         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.server);
378         W_ERROR_NOT_OK_RETURN(status);
379
380         status = ntptr_EnumPrinterDrivers(ntptr, mem_ctx, r);
381         W_ERROR_NOT_OK_RETURN(status);
382
383         *r->out.needed  = SPOOLSS_BUFFER_UNION_ARRAY(spoolss_EnumPrinterDrivers, *r->out.info, r->in.level, *r->out.count);
384         *r->out.info    = SPOOLSS_BUFFER_OK(*r->out.info, NULL);
385         *r->out.count   = SPOOLSS_BUFFER_OK(*r->out.count, 0);
386         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
387 }
388
389
390 /* 
391   spoolss_GetPrinterDriver 
392 */
393 static WERROR dcesrv_spoolss_GetPrinterDriver(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
394                        struct spoolss_GetPrinterDriver *r)
395 {
396         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
397 }
398
399
400 /* 
401   spoolss_GetPrinterDriverDirectory 
402 */
403 static WERROR dcesrv_spoolss_GetPrinterDriverDirectory(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
404                        struct spoolss_GetPrinterDriverDirectory *r)
405 {
406         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
407         WERROR status;
408
409         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.server);
410         W_ERROR_NOT_OK_RETURN(status);
411
412         status = ntptr_GetPrinterDriverDirectory(ntptr, mem_ctx, r);
413         W_ERROR_NOT_OK_RETURN(status);
414
415         *r->out.needed  = SPOOLSS_BUFFER_UNION(spoolss_DriverDirectoryInfo, r->out.info, r->in.level);
416         r->out.info     = SPOOLSS_BUFFER_OK(r->out.info, NULL);
417         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
418 }
419
420
421 /* 
422   spoolss_DeletePrinterDriver 
423 */
424 static WERROR dcesrv_spoolss_DeletePrinterDriver(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
425                        struct spoolss_DeletePrinterDriver *r)
426 {
427         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
428 }
429
430
431 /* 
432   spoolss_AddPrintProcessor 
433 */
434 static WERROR dcesrv_spoolss_AddPrintProcessor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
435                        struct spoolss_AddPrintProcessor *r)
436 {
437         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
438 }
439
440
441 /* 
442   spoolss_EnumPrintProcessors 
443 */
444 static WERROR dcesrv_spoolss_EnumPrintProcessors(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
445                        struct spoolss_EnumPrintProcessors *r)
446 {
447         return WERR_OK;
448 }
449
450
451 /* 
452   spoolss_GetPrintProcessorDirectory 
453 */
454 static WERROR dcesrv_spoolss_GetPrintProcessorDirectory(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
455                        struct spoolss_GetPrintProcessorDirectory *r)
456 {
457         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
458         WERROR status;
459
460         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.server);
461         W_ERROR_NOT_OK_RETURN(status);
462
463         status = ntptr_GetPrintProcessorDirectory(ntptr, mem_ctx, r);
464         W_ERROR_NOT_OK_RETURN(status);
465
466         *r->out.needed  = SPOOLSS_BUFFER_UNION(spoolss_PrintProcessorDirectoryInfo, r->out.info, r->in.level);
467         r->out.info     = SPOOLSS_BUFFER_OK(r->out.info, NULL);
468         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
469 }
470
471
472 /* 
473   spoolss_StartDocPrinter 
474 */
475 static WERROR dcesrv_spoolss_StartDocPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
476                        struct spoolss_StartDocPrinter *r)
477 {
478         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
479 }
480
481
482 /* 
483   spoolss_StartPagePrinter 
484 */
485 static WERROR dcesrv_spoolss_StartPagePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
486                        struct spoolss_StartPagePrinter *r)
487 {
488         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
489 }
490
491
492 /* 
493   spoolss_WritePrinter 
494 */
495 static WERROR dcesrv_spoolss_WritePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
496                        struct spoolss_WritePrinter *r)
497 {
498         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
499 }
500
501
502 /* 
503   spoolss_EndPagePrinter 
504 */
505 static WERROR dcesrv_spoolss_EndPagePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
506                        struct spoolss_EndPagePrinter *r)
507 {
508         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
509 }
510
511
512 /* 
513   spoolss_AbortPrinter 
514 */
515 static WERROR dcesrv_spoolss_AbortPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
516                        struct spoolss_AbortPrinter *r)
517 {
518         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
519 }
520
521
522 /* 
523   spoolss_ReadPrinter 
524 */
525 static WERROR dcesrv_spoolss_ReadPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
526                        struct spoolss_ReadPrinter *r)
527 {
528         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
529 }
530
531
532 /* 
533   spoolss_EndDocPrinter 
534 */
535 static WERROR dcesrv_spoolss_EndDocPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
536                        struct spoolss_EndDocPrinter *r)
537 {
538         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
539 }
540
541
542 /* 
543   spoolss_AddJob 
544 */
545 static WERROR dcesrv_spoolss_AddJob(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
546                        struct spoolss_AddJob *r)
547 {
548         if (r->in.level != 1) {
549                 return WERR_UNKNOWN_LEVEL;
550         }
551
552         return WERR_INVALID_PARAM;
553 }
554
555
556 /* 
557   spoolss_ScheduleJob 
558 */
559 static WERROR dcesrv_spoolss_ScheduleJob(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
560                        struct spoolss_ScheduleJob *r)
561 {
562         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
563 }
564
565
566 /* 
567   spoolss_GetPrinterData 
568 */
569 static WERROR dcesrv_spoolss_GetPrinterData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
570                        struct spoolss_GetPrinterData *r)
571 {
572         struct ntptr_GenericHandle *handle;
573         struct dcesrv_handle *h;
574         WERROR status;
575
576         r->out.type = talloc_zero(mem_ctx, enum winreg_Type);
577         W_ERROR_HAVE_NO_MEMORY(r->out.type);
578
579         r->out.needed = talloc_zero(mem_ctx, uint32_t);
580         W_ERROR_HAVE_NO_MEMORY(r->out.needed);
581
582         r->out.data = talloc_zero_array(mem_ctx, uint8_t, r->in.offered);
583         W_ERROR_HAVE_NO_MEMORY(r->out.data);
584
585         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
586         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
587         if (!handle)
588                 return WERR_BADFID;
589
590         switch (handle->type) {
591                 case NTPTR_HANDLE_SERVER:
592                         status = ntptr_GetPrintServerData(handle, mem_ctx, r);
593                         break;
594                 default:
595                         status = WERR_FOOBAR;
596                         break;
597         }
598
599         W_ERROR_NOT_OK_RETURN(status);
600
601         *r->out.type    = SPOOLSS_BUFFER_OK(*r->out.type, REG_NONE);
602         r->out.data     = SPOOLSS_BUFFER_OK(r->out.data, r->out.data);
603         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_MORE_DATA);
604 }
605
606
607 /* 
608   spoolss_SetPrinterData 
609 */
610 static WERROR dcesrv_spoolss_SetPrinterData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
611                        struct spoolss_SetPrinterData *r)
612 {
613         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
614 }
615
616
617 /* 
618   spoolss_WaitForPrinterChange 
619 */
620 static WERROR dcesrv_spoolss_WaitForPrinterChange(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
621                        struct spoolss_WaitForPrinterChange *r)
622 {
623         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
624 }
625
626
627 /* 
628   spoolss_ClosePrinter 
629 */
630 static WERROR dcesrv_spoolss_ClosePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
631                        struct spoolss_ClosePrinter *r)
632 {
633         struct dcesrv_handle *h;
634
635         *r->out.handle = *r->in.handle;
636
637         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
638
639         talloc_free(h);
640
641         ZERO_STRUCTP(r->out.handle);
642
643         return WERR_OK;
644 }
645
646
647 /* 
648   spoolss_AddForm 
649 */
650 static WERROR dcesrv_spoolss_AddForm(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
651                        struct spoolss_AddForm *r)
652 {
653         struct ntptr_GenericHandle *handle;
654         struct dcesrv_handle *h;
655         WERROR status;
656
657         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
658         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
659         if (!handle)
660                 return WERR_BADFID;
661
662         switch (handle->type) {
663                 case NTPTR_HANDLE_SERVER:
664                         status = ntptr_AddPrintServerForm(handle, mem_ctx, r);
665                         W_ERROR_NOT_OK_RETURN(status);
666                         break;
667                 case NTPTR_HANDLE_PRINTER:
668                         status = ntptr_AddPrinterForm(handle, mem_ctx, r);
669                         W_ERROR_NOT_OK_RETURN(status);
670                         break;
671                 default:
672                         return WERR_FOOBAR;
673         }
674
675         return WERR_OK;
676 }
677
678
679 /* 
680   spoolss_DeleteForm 
681 */
682 static WERROR dcesrv_spoolss_DeleteForm(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
683                        struct spoolss_DeleteForm *r)
684 {
685         struct ntptr_GenericHandle *handle;
686         struct dcesrv_handle *h;
687         WERROR status;
688
689         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
690         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
691         if (!handle)
692                 return WERR_BADFID;
693
694         switch (handle->type) {
695                 case NTPTR_HANDLE_SERVER:
696                         status = ntptr_DeletePrintServerForm(handle, mem_ctx, r);
697                         W_ERROR_NOT_OK_RETURN(status);
698                         break;
699                 case NTPTR_HANDLE_PRINTER:
700                         status = ntptr_DeletePrinterForm(handle, mem_ctx, r);
701                         W_ERROR_NOT_OK_RETURN(status);
702                         break;
703                 default:
704                         return WERR_FOOBAR;
705         }
706
707         return WERR_OK;
708 }
709
710
711 /* 
712   spoolss_GetForm 
713 */
714 static WERROR dcesrv_spoolss_GetForm(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
715                        struct spoolss_GetForm *r)
716 {
717         struct ntptr_GenericHandle *handle;
718         struct dcesrv_handle *h;
719         WERROR status;
720
721         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
722         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
723         if (!handle)
724                 return WERR_BADFID;
725
726         switch (handle->type) {
727                 case NTPTR_HANDLE_SERVER:
728                         /*
729                          * stupid, but w2k3 returns WERR_BADFID here?
730                          */
731                         return WERR_BADFID;
732                 case NTPTR_HANDLE_PRINTER:
733                         status = ntptr_GetPrinterForm(handle, mem_ctx, r);
734                         W_ERROR_NOT_OK_RETURN(status);
735                         break;
736                 default:
737                         return WERR_FOOBAR;
738         }
739
740         *r->out.needed  = SPOOLSS_BUFFER_UNION(spoolss_FormInfo, r->out.info, r->in.level);
741         r->out.info     = SPOOLSS_BUFFER_OK(r->out.info, NULL);
742         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
743 }
744
745
746 /* 
747   spoolss_SetForm 
748 */
749 static WERROR dcesrv_spoolss_SetForm(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
750                        struct spoolss_SetForm *r)
751 {
752         struct ntptr_GenericHandle *handle;
753         struct dcesrv_handle *h;
754         WERROR status;
755
756         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
757         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
758         if (!handle)
759                 return WERR_BADFID;
760
761         switch (handle->type) {
762                 case NTPTR_HANDLE_SERVER:
763                         status = ntptr_SetPrintServerForm(handle, mem_ctx, r);
764                         W_ERROR_NOT_OK_RETURN(status);
765                         break;
766                 case NTPTR_HANDLE_PRINTER:
767                         status = ntptr_SetPrinterForm(handle, mem_ctx, r);
768                         W_ERROR_NOT_OK_RETURN(status);
769                         break;
770                 default:
771                         return WERR_FOOBAR;
772         }
773
774         return WERR_OK;
775 }
776
777
778 /* 
779   spoolss_EnumForms 
780 */
781 static WERROR dcesrv_spoolss_EnumForms(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
782                        struct spoolss_EnumForms *r)
783 {
784         struct ntptr_GenericHandle *handle;
785         struct dcesrv_handle *h;
786         WERROR status;
787
788         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
789         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
790         if (!handle)
791                 return WERR_BADFID;
792
793         switch (handle->type) {
794                 case NTPTR_HANDLE_SERVER:
795                         status = ntptr_EnumPrintServerForms(handle, mem_ctx, r);
796                         W_ERROR_NOT_OK_RETURN(status);
797                         break;
798                 case NTPTR_HANDLE_PRINTER:
799                         status = ntptr_EnumPrinterForms(handle, mem_ctx, r);
800                         W_ERROR_NOT_OK_RETURN(status);
801                         break;
802                 default:
803                         return WERR_FOOBAR;
804         }
805
806         *r->out.needed  = SPOOLSS_BUFFER_UNION_ARRAY(spoolss_EnumForms, *r->out.info, r->in.level, *r->out.count);
807         *r->out.info    = SPOOLSS_BUFFER_OK(*r->out.info, NULL);
808         *r->out.count   = SPOOLSS_BUFFER_OK(*r->out.count, 0);
809         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
810 }
811
812
813 /* 
814   spoolss_EnumPorts 
815 */
816 static WERROR dcesrv_spoolss_EnumPorts(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
817                        struct spoolss_EnumPorts *r)
818 {
819         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
820         WERROR status;
821
822         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.servername);
823         W_ERROR_NOT_OK_RETURN(status);
824
825         status = ntptr_EnumPorts(ntptr, mem_ctx, r);
826         W_ERROR_NOT_OK_RETURN(status);
827
828         *r->out.needed  = SPOOLSS_BUFFER_UNION_ARRAY(spoolss_EnumPorts, *r->out.info, r->in.level, *r->out.count);
829         *r->out.info    = SPOOLSS_BUFFER_OK(*r->out.info, NULL);
830         *r->out.count   = SPOOLSS_BUFFER_OK(*r->out.count, 0);
831         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
832 }
833
834
835 /* 
836   spoolss_EnumMonitors 
837 */
838 static WERROR dcesrv_spoolss_EnumMonitors(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
839                        struct spoolss_EnumMonitors *r)
840 {
841         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
842         WERROR status;
843
844         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, r->in.servername);
845         W_ERROR_NOT_OK_RETURN(status);
846
847         status = ntptr_EnumMonitors(ntptr, mem_ctx, r);
848         W_ERROR_NOT_OK_RETURN(status);
849
850         *r->out.needed  = SPOOLSS_BUFFER_UNION_ARRAY(spoolss_EnumMonitors, *r->out.info, r->in.level, *r->out.count);
851         *r->out.info    = SPOOLSS_BUFFER_OK(*r->out.info, NULL);
852         *r->out.count   = SPOOLSS_BUFFER_OK(*r->out.count, 0);
853         return SPOOLSS_BUFFER_OK(WERR_OK, WERR_INSUFFICIENT_BUFFER);
854 }
855
856
857 /* 
858   spoolss_AddPort 
859 */
860 static WERROR dcesrv_spoolss_AddPort(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
861                        struct spoolss_AddPort *r)
862 {
863         return WERR_NOT_SUPPORTED;
864 }
865
866
867 /* 
868   spoolss_ConfigurePort 
869 */
870 static WERROR dcesrv_spoolss_ConfigurePort(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
871                        struct spoolss_ConfigurePort *r)
872 {
873         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
874 }
875
876
877 /* 
878   spoolss_DeletePort 
879 */
880 static WERROR dcesrv_spoolss_DeletePort(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
881                        struct spoolss_DeletePort *r)
882 {
883         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
884 }
885
886
887 /* 
888   spoolss_CreatePrinterIC 
889 */
890 static WERROR dcesrv_spoolss_CreatePrinterIC(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
891                        struct spoolss_CreatePrinterIC *r)
892 {
893         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
894 }
895
896
897 /* 
898   spoolss_PlayGDIScriptOnPrinterIC 
899 */
900 static WERROR dcesrv_spoolss_PlayGDIScriptOnPrinterIC(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
901                        struct spoolss_PlayGDIScriptOnPrinterIC *r)
902 {
903         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
904 }
905
906
907 /* 
908   spoolss_DeletePrinterIC 
909 */
910 static WERROR dcesrv_spoolss_DeletePrinterIC(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
911                        struct spoolss_DeletePrinterIC *r)
912 {
913         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
914 }
915
916
917 /* 
918   spoolss_AddPrinterConnection 
919 */
920 static WERROR dcesrv_spoolss_AddPrinterConnection(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
921                        struct spoolss_AddPrinterConnection *r)
922 {
923         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
924 }
925
926
927 /* 
928   spoolss_DeletePrinterConnection 
929 */
930 static WERROR dcesrv_spoolss_DeletePrinterConnection(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
931                        struct spoolss_DeletePrinterConnection *r)
932 {
933         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
934 }
935
936
937 /* 
938   spoolss_PrinterMessageBox 
939 */
940 static WERROR dcesrv_spoolss_PrinterMessageBox(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
941                        struct spoolss_PrinterMessageBox *r)
942 {
943         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
944 }
945
946
947 /* 
948   spoolss_AddMonitor 
949 */
950 static WERROR dcesrv_spoolss_AddMonitor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
951                        struct spoolss_AddMonitor *r)
952 {
953         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
954 }
955
956
957 /* 
958   spoolss_DeleteMonitor 
959 */
960 static WERROR dcesrv_spoolss_DeleteMonitor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
961                        struct spoolss_DeleteMonitor *r)
962 {
963         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
964 }
965
966
967 /* 
968   spoolss_DeletePrintProcessor 
969 */
970 static WERROR dcesrv_spoolss_DeletePrintProcessor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
971                        struct spoolss_DeletePrintProcessor *r)
972 {
973         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
974 }
975
976
977 /* 
978   spoolss_AddPrintProvidor 
979 */
980 static WERROR dcesrv_spoolss_AddPrintProvidor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
981                        struct spoolss_AddPrintProvidor *r)
982 {
983         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
984 }
985
986
987 /* 
988   spoolss_DeletePrintProvidor 
989 */
990 static WERROR dcesrv_spoolss_DeletePrintProvidor(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
991                        struct spoolss_DeletePrintProvidor *r)
992 {
993         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
994 }
995
996
997 /* 
998   spoolss_EnumPrintProcDataTypes 
999 */
1000 static WERROR dcesrv_spoolss_EnumPrintProcDataTypes(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1001                        struct spoolss_EnumPrintProcDataTypes *r)
1002 {
1003         return WERR_OK;
1004 }
1005
1006
1007 /* 
1008   spoolss_ResetPrinter 
1009 */
1010 static WERROR dcesrv_spoolss_ResetPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1011                        struct spoolss_ResetPrinter *r)
1012 {
1013         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1014 }
1015
1016
1017 /* 
1018   spoolss_GetPrinterDriver2 
1019 */
1020 static WERROR dcesrv_spoolss_GetPrinterDriver2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1021                        struct spoolss_GetPrinterDriver2 *r)
1022 {
1023         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1024 }
1025
1026
1027 /* 
1028   spoolss_FindFirstPrinterChangeNotification 
1029 */
1030 static WERROR dcesrv_spoolss_FindFirstPrinterChangeNotification(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1031                        struct spoolss_FindFirstPrinterChangeNotification *r)
1032 {
1033         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1034 }
1035
1036
1037 /* 
1038   spoolss_FindNextPrinterChangeNotification 
1039 */
1040 static WERROR dcesrv_spoolss_FindNextPrinterChangeNotification(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1041                        struct spoolss_FindNextPrinterChangeNotification *r)
1042 {
1043         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1044 }
1045
1046
1047 /* 
1048   spoolss_FindClosePrinterNotify 
1049 */
1050 static WERROR dcesrv_spoolss_FindClosePrinterNotify(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1051                        struct spoolss_FindClosePrinterNotify *r)
1052 {
1053         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1054 }
1055
1056
1057 /* 
1058   spoolss_RouterFindFirstPrinterChangeNotificationOld 
1059 */
1060 static WERROR dcesrv_spoolss_RouterFindFirstPrinterChangeNotificationOld(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1061                        struct spoolss_RouterFindFirstPrinterChangeNotificationOld *r)
1062 {
1063         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1064 }
1065
1066
1067 /* 
1068   spoolss_ReplyOpenPrinter 
1069 */
1070 static WERROR dcesrv_spoolss_ReplyOpenPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1071                        struct spoolss_ReplyOpenPrinter *r)
1072 {
1073         struct dcesrv_handle *handle;
1074
1075         handle = dcesrv_handle_new(dce_call->context, SPOOLSS_NOTIFY);
1076         W_ERROR_HAVE_NO_MEMORY(handle);
1077
1078         /* For now, just return a handle */
1079
1080         *r->out.handle = handle->wire_handle;
1081
1082         return WERR_OK;
1083 }
1084
1085
1086 /* 
1087   spoolss_RouterReplyPrinter 
1088 */
1089 static WERROR dcesrv_spoolss_RouterReplyPrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1090                        struct spoolss_RouterReplyPrinter *r)
1091 {
1092         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1093 }
1094
1095
1096 /* 
1097   spoolss_ReplyClosePrinter 
1098 */
1099 static WERROR dcesrv_spoolss_ReplyClosePrinter(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1100                        struct spoolss_ReplyClosePrinter *r)
1101 {
1102         struct dcesrv_handle *handle;
1103         
1104         DCESRV_PULL_HANDLE_WERR(handle, r->in.handle, SPOOLSS_NOTIFY);
1105
1106         talloc_free(handle);
1107
1108         ZERO_STRUCTP(r->out.handle);
1109
1110         return WERR_OK;
1111 }
1112
1113 /* 
1114   spoolss_AddPortEx 
1115 */
1116 static WERROR dcesrv_spoolss_AddPortEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1117                        struct spoolss_AddPortEx *r)
1118 {
1119         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1120 }
1121
1122
1123 /* 
1124   spoolss_RouterFindFirstPrinterChangeNotification 
1125 */
1126 static WERROR dcesrv_spoolss_RouterFindFirstPrinterChangeNotification(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1127                        struct spoolss_RouterFindFirstPrinterChangeNotification *r)
1128 {
1129         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1130 }
1131
1132
1133 /* 
1134   spoolss_SpoolerInit 
1135 */
1136 static WERROR dcesrv_spoolss_SpoolerInit(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1137                        struct spoolss_SpoolerInit *r)
1138 {
1139         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1140 }
1141
1142
1143 /* 
1144   spoolss_ResetPrinterEx 
1145 */
1146 static WERROR dcesrv_spoolss_ResetPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1147                        struct spoolss_ResetPrinterEx *r)
1148 {
1149         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1150 }
1151
1152
1153 /* 
1154   spoolss_RemoteFindFirstPrinterChangeNotifyEx 
1155 */
1156 static WERROR dcesrv_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1157                        struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r)
1158 {
1159         struct dcerpc_pipe *p;
1160         struct dcerpc_binding *binding;
1161         NTSTATUS status;
1162         struct spoolss_ReplyOpenPrinter rop;
1163         struct cli_credentials *creds;
1164         struct policy_handle notify_handle;
1165
1166         DEBUG(2, ("Received RFFPCNex from %s\n", r->in.local_machine));
1167
1168         /*
1169          * TODO: for now just open a connection to the client and drop it again
1170          *       to keep the w2k3 PrintServer 
1171          *       happy to allow to open the Add Printer GUI
1172          *       and the torture suite passing
1173          */
1174
1175         binding = talloc_zero(mem_ctx, struct dcerpc_binding);
1176
1177         binding->transport = NCACN_NP; 
1178         if (strncmp(r->in.local_machine, "\\\\", 2))
1179                 return WERR_INVALID_COMPUTERNAME;
1180         binding->host = r->in.local_machine+2;
1181
1182         creds = cli_credentials_init_anon(mem_ctx); /* FIXME: Use machine credentials instead ? */
1183
1184         status = dcerpc_pipe_connect_b(mem_ctx, &p, binding, &ndr_table_spoolss, 
1185                                        creds, dce_call->event_ctx,
1186                                        dce_call->conn->dce_ctx->lp_ctx);
1187
1188         if (NT_STATUS_IS_ERR(status)) {
1189                 DEBUG(0, ("unable to call back to %s\n", r->in.local_machine));
1190                 return WERR_SERVER_UNAVAILABLE;
1191         }
1192
1193         ZERO_STRUCT(rop);
1194         rop.in.server_name = lpcfg_netbios_name(dce_call->conn->dce_ctx->lp_ctx);
1195         W_ERROR_HAVE_NO_MEMORY(rop.in.server_name);
1196         rop.in.printer_local = 0;
1197         rop.in.type = REG_NONE;
1198         rop.in.bufsize = 0;
1199         rop.in.buffer = NULL;
1200         rop.out.handle = &notify_handle;
1201
1202         status = dcerpc_spoolss_ReplyOpenPrinter_r(p->binding_handle, mem_ctx, &rop);
1203         if (NT_STATUS_IS_ERR(status)) {
1204                 DEBUG(0, ("unable to open remote printer %s\n",
1205                         r->in.local_machine));
1206                 return WERR_SERVER_UNAVAILABLE;
1207         }
1208
1209         talloc_free(p);
1210
1211         return WERR_OK;
1212 }
1213
1214
1215 /* 
1216   spoolss_RouterReplyPrinterEx
1217 */
1218 static WERROR dcesrv_spoolss_RouterReplyPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1219                        struct spoolss_RouterReplyPrinterEx *r)
1220 {
1221         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1222 }
1223
1224
1225 /* 
1226   spoolss_RouterRefreshPrinterChangeNotify
1227 */
1228 static WERROR dcesrv_spoolss_RouterRefreshPrinterChangeNotify(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1229                        struct spoolss_RouterRefreshPrinterChangeNotify *r)
1230 {
1231         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1232 }
1233
1234
1235 /* 
1236   spoolss_44 
1237 */
1238 static WERROR dcesrv_spoolss_44(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1239                        struct spoolss_44 *r)
1240 {
1241         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1242 }
1243
1244 /* 
1245   spoolss_OpenPrinterEx 
1246 */
1247 static WERROR dcesrv_spoolss_OpenPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1248                        struct spoolss_OpenPrinterEx *r)
1249 {
1250         struct ntptr_context *ntptr = talloc_get_type(dce_call->context->private_data, struct ntptr_context);
1251         struct ntptr_GenericHandle *handle;
1252         struct dcesrv_handle *h;
1253         const char *server;
1254         const char *object;
1255         enum ntptr_HandleType type;
1256         WERROR status;
1257
1258         ZERO_STRUCTP(r->out.handle);
1259
1260         status = dcesrv_spoolss_parse_printer_name(mem_ctx, r->in.printername, &server, &object, &type);
1261         W_ERROR_NOT_OK_RETURN(status);
1262
1263         status = dcesrv_spoolss_check_server_name(dce_call, mem_ctx, server);
1264         W_ERROR_NOT_OK_RETURN(status);
1265
1266         switch (type) {
1267                 case NTPTR_HANDLE_SERVER:
1268                         status = ntptr_OpenPrintServer(ntptr, mem_ctx, r, server, &handle);
1269                         W_ERROR_NOT_OK_RETURN(status);
1270                         break;
1271                 case NTPTR_HANDLE_PORT:
1272                         status = ntptr_OpenPort(ntptr, mem_ctx, r, object, &handle);
1273                         W_ERROR_NOT_OK_RETURN(status);
1274                         break;
1275                 case NTPTR_HANDLE_MONITOR:
1276                         status = ntptr_OpenMonitor(ntptr, mem_ctx, r, object, &handle);
1277                         W_ERROR_NOT_OK_RETURN(status);
1278                         break;
1279                 case NTPTR_HANDLE_PRINTER:
1280                         status = ntptr_OpenPrinter(ntptr, mem_ctx, r, object, &handle);
1281                         W_ERROR_NOT_OK_RETURN(status);
1282                         break;
1283                 default:
1284                         return WERR_FOOBAR;
1285         }
1286
1287         h = dcesrv_handle_new(dce_call->context, handle->type);
1288         W_ERROR_HAVE_NO_MEMORY(h);
1289
1290         h->data = talloc_steal(h, handle);
1291
1292         *r->out.handle  = h->wire_handle;
1293
1294         return WERR_OK;
1295 }
1296
1297 /* 
1298   spoolss_AddPrinterEx 
1299 */
1300 static WERROR dcesrv_spoolss_AddPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1301                        struct spoolss_AddPrinterEx *r)
1302 {
1303         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1304 }
1305
1306
1307 /* 
1308   spoolss_SetPort
1309 */
1310 static WERROR dcesrv_spoolss_SetPort(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1311                        struct spoolss_SetPort *r)
1312 {
1313         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1314 }
1315
1316
1317 /* 
1318   spoolss_EnumPrinterData 
1319 */
1320 static WERROR dcesrv_spoolss_EnumPrinterData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1321                        struct spoolss_EnumPrinterData *r)
1322 {
1323         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1324 }
1325
1326
1327 /* 
1328   spoolss_DeletePrinterData 
1329 */
1330 static WERROR dcesrv_spoolss_DeletePrinterData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1331                        struct spoolss_DeletePrinterData *r)
1332 {
1333         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1334 }
1335
1336
1337 /* 
1338   spoolss_4a 
1339 */
1340 static WERROR dcesrv_spoolss_4a(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1341                        struct spoolss_4a *r)
1342 {
1343         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1344 }
1345
1346
1347 /* 
1348   spoolss_4b 
1349 */
1350 static WERROR dcesrv_spoolss_4b(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1351                        struct spoolss_4b *r)
1352 {
1353         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1354 }
1355
1356
1357 /* 
1358   spoolss_4c 
1359 */
1360 static WERROR dcesrv_spoolss_4c(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1361                        struct spoolss_4c *r)
1362 {
1363         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1364 }
1365
1366
1367 /* 
1368   spoolss_SetPrinterDataEx 
1369 */
1370 static WERROR dcesrv_spoolss_SetPrinterDataEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1371                        struct spoolss_SetPrinterDataEx *r)
1372 {
1373         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1374 }
1375
1376
1377 /* 
1378   spoolss_GetPrinterDataEx 
1379 */
1380 static WERROR dcesrv_spoolss_GetPrinterDataEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1381                        struct spoolss_GetPrinterDataEx *r)
1382 {
1383         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1384 }
1385
1386
1387 /* 
1388   spoolss_EnumPrinterDataEx 
1389 */
1390 static WERROR dcesrv_spoolss_EnumPrinterDataEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1391                        struct spoolss_EnumPrinterDataEx *r)
1392 {
1393         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1394 }
1395
1396
1397 /* 
1398   spoolss_EnumPrinterKey 
1399 */
1400 static WERROR dcesrv_spoolss_EnumPrinterKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1401                        struct spoolss_EnumPrinterKey *r)
1402 {
1403         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1404 }
1405
1406
1407 /* 
1408   spoolss_DeletePrinterDataEx 
1409 */
1410 static WERROR dcesrv_spoolss_DeletePrinterDataEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1411                        struct spoolss_DeletePrinterDataEx *r)
1412 {
1413         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1414 }
1415
1416
1417 /* 
1418   spoolss_DeletePrinterKey 
1419 */
1420 static WERROR dcesrv_spoolss_DeletePrinterKey(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1421                        struct spoolss_DeletePrinterKey *r)
1422 {
1423         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1424 }
1425
1426
1427 /* 
1428   spoolss_53 
1429 */
1430 static WERROR dcesrv_spoolss_53(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1431                        struct spoolss_53 *r)
1432 {
1433         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1434 }
1435
1436
1437 /* 
1438   spoolss_DeletePrinterDriverEx 
1439 */
1440 static WERROR dcesrv_spoolss_DeletePrinterDriverEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1441                        struct spoolss_DeletePrinterDriverEx *r)
1442 {
1443         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1444 }
1445
1446
1447 /* 
1448   spoolss_AddPerMachineConnection
1449 */
1450 static WERROR dcesrv_spoolss_AddPerMachineConnection(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1451                        struct spoolss_AddPerMachineConnection *r)
1452 {
1453         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1454 }
1455
1456
1457 /* 
1458   spoolss_DeletePerMachineConnection
1459 */
1460 static WERROR dcesrv_spoolss_DeletePerMachineConnection(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1461                        struct spoolss_DeletePerMachineConnection *r)
1462 {
1463         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1464 }
1465
1466
1467 /* 
1468   spoolss_EnumPerMachineConnections
1469 */
1470 static WERROR dcesrv_spoolss_EnumPerMachineConnections(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1471                        struct spoolss_EnumPerMachineConnections *r)
1472 {
1473         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1474 }
1475
1476
1477 /* 
1478   spoolss_XcvData
1479 */
1480 static WERROR dcesrv_spoolss_XcvData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1481                        struct spoolss_XcvData *r)
1482 {
1483         struct ntptr_GenericHandle *handle;
1484         struct dcesrv_handle *h;
1485         WERROR status;
1486
1487         DCESRV_PULL_HANDLE_WERR(h, r->in.handle, DCESRV_HANDLE_ANY);
1488         handle = talloc_get_type(h->data, struct ntptr_GenericHandle);
1489
1490         switch (handle->type) {
1491                 case NTPTR_HANDLE_SERVER:
1492                         status = ntptr_XcvDataPrintServer(handle, mem_ctx, r);
1493                         W_ERROR_NOT_OK_RETURN(status);
1494                         break;
1495                 case NTPTR_HANDLE_PRINTER:
1496                         status = ntptr_XcvDataPrinter(handle, mem_ctx, r);
1497                         W_ERROR_NOT_OK_RETURN(status);
1498                         break;
1499                 case NTPTR_HANDLE_PORT:
1500                         status = ntptr_XcvDataPort(handle, mem_ctx, r);
1501                         W_ERROR_NOT_OK_RETURN(status);
1502                         break;
1503                 case NTPTR_HANDLE_MONITOR:
1504                         status = ntptr_XcvDataMonitor(handle, mem_ctx, r);
1505                         W_ERROR_NOT_OK_RETURN(status);
1506                         break;
1507                 default:
1508                         return WERR_FOOBAR;
1509         }
1510
1511         /* TODO: handle the buffer sizes here! */
1512         return WERR_OK;
1513 }
1514
1515
1516 /* 
1517   spoolss_AddPrinterDriverEx 
1518 */
1519 static WERROR dcesrv_spoolss_AddPrinterDriverEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1520                        struct spoolss_AddPrinterDriverEx *r)
1521 {
1522         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1523 }
1524
1525
1526 /* 
1527   spoolss_5a 
1528 */
1529 static WERROR dcesrv_spoolss_5a(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1530                        struct spoolss_5a *r)
1531 {
1532         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1533 }
1534
1535
1536 /* 
1537   spoolss_5b 
1538 */
1539 static WERROR dcesrv_spoolss_5b(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1540                        struct spoolss_5b *r)
1541 {
1542         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1543 }
1544
1545
1546 /* 
1547   spoolss_5c 
1548 */
1549 static WERROR dcesrv_spoolss_5c(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1550                        struct spoolss_5c *r)
1551 {
1552         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1553 }
1554
1555
1556 /* 
1557   spoolss_5d 
1558 */
1559 static WERROR dcesrv_spoolss_5d(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1560                        struct spoolss_5d *r)
1561 {
1562         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1563 }
1564
1565
1566 /* 
1567   spoolss_5e 
1568 */
1569 static WERROR dcesrv_spoolss_5e(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1570                        struct spoolss_5e *r)
1571 {
1572         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1573 }
1574
1575
1576 /* 
1577   spoolss_5f 
1578 */
1579 static WERROR dcesrv_spoolss_5f(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1580                        struct spoolss_5f *r)
1581 {
1582         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1583 }
1584
1585 /*
1586   spoolss_60
1587 */
1588 static WERROR dcesrv_spoolss_60(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1589                        struct spoolss_60 *r)
1590 {
1591         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1592 }
1593
1594
1595 /*
1596   spoolss_61
1597 */
1598 static WERROR dcesrv_spoolss_61(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1599                        struct spoolss_61 *r)
1600 {
1601         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1602 }
1603
1604
1605 /*
1606   spoolss_62
1607 */
1608 static WERROR dcesrv_spoolss_62(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1609                        struct spoolss_62 *r)
1610 {
1611         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1612 }
1613
1614
1615 /*
1616   spoolss_63
1617 */
1618 static WERROR dcesrv_spoolss_63(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1619                        struct spoolss_63 *r)
1620 {
1621         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1622 }
1623
1624
1625 /*
1626   spoolss_64
1627 */
1628 static WERROR dcesrv_spoolss_64(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1629                        struct spoolss_64 *r)
1630 {
1631         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1632 }
1633
1634
1635 /*
1636   spoolss_65
1637 */
1638 static WERROR dcesrv_spoolss_65(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1639                        struct spoolss_65 *r)
1640 {
1641         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1642 }
1643
1644
1645 /*
1646   spoolss_GetCorePrinterDrivers
1647 */
1648 static WERROR dcesrv_spoolss_GetCorePrinterDrivers(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1649                        struct spoolss_GetCorePrinterDrivers *r)
1650 {
1651         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1652 }
1653
1654
1655 /*
1656   spoolss_67
1657 */
1658 static WERROR dcesrv_spoolss_67(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1659                        struct spoolss_67 *r)
1660 {
1661         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1662 }
1663
1664
1665 /*
1666   spoolss_GetPrinterDriverPackagePath
1667 */
1668 static WERROR dcesrv_spoolss_GetPrinterDriverPackagePath(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1669                        struct spoolss_GetPrinterDriverPackagePath *r)
1670 {
1671         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1672 }
1673
1674
1675 /*
1676   spoolss_69
1677 */
1678 static WERROR dcesrv_spoolss_69(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1679                        struct spoolss_69 *r)
1680 {
1681         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1682 }
1683
1684
1685 /*
1686   spoolss_6a
1687 */
1688 static WERROR dcesrv_spoolss_6a(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1689                        struct spoolss_6a *r)
1690 {
1691         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1692 }
1693
1694
1695 /*
1696   spoolss_6b
1697 */
1698 static WERROR dcesrv_spoolss_6b(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1699                        struct spoolss_6b *r)
1700 {
1701         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1702 }
1703
1704
1705 /*
1706   spoolss_6c
1707 */
1708 static WERROR dcesrv_spoolss_6c(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1709                        struct spoolss_6c *r)
1710 {
1711         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1712 }
1713
1714
1715 /*
1716   spoolss_6d
1717 */
1718 static WERROR dcesrv_spoolss_6d(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1719                        struct spoolss_6d *r)
1720 {
1721         DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1722 }
1723
1724
1725
1726 /* include the generated boilerplate */
1727 #include "librpc/gen_ndr/ndr_spoolss_s.c"