spoolss: fix relative pointers in ndr_push_spoolss_DriverInfo101.
[abartlet/samba.git/.git] / librpc / ndr / ndr_spoolss_buf.c
index 97624d3a1248d927cad65a07bdb20404d2895531..0012ce3e2acbb33e2dc24a68a20fb122d1ac0e6e 100644 (file)
@@ -5,6 +5,7 @@
 
    Copyright (C) Andrew Tridgell 2003
    Copyright (C) Tim Potter 2003
+   Copyright (C) Guenther Deschner 2009
 
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
 } while (0)
 
 /* TODO: set _ndr_info->flags correct */
-#define NDR_SPOOLSS_SIZE_ENUM(fn) do { \
+#define NDR_SPOOLSS_SIZE_ENUM_LEVEL(fn) do { \
        struct __##fn __r;\
        DATA_BLOB _data_blob_info;\
        struct ndr_push *_ndr_info = ndr_push_init_ctx(mem_ctx, iconv_convenience);\
        return _data_blob_info.length;\
 } while(0)
 
+/* TODO: set _ndr_info->flags correct */
+#define NDR_SPOOLSS_SIZE_ENUM(fn) do { \
+       struct __##fn __r;\
+       DATA_BLOB _data_blob_info;\
+       struct ndr_push *_ndr_info = ndr_push_init_ctx(mem_ctx, iconv_convenience);\
+       if (!_ndr_info) return 0;\
+       _ndr_info->flags|=0;\
+       __r.in.count    = count;\
+       __r.out.info    = info;\
+       _NDR_CHECK_UINT32(ndr_push___##fn(_ndr_info, NDR_OUT, &__r)); \
+       _data_blob_info = ndr_push_blob(_ndr_info);\
+       return _data_blob_info.length;\
+} while(0)
+
+
 /*
   spoolss_EnumPrinters
 */
@@ -216,7 +232,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumPrinters(struct ndr_pull *ndr, int flags,
 
 uint32_t ndr_size_spoolss_EnumPrinters_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_PrinterInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPrinters);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumPrinters);
 }
 
 /*
@@ -252,7 +268,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumJobs(struct ndr_pull *ndr, int flags, str
 
 uint32_t ndr_size_spoolss_EnumJobs_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_JobInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumJobs);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumJobs);
 }
 
 /*
@@ -284,7 +300,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumPrinterDrivers(struct ndr_pull *ndr, int
 
 uint32_t ndr_size_spoolss_EnumPrinterDrivers_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_DriverInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPrinterDrivers);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumPrinterDrivers);
 }
 
 /*
@@ -312,7 +328,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumForms(struct ndr_pull *ndr, int flags, st
 
 uint32_t ndr_size_spoolss_EnumForms_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_FormInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumForms);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumForms);
 }
 
 /*
@@ -340,7 +356,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumPorts(struct ndr_pull *ndr, int flags, st
 
 uint32_t ndr_size_spoolss_EnumPorts_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_PortInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPorts);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumPorts);
 }
 
 /*
@@ -368,7 +384,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumMonitors(struct ndr_pull *ndr, int flags,
 
 uint32_t ndr_size_spoolss_EnumMonitors_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience, uint32_t level, uint32_t count, union spoolss_MonitorInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumMonitors);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumMonitors);
 }
 
 /*
@@ -401,7 +417,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumPrintProcessors(struct ndr_pull *ndr, int
 uint32_t ndr_size_spoolss_EnumPrintProcessors_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience,
                                                   uint32_t level, uint32_t count, union spoolss_PrintProcessorInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPrintProcessors);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumPrintProcessors);
 }
 
 /*
@@ -434,7 +450,7 @@ enum ndr_err_code ndr_pull_spoolss_EnumPrintProcDataTypes(struct ndr_pull *ndr,
 uint32_t ndr_size_spoolss_EnumPrintProcDataTypes_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience,
                                                      uint32_t level, uint32_t count, union spoolss_PrintProcDataTypesInfo *info)
 {
-       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPrintProcDataTypes);
+       NDR_SPOOLSS_SIZE_ENUM_LEVEL(spoolss_EnumPrintProcDataTypes);
 }
 
 /*
@@ -531,6 +547,12 @@ enum ndr_err_code ndr_pull_spoolss_EnumPrinterDataEx(struct ndr_pull *ndr, int f
        return NDR_ERR_SUCCESS;
 }
 
+uint32_t ndr_size_spoolss_EnumPrinterDataEx_info(TALLOC_CTX *mem_ctx, struct smb_iconv_convenience *iconv_convenience,
+                                                uint32_t count, struct spoolss_PrinterEnumValues *info)
+{
+       NDR_SPOOLSS_SIZE_ENUM(spoolss_EnumPrinterDataEx);
+}
+
 /*
   spoolss_GetPrinterData
 */
