Coverage Report

Created: 2025-07-23 07:04

/src/samba/source3/rpc_client/cli_spoolss.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
   Unix SMB/CIFS implementation.
3
   RPC pipe client
4
5
   Copyright (C) Gerald Carter                2001-2005,
6
   Copyright (C) Tim Potter                   2000-2002,
7
   Copyright (C) Andrew Tridgell              1994-2000,
8
   Copyright (C) Jean-Francois Micouleau      1999-2000.
9
   Copyright (C) Jeremy Allison                         2005.
10
11
   This program is free software; you can redistribute it and/or modify
12
   it under the terms of the GNU General Public License as published by
13
   the Free Software Foundation; either version 3 of the License, or
14
   (at your option) any later version.
15
16
   This program is distributed in the hope that it will be useful,
17
   but WITHOUT ANY WARRANTY; without even the implied warranty of
18
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19
   GNU General Public License for more details.
20
21
   You should have received a copy of the GNU General Public License
22
   along with this program.  If not, see <http://www.gnu.org/licenses/>.
23
*/
24
25
#include "includes.h"
26
#include "rpc_client/rpc_client.h"
27
#include "../librpc/gen_ndr/ndr_spoolss_c.h"
28
#include "rpc_client/cli_spoolss.h"
29
#include "auth/gensec/gensec.h"
30
#include "auth/credentials/credentials.h"
31
#include "rpc_client/init_spoolss.h"
32
33
/**********************************************************************
34
 convenience wrapper around rpccli_spoolss_OpenPrinterEx
35
**********************************************************************/
36
37
WERROR rpccli_spoolss_openprinter_ex(struct rpc_pipe_client *cli,
38
             TALLOC_CTX *mem_ctx,
39
             const char *printername,
40
             uint32_t access_desired,
41
             struct policy_handle *handle)
42
0
{
43
0
  NTSTATUS status;
44
0
  WERROR werror;
45
0
  struct spoolss_DevmodeContainer devmode_ctr;
46
0
  struct spoolss_UserLevelCtr userlevel_ctr;
47
0
  struct spoolss_UserLevel1 level1;
48
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
49
50
0
  ZERO_STRUCT(devmode_ctr);
51
52
0
  werror = spoolss_init_spoolss_UserLevel1(mem_ctx,
53
0
             cli->printer_username,
54
0
             &level1);
55
0
  if (!W_ERROR_IS_OK(werror)) {
56
0
    return werror;
57
0
  }
58
59
0
  userlevel_ctr.level = 1;
60
0
  userlevel_ctr.user_info.level1 = &level1;
61
62
0
  status = dcerpc_spoolss_OpenPrinterEx(b, mem_ctx,
63
0
                printername,
64
0
                NULL,
65
0
                devmode_ctr,
66
0
                access_desired,
67
0
                userlevel_ctr,
68
0
                handle,
69
0
                &werror);
70
71
0
  if (!NT_STATUS_IS_OK(status)) {
72
0
    return ntstatus_to_werror(status);
73
0
  }
74
75
0
  if (!W_ERROR_IS_OK(werror)) {
76
0
    return werror;
77
0
  }
78
79
0
  return WERR_OK;
80
0
}
81
82
/**********************************************************************
83
 convenience wrapper around rpccli_spoolss_GetPrinterDriver
84
**********************************************************************/
85
86
WERROR rpccli_spoolss_getprinterdriver(struct rpc_pipe_client *cli,
87
               TALLOC_CTX *mem_ctx,
88
               struct policy_handle *handle,
89
               const char *architecture,
90
               uint32_t level,
91
               uint32_t offered,
92
               union spoolss_DriverInfo *info)
93
0
{
94
0
  NTSTATUS status;
95
0
  WERROR werror;
96
0
  uint32_t needed;
97
0
  DATA_BLOB buffer;
98
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
99
100
0
  if (offered > 0) {
101
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
102
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
103
0
  }
104
105
0
  status = dcerpc_spoolss_GetPrinterDriver(b, mem_ctx,
106
0
             handle,
107
0
             architecture,
108
0
             level,
109
0
             (offered > 0) ? &buffer : NULL,
110
0
             offered,
111
0
             info,
112
0
             &needed,
113
0
             &werror);
114
0
  if (!NT_STATUS_IS_OK(status)) {
115
0
    return ntstatus_to_werror(status);
116
0
  }
117
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
118
0
    offered = needed;
119
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
120
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
121
122
0
    status = dcerpc_spoolss_GetPrinterDriver(b, mem_ctx,
123
0
               handle,
124
0
               architecture,
125
0
               level,
126
0
               &buffer,
127
0
               offered,
128
0
               info,
129
0
               &needed,
130
0
               &werror);
131
0
  }
132
0
  if (!NT_STATUS_IS_OK(status)) {
133
0
    return ntstatus_to_werror(status);
134
0
  }
135
136
0
  return werror;
137
0
}
138
139
/**********************************************************************
140
 convenience wrapper around rpccli_spoolss_GetPrinterDriver2
141
**********************************************************************/
142
143
WERROR rpccli_spoolss_getprinterdriver2(struct rpc_pipe_client *cli,
144
          TALLOC_CTX *mem_ctx,
145
          struct policy_handle *handle,
146
          const char *architecture,
147
          uint32_t level,
148
          uint32_t offered,
149
          uint32_t client_major_version,
150
          uint32_t client_minor_version,
151
          union spoolss_DriverInfo *info,
152
          uint32_t *server_major_version,
153
          uint32_t *server_minor_version)
154
0
{
155
0
  NTSTATUS status;
156
0
  WERROR werror;
157
0
  uint32_t needed;
158
0
  DATA_BLOB buffer;
159
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
160
161
0
  if (offered > 0) {
162
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
163
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
164
0
  }
165
166
0
  status = dcerpc_spoolss_GetPrinterDriver2(b, mem_ctx,
167
0
              handle,
168
0
              architecture,
169
0
              level,
170
0
              (offered > 0) ? &buffer : NULL,
171
0
              offered,
172
0
              client_major_version,
173
0
              client_minor_version,
174
0
              info,
175
0
              &needed,
176
0
              server_major_version,
177
0
              server_minor_version,
178
0
              &werror);
179
0
  if (!NT_STATUS_IS_OK(status)) {
180
0
    return ntstatus_to_werror(status);
181
0
  }
182
183
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
184
0
    offered = needed;
185
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
186
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
187
188
0
    status = dcerpc_spoolss_GetPrinterDriver2(b, mem_ctx,
189
0
                handle,
190
0
                architecture,
191
0
                level,
192
0
                &buffer,
193
0
                offered,
194
0
                client_major_version,
195
0
                client_minor_version,
196
0
                info,
197
0
                &needed,
198
0
                server_major_version,
199
0
                server_minor_version,
200
0
                &werror);
201
0
  }
202
0
  if (!NT_STATUS_IS_OK(status)) {
203
0
    return ntstatus_to_werror(status);
204
0
  }
205
206
0
  return werror;
207
0
}
208
209
/**********************************************************************
210
 convenience wrapper around rpccli_spoolss_AddPrinterEx
211
**********************************************************************/
212
213
WERROR rpccli_spoolss_addprinterex(struct rpc_pipe_client *cli,
214
           TALLOC_CTX *mem_ctx,
215
           struct spoolss_SetPrinterInfoCtr *info_ctr)