@@ -671,6 +693,153 @@ enum ndr_err_code ndr_push_spoolss_SetPrinterData(struct ndr_push *ndr, int flag
        return NDR_ERR_SUCCESS;
 }
 
+/*
+  spoolss_GetPrinterDataEx
+*/
+enum ndr_err_code ndr_push_spoolss_GetPrinterDataEx(struct ndr_push *ndr, int flags, const struct spoolss_GetPrinterDataEx *r)
+{
+       struct _spoolss_GetPrinterDataEx _r;
+       if (flags & NDR_IN) {
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.offered   = r->in.offered;
+               NDR_CHECK(ndr_push__spoolss_GetPrinterDataEx(ndr, flags, &_r));
+       }
+       if (flags & NDR_OUT) {
+               struct ndr_push *_ndr_info;
+               DATA_BLOB blob = data_blob(NULL, 0);
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.offered   = r->in.offered;
+               _r.out.type     = r->out.type;
+               _r.out.data     = &blob;
+               _r.out.needed   = r->out.needed;
+               _r.out.result   = r->out.result;
+               {
+                       struct __spoolss_GetPrinterDataEx __r;
+                       DATA_BLOB _blob;
+                       _ndr_info = ndr_push_init_ctx(ndr, ndr->iconv_convenience);
+                       NDR_ERR_HAVE_NO_MEMORY(_ndr_info);
+                       _ndr_info->flags= ndr->flags;
+                       __r.in.type     = *r->out.type;
+                       __r.out.data    = r->out.data;
+                       NDR_CHECK(ndr_push___spoolss_GetPrinterDataEx(_ndr_info, flags, &__r));
+                       if (r->in.offered > _ndr_info->offset) {
+                               uint32_t _padding_len = r->in.offered - _ndr_info->offset;
+                               NDR_CHECK(ndr_push_zero(_ndr_info, _padding_len));
+                       }
+                       _blob = ndr_push_blob(_ndr_info);
+                       _r.out.data = &_blob;
+               }
+               NDR_CHECK(ndr_push__spoolss_GetPrinterDataEx(ndr, flags, &_r));
+       }
+       return NDR_ERR_SUCCESS;
+}
+
+enum ndr_err_code ndr_pull_spoolss_GetPrinterDataEx(struct ndr_pull *ndr, int flags, struct spoolss_GetPrinterDataEx *r)
+{
+       struct _spoolss_GetPrinterDataEx _r;
+       if (flags & NDR_IN) {
+               DATA_BLOB blob = data_blob(NULL,0);
+               ZERO_STRUCT(r->out);
+
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.offered   = r->in.offered;
+               _r.out.type     = r->out.type;
+               _r.out.data     = &blob;
+               _r.out.needed   = r->out.needed;
+               NDR_CHECK(ndr_pull__spoolss_GetPrinterDataEx(ndr, flags, &_r));
+               r->in.handle    = _r.in.handle;
+               r->in.key_name  = _r.in.key_name;
+               r->in.value_name= _r.in.value_name;
+               r->in.offered   = _r.in.offered;
+               r->out.needed   = _r.out.needed;
+       }
+       if (flags & NDR_OUT) {
+               DATA_BLOB blob = data_blob_talloc(ndr,NULL,0);
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.offered   = r->in.offered;
+               _r.out.type     = r->out.type;
+               _r.out.data     = &blob;
+               _r.out.needed   = r->out.needed;
+               _r.out.result   = r->out.result;
+               NDR_CHECK(ndr_pull__spoolss_GetPrinterDataEx(ndr, flags, &_r));
+               r->out.type     = _r.out.type;
+               if (ndr->flags & LIBNDR_FLAG_REF_ALLOC) {
+                       NDR_PULL_ALLOC(ndr, r->out.data);
+               }
+               ZERO_STRUCTP(r->out.data);
+               r->out.needed   = _r.out.needed;
+               r->out.result   = _r.out.result;
+               if (_r.out.data && _r.out.data->length != r->in.offered) {
+                       return ndr_pull_error(ndr, NDR_ERR_BUFSIZE,
+                               "SPOOLSS Buffer: r->in.offered[%u] doesn't match length of out buffer[%u]",
+                               (unsigned)r->in.offered, (unsigned)_r.out.data->length);
+               }
+               if (_r.out.data && _r.out.data->length > 0 && *r->out.needed <= _r.out.data->length) {
+                       struct __spoolss_GetPrinterDataEx __r;
+                       struct ndr_pull *_ndr_data = ndr_pull_init_blob(_r.out.data, ndr, ndr->iconv_convenience);
+                       NDR_ERR_HAVE_NO_MEMORY(_ndr_data);
+                       _ndr_data->flags= ndr->flags;
+                       __r.in.type     = *r->out.type;
+                       __r.out.data    = r->out.data;
+                       NDR_CHECK(ndr_pull___spoolss_GetPrinterDataEx(_ndr_data, flags, &__r));
+                       r->out.data     = __r.out.data;
+               } else {
+                       *r->out.type    = REG_NONE;
+               }
+       }
+       return NDR_ERR_SUCCESS;
+}
+
+/*
+  spoolss_SetPrinterDataEx
+*/
+enum ndr_err_code ndr_push_spoolss_SetPrinterDataEx(struct ndr_push *ndr, int flags, const struct spoolss_SetPrinterDataEx *r)
+{
+       struct _spoolss_SetPrinterDataEx _r;
+       if (flags & NDR_IN) {
+               struct ndr_push *_ndr_data;
+               struct __spoolss_SetPrinterDataEx __r;
+               DATA_BLOB _data_blob_data;
+
+               _ndr_data = ndr_push_init_ctx(ndr, ndr->iconv_convenience);
+               NDR_ERR_HAVE_NO_MEMORY(_ndr_data);
+               _ndr_data->flags= ndr->flags;
+
+               __r.in.type     = r->in.type;
+               __r.out.data    = discard_const_p(union spoolss_PrinterData, &r->in.data);
+               NDR_CHECK(ndr_push___spoolss_SetPrinterDataEx(_ndr_data, NDR_OUT, &__r));
+               _data_blob_data = ndr_push_blob(_ndr_data);
+
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.type      = r->in.type;
+               _r.in.data      = _data_blob_data;
+               _r.in._offered  = _data_blob_data.length;
+               _r.out.result   = r->out.result;
+               NDR_CHECK(ndr_push__spoolss_SetPrinterDataEx(ndr, flags, &_r));
+       }
+       if (flags & NDR_OUT) {
+               _r.in.handle    = r->in.handle;
+               _r.in.key_name  = r->in.key_name;
+               _r.in.value_name= r->in.value_name;
+               _r.in.type      = r->in.type;
+               _r.in.data      = data_blob(NULL,0),
+               _r.in._offered  = r->in._offered;
+               _r.out.result   = r->out.result;
+               NDR_CHECK(ndr_push__spoolss_SetPrinterDataEx(ndr, flags, &_r));
+       }
+       return NDR_ERR_SUCCESS;
+}
+
 uint32_t _ndr_size_spoolss_DeviceMode(struct spoolss_DeviceMode *devmode, struct smb_iconv_convenience *ic, uint32_t flags)
 {
        if (!devmode) return 0;
@@ -753,14 +922,16 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        NDR_CHECK(ndr_push_relative_ptr1(ndr, r->provider));
                        ndr->flags = _flags_save_string;
                }