216
0
{
217
0
  WERROR result;
218
0
  NTSTATUS status;
219
0
  struct spoolss_DevmodeContainer devmode_ctr;
220
0
  struct sec_desc_buf secdesc_ctr;
221
0
  struct spoolss_UserLevelCtr userlevel_ctr;
222
0
  struct spoolss_UserLevel1 level1;
223
0
  struct policy_handle handle;
224
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
225
226
0
  ZERO_STRUCT(devmode_ctr);
227
0
  ZERO_STRUCT(secdesc_ctr);
228
229
0
  result = spoolss_init_spoolss_UserLevel1(mem_ctx,
230
0
             cli->printer_username,
231
0
             &level1);
232
0
  if (!W_ERROR_IS_OK(result)) {
233
0
    return result;
234
0
  }
235
236
0
  userlevel_ctr.level = 1;
237
0
  userlevel_ctr.user_info.level1 = &level1;
238
239
0
  status = dcerpc_spoolss_AddPrinterEx(b, mem_ctx,
240
0
               cli->srv_name_slash,
241
0
               info_ctr,
242
0
               &devmode_ctr,
243
0
               &secdesc_ctr,
244
0
               &userlevel_ctr,
245
0
               &handle,
246
0
               &result);
247
0
  if (!NT_STATUS_IS_OK(status)) {
248
0
    return ntstatus_to_werror(status);
249
0
  }
250
251
0
  return result;
252
0
}
253
254
/**********************************************************************
255
 convenience wrapper around rpccli_spoolss_GetPrinter
256
**********************************************************************/
257
258
WERROR rpccli_spoolss_getprinter(struct rpc_pipe_client *cli,
259
         TALLOC_CTX *mem_ctx,
260
         struct policy_handle *handle,
261
         uint32_t level,
262
         uint32_t offered,
263
         union spoolss_PrinterInfo *info)
264
0
{
265
0
  NTSTATUS status;
266
0
  WERROR werror;
267
0
  DATA_BLOB buffer;
268
0
  uint32_t needed;
269
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
270
271
0
  if (offered > 0) {
272
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
273
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
274
0
  }
275
276
0
  status = dcerpc_spoolss_GetPrinter(b, mem_ctx,
277
0
             handle,
278
0
             level,
279
0
             (offered > 0) ? &buffer : NULL,
280
0
             offered,
281
0
             info,
282
0
             &needed,
283
0
             &werror);
284
0
  if (!NT_STATUS_IS_OK(status)) {
285
0
    return ntstatus_to_werror(status);
286
0
  }
287
288
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
289
290
0
    offered = needed;
291
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
292
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
293
294
0
    status = dcerpc_spoolss_GetPrinter(b, mem_ctx,
295
0
               handle,
296
0
               level,
297
0
               &buffer,
298
0
               offered,
299
0
               info,
300
0
               &needed,
301
0
               &werror);
302
0
  }
303
0
  if (!NT_STATUS_IS_OK(status)) {
304
0
    return ntstatus_to_werror(status);
305
0
  }
306
307
0
  return werror;
308
0
}
309
310
/**********************************************************************
311
 convenience wrapper around rpccli_spoolss_GetJob
312
**********************************************************************/
313
314
WERROR rpccli_spoolss_getjob(struct rpc_pipe_client *cli,
315
           TALLOC_CTX *mem_ctx,
316
           struct policy_handle *handle,
317
           uint32_t job_id,
318
           uint32_t level,
319
           uint32_t offered,
320
           union spoolss_JobInfo *info)
321
0
{
322
0
  NTSTATUS status;
323
0
  WERROR werror;
324
0
  uint32_t needed;
325
0
  DATA_BLOB buffer;
326
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
327
328
0
  if (offered > 0) {
329
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
330
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
331
0
  }
332
333
0
  status = dcerpc_spoolss_GetJob(b, mem_ctx,
334
0
               handle,
335
0
               job_id,
336
0
               level,
337
0
               (offered > 0) ? &buffer : NULL,
338
0
               offered,
339
0
               info,
340
0
               &needed,
341
0
               &werror);
342
0
  if (!NT_STATUS_IS_OK(status)) {
343
0
    return ntstatus_to_werror(status);
344
0
  }
345
346
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
347
0
    offered = needed;
348
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
349
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
350
351
0
    status = dcerpc_spoolss_GetJob(b, mem_ctx,
352
0
                 handle,
353
0
                 job_id,
354
0
                 level,
355
0
                 &buffer,
356
0
                 offered,
357
0
                 info,
358
0
                 &needed,
359
0
                 &werror);
360
0
  }
361
0
  if (!NT_STATUS_IS_OK(status)) {
362
0
    return ntstatus_to_werror(status);
363
0
  }
364
365
0
  return werror;
366
0
}
367
368
/**********************************************************************
369
 convenience wrapper around rpccli_spoolss_EnumForms
370
**********************************************************************/
371
372
WERROR rpccli_spoolss_enumforms(struct rpc_pipe_client *cli,
373
        TALLOC_CTX *mem_ctx,
374
        struct policy_handle *handle,
375
        uint32_t level,
376
        uint32_t offered,
377
        uint32_t *count,
378
        union spoolss_FormInfo **info)
379
0
{
380
0
  NTSTATUS status;
381
0
  WERROR werror;
382
0
  uint32_t needed;
383
0
  DATA_BLOB buffer;
384
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
385
386
0
  if (offered > 0) {
387
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
388
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
389
0
  }
390
391
0
  status = dcerpc_spoolss_EnumForms(b, mem_ctx,
392
0
            handle,
393
0
            level,
394
0
            (offered > 0) ? &buffer : NULL,
395
0
            offered,
396
0
            count,
397
0
            info,
398
0
            &needed,
399
0
            &werror);
400
0
  if (!NT_STATUS_IS_OK(status)) {
401
0
    return ntstatus_to_werror(status);
402
0
  }
403
404
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
405
0
    offered = needed;
406
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
407
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
408
409
0
    status = dcerpc_spoolss_EnumForms(b, mem_ctx,
410
0
              handle,
411
0
              level,
412
0
              (offered > 0) ? &buffer : NULL,
413
0
              offered,
414
0
              count,
415
0
              info,
416
0
              &needed,
417
0
              &werror);
418
0
  }
419
0
  if (!NT_STATUS_IS_OK(status)) {
420
0
    return ntstatus_to_werror(status);
421
0
  }
422
423
0
  return werror;
424
0
}
425
426
/**********************************************************************
427
 convenience wrapper around rpccli_spoolss_EnumPrintProcessors
428
**********************************************************************/
429
430
WERROR rpccli_spoolss_enumprintprocessors(struct rpc_pipe_client *cli,
431
            TALLOC_CTX *mem_ctx,
432
            const char *servername,
433
            const char *environment,
434
            uint32_t level,
435
            uint32_t offered,
436
            uint32_t *count,
437
            union spoolss_PrintProcessorInfo **info)
438
0
{
439
0
  NTSTATUS status;
440
0
  WERROR werror;
441
0
  uint32_t needed;
442
0
  DATA_BLOB buffer;
443
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
444
445
0
  if (offered > 0) {
446
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
447
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
448
0
  }
449
450
0
  status = dcerpc_spoolss_EnumPrintProcessors(b, mem_ctx,
451
0
                servername,
452
0
                environment,
453
0
                level,
454
0
                (offered > 0) ? &buffer : NULL,
455
0
                offered,
456
0
                count,
457
0
                info,
458
0
                &needed,
459
0
                &werror);
460
0
  if (!NT_STATUS_IS_OK(status)) {
461
0
    return ntstatus_to_werror(status);
462
0
  }
463
464
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
465
0
    offered = needed;
466
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
467
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
468
469
0
    status = dcerpc_spoolss_EnumPrintProcessors(b, mem_ctx,
470
0
                  servername,
471
0
                  environment,
472
0
                  level,
473
0
                  (offered > 0) ? &buffer : NULL,
474
0
                  offered,
475
0
                  count,
476
0
                  info,
477
0
                  &needed,
478
0
                  &werror);
479
0
  }
480
0
  if (!NT_STATUS_IS_OK(status)) {
481
0
    return ntstatus_to_werror(status);
482
0
  }
483
484
0
  return werror;
485
0
}
486
487
/**********************************************************************
488
 convenience wrapper around rpccli_spoolss_EnumPrintProcessorDataTypes
489
**********************************************************************/
490
491
WERROR rpccli_spoolss_enumprintprocessordatatypes(struct rpc_pipe_client *cli,
492
              TALLOC_CTX *mem_ctx,
493
              const char *servername,
494
              const char *print_processor_name,
495
              uint32_t level,
496
              uint32_t offered,
497
              uint32_t *count,
498
              union spoolss_PrintProcDataTypesInfo **info)