+               NDR_CHECK(ndr_push_trailer_align(ndr, 8));
        }
        if (ndr_flags & NDR_BUFFERS) {
                {
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->driver_name) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->driver_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->driver_name));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->driver_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->driver_name));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -768,15 +939,16 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->architecture) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->architecture));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->architecture));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->architecture));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->architecture));
                        }
                        ndr->flags = _flags_save_string;
                }
                if (r->file_info) {
-                       NDR_CHECK(ndr_push_relative_ptr2(ndr, r->file_info));
+                       NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->file_info));
 #if 0
-                       NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r->file_count));
+                       NDR_CHECK(ndr_push_uint3264(ndr, NDR_SCALARS, r->file_count));
 #endif
                        for (cntr_file_info_1 = 0; cntr_file_info_1 < r->file_count; cntr_file_info_1++) {
                                NDR_CHECK(ndr_push_spoolss_DriverFileInfo(ndr, NDR_SCALARS, &r->file_info[cntr_file_info_1]));
@@ -784,13 +956,15 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        for (cntr_file_info_1 = 0; cntr_file_info_1 < r->file_count; cntr_file_info_1++) {
                                NDR_CHECK(ndr_push_spoolss_DriverFileInfo(ndr, NDR_BUFFERS, &r->file_info[cntr_file_info_1]));
                        }
+                       NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->file_info));
                }
                {
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->monitor_name) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->monitor_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->monitor_name));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->monitor_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->monitor_name));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -798,8 +972,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->default_datatype) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->default_datatype));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->default_datatype));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->default_datatype));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->default_datatype));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -807,8 +982,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string_array = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->previous_names) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->previous_names));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->previous_names));
                                NDR_CHECK(ndr_push_string_array(ndr, NDR_SCALARS, r->previous_names));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->previous_names));
                        }
                        ndr->flags = _flags_save_string_array;
                }