499
0
{
500
0
  NTSTATUS status;
501
0
  WERROR werror;
502
0
  uint32_t needed;
503
0
  DATA_BLOB buffer;
504
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
505
506
0
  if (offered > 0) {
507
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
508
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
509
0
  }
510
511
0
  status = dcerpc_spoolss_EnumPrintProcessorDataTypes(b, mem_ctx,
512
0
                  servername,
513
0
                  print_processor_name,
514
0
                  level,
515
0
                  (offered > 0) ? &buffer : NULL,
516
0
                  offered,
517
0
                  count,
518
0
                  info,
519
0
                  &needed,
520
0
                  &werror);
521
0
  if (!NT_STATUS_IS_OK(status)) {
522
0
    return ntstatus_to_werror(status);
523
0
  }
524
525
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
526
0
    offered = needed;
527
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
528
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
529
530
0
    status = dcerpc_spoolss_EnumPrintProcessorDataTypes(b, mem_ctx,
531
0
                    servername,
532
0
                    print_processor_name,
533
0
                    level,
534
0
                    (offered > 0) ? &buffer : NULL,
535
0
                    offered,
536
0
                    count,
537
0
                    info,
538
0
                    &needed,
539
0
                    &werror);
540
0
  }
541
0
  if (!NT_STATUS_IS_OK(status)) {
542
0
    return ntstatus_to_werror(status);
543
0
  }
544
545
0
  return werror;
546
0
}
547
548
/**********************************************************************
549
 convenience wrapper around rpccli_spoolss_EnumPorts
550
**********************************************************************/
551
552
WERROR rpccli_spoolss_enumports(struct rpc_pipe_client *cli,
553
        TALLOC_CTX *mem_ctx,
554
        const char *servername,
555
        uint32_t level,
556
        uint32_t offered,
557
        uint32_t *count,
558
        union spoolss_PortInfo **info)
559
0
{
560
0
  NTSTATUS status;
561
0
  WERROR werror;
562
0
  uint32_t needed;
563
0
  DATA_BLOB buffer;
564
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
565
566
0
  if (offered > 0) {
567
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
568
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
569
0
  }
570
571
0
  status = dcerpc_spoolss_EnumPorts(b, mem_ctx,
572
0
            servername,
573
0
            level,
574
0
            (offered > 0) ? &buffer : NULL,
575
0
            offered,
576
0
            count,
577
0
            info,
578
0
            &needed,
579
0
            &werror);
580
0
  if (!NT_STATUS_IS_OK(status)) {
581
0
    return ntstatus_to_werror(status);
582
0
  }
583
584
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
585
0
    offered = needed;
586
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
587
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
588
589
0
    status = dcerpc_spoolss_EnumPorts(b, mem_ctx,
590
0
              servername,
591
0
              level,
592
0
              (offered > 0) ? &buffer : NULL,
593
0
              offered,
594
0
              count,
595
0
              info,
596
0
              &needed,
597
0
              &werror);
598
0
  }
599
0
  if (!NT_STATUS_IS_OK(status)) {
600
0
    return ntstatus_to_werror(status);
601
0
  }
602
603
0
  return werror;
604
0
}
605
606
/**********************************************************************
607
 convenience wrapper around rpccli_spoolss_EnumMonitors
608
**********************************************************************/
609
610
WERROR rpccli_spoolss_enummonitors(struct rpc_pipe_client *cli,
611
           TALLOC_CTX *mem_ctx,
612
           const char *servername,
613
           uint32_t level,
614
           uint32_t offered,
615
           uint32_t *count,
616
           union spoolss_MonitorInfo **info)