@@ -816,8 +992,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->manufacturer_name) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->manufacturer_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->manufacturer_name));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->manufacturer_name));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->manufacturer_name));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -825,8 +1002,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->manufacturer_url) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->manufacturer_url));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->manufacturer_url));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->manufacturer_url));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->manufacturer_url));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -834,8 +1012,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->hardware_id) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->hardware_id));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->hardware_id));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->hardware_id));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->hardware_id));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -843,8 +1022,9 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_DriverInfo101(struct ndr_push *ndr,
                        uint32_t _flags_save_string = ndr->flags;
                        ndr_set_flags(&ndr->flags, LIBNDR_FLAG_STR_NULLTERM);
                        if (r->provider) {
-                               NDR_CHECK(ndr_push_relative_ptr2(ndr, r->provider));
+                               NDR_CHECK(ndr_push_relative_ptr2_start(ndr, r->provider));
                                NDR_CHECK(ndr_push_string(ndr, NDR_SCALARS, r->provider));
+                               NDR_CHECK(ndr_push_relative_ptr2_end(ndr, r->provider));
                        }
                        ndr->flags = _flags_save_string;
                }
@@ -997,6 +1177,7 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                        }
                        ndr->flags = _flags_save_string;
                }
+               NDR_CHECK(ndr_pull_trailer_align(ndr, 8));
        }
        if (ndr_flags & NDR_BUFFERS) {
                {
@@ -1010,6 +1191,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->driver_name, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->driver_name));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_driver_name_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1025,6 +1209,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->architecture, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->architecture));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_architecture_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1051,6 +1238,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                        }
                        NDR_PULL_SET_MEM_CTX(ndr, _mem_save_file_info_1, 0);
                        NDR_PULL_SET_MEM_CTX(ndr, _mem_save_file_info_0, 0);
+                       if (ndr->offset > ndr->relative_highest_offset) {
+                               ndr->relative_highest_offset = ndr->offset;
+                       }
                        ndr->offset = _relative_save_offset;
                }
                {
@@ -1064,6 +1254,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->monitor_name, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->monitor_name));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_monitor_name_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1079,6 +1272,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->default_datatype, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->default_datatype));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_default_datatype_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1094,6 +1290,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->previous_names, 0);
                                NDR_CHECK(ndr_pull_string_array(ndr, NDR_SCALARS, &r->previous_names));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_previous_names_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string_array;
@@ -1109,6 +1308,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->manufacturer_name, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->manufacturer_name));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_manufacturer_name_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1124,6 +1326,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->manufacturer_url, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->manufacturer_url));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_manufacturer_url_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1139,6 +1344,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->hardware_id, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->hardware_id));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_hardware_id_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1154,6 +1362,9 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
                                NDR_PULL_SET_MEM_CTX(ndr, r->provider, 0);
                                NDR_CHECK(ndr_pull_string(ndr, NDR_SCALARS, &r->provider));
                                NDR_PULL_SET_MEM_CTX(ndr, _mem_save_provider_0, 0);
+                               if (ndr->offset > ndr->relative_highest_offset) {
+                                       ndr->relative_highest_offset = ndr->offset;
+                               }
                                ndr->offset = _relative_save_offset;
                        }
                        ndr->flags = _flags_save_string;
@@ -1164,3 +1375,33 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_DriverInfo101(struct ndr_pull *ndr,
        }
        return NDR_ERR_SUCCESS;
 }
+
+void ndr_print_spoolss_Field(struct ndr_print *ndr, const char *name, const union spoolss_Field *r)
+{
+       int level;
+       level = ndr_print_get_switch_value(ndr, r);
+       ndr_print_union(ndr, name, level, "spoolss_Field");
+       switch (level) {
+               case PRINTER_NOTIFY_TYPE:
+                       ndr_print_spoolss_PrintNotifyField(ndr, "field", r->field);
+               break;
+
+               case JOB_NOTIFY_TYPE:
+                       ndr_print_spoolss_JobNotifyField(ndr, "field", r->field);
+               break;
+
+               default:
+                       ndr_print_uint16(ndr, "field", r->field);
+               break;
+
+       }
+}
+
+_PUBLIC_ size_t ndr_size_spoolss_PrinterData(const union spoolss_PrinterData *r, uint32_t level, struct smb_iconv_convenience *ic, int flags)
+{
+       if (!r) {
+               return 0;
+       }
+       return ndr_size_union(r, flags, level, (ndr_push_flags_fn_t)ndr_push_spoolss_PrinterData, ic);
+}
+