617
0
{
618
0
  NTSTATUS status;
619
0
  WERROR werror;
620
0
  uint32_t needed;
621
0
  DATA_BLOB buffer;
622
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
623
624
0
  if (offered > 0) {
625
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
626
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
627
0
  }
628
629
0
  status = dcerpc_spoolss_EnumMonitors(b, mem_ctx,
630
0
               servername,
631
0
               level,
632
0
               (offered > 0) ? &buffer : NULL,
633
0
               offered,
634
0
               count,
635
0
               info,
636
0
               &needed,
637
0
               &werror);
638
0
  if (!NT_STATUS_IS_OK(status)) {
639
0
    return ntstatus_to_werror(status);
640
0
  }
641
642
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
643
0
    offered = needed;
644
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
645
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
646
647
0
    status = dcerpc_spoolss_EnumMonitors(b, mem_ctx,
648
0
                 servername,
649
0
                 level,
650
0
                 (offered > 0) ? &buffer : NULL,
651
0
                 offered,
652
0
                 count,
653
0
                 info,
654
0
                 &needed,
655
0
                 &werror);
656
0
  }
657
0
  if (!NT_STATUS_IS_OK(status)) {
658
0
    return ntstatus_to_werror(status);
659
0
  }
660
661
0
  return werror;
662
0
}
663
664
/**********************************************************************
665
 convenience wrapper around rpccli_spoolss_EnumJobs
666
**********************************************************************/
667
668
WERROR rpccli_spoolss_enumjobs(struct rpc_pipe_client *cli,
669
             TALLOC_CTX *mem_ctx,
670
             struct policy_handle *handle,
671
             uint32_t firstjob,
672
             uint32_t numjobs,
673
             uint32_t level,
674
             uint32_t offered,
675
             uint32_t *count,
676
             union spoolss_JobInfo **info)
677
0
{
678
0
  NTSTATUS status;
679
0
  WERROR werror;
680
0
  uint32_t needed;
681
0
  DATA_BLOB buffer;
682
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
683
684
0
  if (offered > 0) {
685
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
686
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
687
0
  }
688
689
0
  status = dcerpc_spoolss_EnumJobs(b, mem_ctx,
690
0
           handle,
691
0
           firstjob,
692
0
           numjobs,
693
0
           level,
694
0
           (offered > 0) ? &buffer : NULL,
695
0
           offered,
696
0
           count,
697
0
           info,
698
0
           &needed,
699
0
           &werror);
700
0
  if (!NT_STATUS_IS_OK(status)) {
701
0
    return ntstatus_to_werror(status);
702
0
  }
703
704
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
705
0
    offered = needed;
706
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
707
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
708
709
0
    status = dcerpc_spoolss_EnumJobs(b, mem_ctx,
710
0
             handle,
711
0
             firstjob,
712
0
             numjobs,
713
0
             level,
714
0
             (offered > 0) ? &buffer : NULL,
715
0
             offered,
716
0
             count,
717
0
             info,
718
0
             &needed,
719
0
             &werror);
720
0
  }
721
0
  if (!NT_STATUS_IS_OK(status)) {
722
0
    return ntstatus_to_werror(status);
723
0
  }
724
725
0
  return werror;
726
0
}
727
728
/**********************************************************************
729
 convenience wrapper around rpccli_spoolss_EnumPrinterDrivers
730
**********************************************************************/
731
732
WERROR rpccli_spoolss_enumprinterdrivers(struct rpc_pipe_client *cli,
733
           TALLOC_CTX *mem_ctx,
734
           const char *server,
735
           const char *environment,
736
           uint32_t level,
737
           uint32_t offered,
738
           uint32_t *count,
739
           union spoolss_DriverInfo **info)
740
0
{
741
0
  NTSTATUS status;
742
0
  WERROR werror;
743
0
  uint32_t needed;
744
0
  DATA_BLOB buffer;
745
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
746
747
0
  if (offered > 0) {
748
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
749
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
750
0
  }
751
752
0
  status = dcerpc_spoolss_EnumPrinterDrivers(b, mem_ctx,
753
0
               server,
754
0
               environment,
755
0
               level,
756
0
               (offered > 0) ? &buffer : NULL,
757
0
               offered,
758
0
               count,
759
0
               info,
760
0
               &needed,
761
0
               &werror);
762
0
  if (!NT_STATUS_IS_OK(status)) {
763
0
    return ntstatus_to_werror(status);
764
0
  }
765
766
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
767
0
    offered = needed;
768
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
769
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
770
771
0
    status = dcerpc_spoolss_EnumPrinterDrivers(b, mem_ctx,
772
0
               server,
773
0
               environment,
774
0
               level,
775
0
               (offered > 0) ? &buffer : NULL,
776
0
               offered,
777
0
               count,
778
0
               info,
779
0
               &needed,
780
0
               &werror);
781
0
  }
782
0
  if (!NT_STATUS_IS_OK(status)) {
783
0
    return ntstatus_to_werror(status);
784
0
  }
785
786
0
  return werror;
787
0
}
788
789
/**********************************************************************
790
 convenience wrapper around rpccli_spoolss_EnumPrinters
791
**********************************************************************/
792
793
WERROR rpccli_spoolss_enumprinters(struct rpc_pipe_client *cli,
794
           TALLOC_CTX *mem_ctx,
795
           uint32_t flags,
796
           const char *server,
797
           uint32_t level,
798
           uint32_t offered,
799
           uint32_t *count,
800
           union spoolss_PrinterInfo **info)
801
0
{
802
0
  NTSTATUS status;
803
0
  WERROR werror;
804
0
  uint32_t needed;
805
0
  DATA_BLOB buffer;
806
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
807
808
0
  if (offered > 0) {
809
0
    buffer = data_blob_talloc_zero(mem_ctx, offered);
810
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
811
0
  }
812
813
0
  status = dcerpc_spoolss_EnumPrinters(b, mem_ctx,
814
0
               flags,
815
0
               server,
816
0
               level,
817
0
               (offered > 0) ? &buffer : NULL,
818
0
               offered,
819
0
               count,
820
0
               info,
821
0
               &needed,
822
0
               &werror);
823
0
  if (!NT_STATUS_IS_OK(status)) {
824
0
    return ntstatus_to_werror(status);
825
0
  }
826
827
0
  if (W_ERROR_EQUAL(werror, WERR_INSUFFICIENT_BUFFER)) {
828
0
    offered = needed;
829
0
    buffer = data_blob_talloc_zero(mem_ctx, needed);
830
0
    W_ERROR_HAVE_NO_MEMORY(buffer.data);
831
832
0
    status = dcerpc_spoolss_EnumPrinters(b, mem_ctx,
833
0
                 flags,
834
0
                 server,
835
0
                 level,
836
0
                 (offered > 0) ? &buffer : NULL,
837
0
                 offered,
838
0
                 count,
839
0
                 info,
840
0
                 &needed,
841
0
                 &werror);
842
0
  }
843
0
  if (!NT_STATUS_IS_OK(status)) {
844
0
    return ntstatus_to_werror(status);
845
0
  }
846
847
0
  return werror;
848
0
}
849
850
/**********************************************************************
851
 convenience wrapper around rpccli_spoolss_GetPrinterData
852
**********************************************************************/
853
854
WERROR rpccli_spoolss_getprinterdata(struct rpc_pipe_client *cli,
855
             TALLOC_CTX *mem_ctx,
856
             struct policy_handle *handle,
857
             const char *value_name,
858
             uint32_t offered,
859
             enum winreg_Type *type,
860
             uint32_t *needed_p,
861
             uint8_t **data_p)
862
0
{
863
0
  NTSTATUS status;
864
0
  WERROR werror;
865
0
  uint32_t needed;
866
0
  uint8_t *data;
867
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
868
869
0
  data = talloc_zero_array(mem_ctx, uint8_t, offered);
870
0
  W_ERROR_HAVE_NO_MEMORY(data);
871
872
0
  status = dcerpc_spoolss_GetPrinterData(b, mem_ctx,
873
0
                 handle,
874
0
                 value_name,
875
0
                 type,
876
0
                 data,
877
0
                 offered,
878
0
                 &needed,
879
0
                 &werror);
880
0
  if (!NT_STATUS_IS_OK(status)) {
881
0
    return ntstatus_to_werror(status);
882
0
  }
883
884
0
  if (W_ERROR_EQUAL(werror, WERR_MORE_DATA)) {
885
0
    offered = needed;
886
0
    data = talloc_zero_array(mem_ctx, uint8_t, offered);
887
0
    W_ERROR_HAVE_NO_MEMORY(data);
888
889
0
    status = dcerpc_spoolss_GetPrinterData(b, mem_ctx,
890
0
                   handle,
891
0
                   value_name,
892
0
                   type,
893
0
                   data,
894
0
                   offered,
895
0
                   &needed,
896
0
                   &werror);
897
0
  }
898
0
  if (!NT_STATUS_IS_OK(status)) {
899
0
    return ntstatus_to_werror(status);
900
0
  }
901
902
0
  *data_p = data;
903
0
  *needed_p = needed;
904
905
0
  return werror;
906
0
}
907
908
/**********************************************************************
909
 convenience wrapper around rpccli_spoolss_EnumPrinterKey
910
**********************************************************************/
911
912
WERROR rpccli_spoolss_enumprinterkey(struct rpc_pipe_client *cli,
913
             TALLOC_CTX *mem_ctx,
914
             struct policy_handle *handle,
915
             const char *key_name,
916
             const char ***key_buffer,
917
             uint32_t offered)
918
0
{
919
0
  NTSTATUS status;
920
0
  WERROR werror;
921
0
  uint32_t needed;
922
0
  union spoolss_KeyNames _key_buffer;
923
0
  uint32_t _ndr_size;
924
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
925
926
0
  status = dcerpc_spoolss_EnumPrinterKey(b, mem_ctx,
927
0
                 handle,
928
0
                 key_name,
929
0
                 &_ndr_size,
930
0
                 &_key_buffer,
931
0
                 offered,
932
0
                 &needed,
933
0
                 &werror);
934
0
  if (!NT_STATUS_IS_OK(status)) {
935
0
    return ntstatus_to_werror(status);
936
0
  }
937
938
0
  if (W_ERROR_EQUAL(werror, WERR_MORE_DATA)) {
939
0
    offered = needed;
940
0
    status = dcerpc_spoolss_EnumPrinterKey(b, mem_ctx,
941
0
                   handle,
942
0
                   key_name,
943
0
                   &_ndr_size,
944
0
                   &_key_buffer,
945
0
                   offered,
946
0
                   &needed,
947
0
                   &werror);
948
0
  }
949
0
  if (!NT_STATUS_IS_OK(status)) {
950
0
    return ntstatus_to_werror(status);
951
0
  }
952
953
0
  *key_buffer = _key_buffer.string_array;
954
955
0
  return werror;
956
0
}
957
958
/**********************************************************************
959
 convenience wrapper around rpccli_spoolss_EnumPrinterDataEx
960
**********************************************************************/
961
962
WERROR rpccli_spoolss_enumprinterdataex(struct rpc_pipe_client *cli,
963
          TALLOC_CTX *mem_ctx,
964
          struct policy_handle *handle,
965
          const char *key_name,
966
          uint32_t offered,
967
          uint32_t *count,
968
          struct spoolss_PrinterEnumValues **info)
969
0
{
970
0
  NTSTATUS status;
971
0
  WERROR werror;
972
0
  uint32_t needed;
973
0
  struct dcerpc_binding_handle *b = cli->binding_handle;
974
975
0
  status = dcerpc_spoolss_EnumPrinterDataEx(b, mem_ctx,
976
0
              handle,
977
0
              key_name,
978
0
              offered,
979
0
              count,
980
0
              info,
981
0
              &needed,
982
0
              &werror);
983
0
  if (!NT_STATUS_IS_OK(status)) {
984
0
    return ntstatus_to_werror(status);
985
0
  }
986
987
0
  if (W_ERROR_EQUAL(werror, WERR_MORE_DATA)) {
988
0
    offered = needed;
989
990
0
    status = dcerpc_spoolss_EnumPrinterDataEx(b, mem_ctx,
991
0
                handle,
992
0
                key_name,
993
0
                offered,
994
0
                count,
995
0
                info,
996
0
                &needed,
997
0
                &werror);
998
0
  }
999
0
  if (!NT_STATUS_IS_OK(status)) {
1000
0
    return ntstatus_to_werror(status);
1001
0
  }
1002
1003
0
  return werror;
1004
0
}