libcli/security Provide a common, top level libcli/security/security.h
[sfrench/samba-autobuild/.git] / source3 / rpc_server / srv_spoolss_util.c
index ab6be2f69d02c9345a071b70111bdc3a215408d4..714567619d126c7c1b609d3dda8aebd5ef25458c 100644 (file)
@@ -27,6 +27,8 @@
 #include "../librpc/gen_ndr/cli_winreg.h"
 #include "../librpc/gen_ndr/ndr_security.h"
 #include "secrets.h"
+#include "rpc_server/rpc_ncacn_np.h"
+#include "../libcli/security/security.h"
 
 #define TOP_LEVEL_PRINT_KEY "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Print"
 #define TOP_LEVEL_PRINT_PRINTERS_KEY TOP_LEVEL_PRINT_KEY "\\Printers"
@@ -223,7 +225,7 @@ static uint32_t winreg_printer_rev_changeid(void)
  *
  * @param[in]  server_info   The supplied server info.
  *
- * @param[out] winreg_pipe   A pointer for the winreg rpc client pipe.
+ * @param[out] binding_handle A pointer for the winreg dcerpc binding handle.
  *
  * @param[in]  path          The path to the key to open.
  *
@@ -242,8 +244,9 @@ static uint32_t winreg_printer_rev_changeid(void)
  *                           code if something gone wrong.
  */
 static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
-                             struct auth_serversupplied_info *server_info,
-                             struct rpc_pipe_client **winreg_pipe,
+                             const struct auth_serversupplied_info *server_info,
+                             struct messaging_context *msg_ctx,
+                             struct dcerpc_binding_handle **winreg_binding_handle,
                              const char *path,
                              const char *key,
                              bool create_key,
@@ -251,24 +254,29 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
                              struct policy_handle *hive_handle,
                              struct policy_handle *key_handle)
 {
-       struct rpc_pipe_client *pipe_handle;
+       static struct client_address client_id;
+       struct dcerpc_binding_handle *binding_handle;
        struct winreg_String wkey, wkeyclass;
        char *keyname;
        NTSTATUS status;
        WERROR result = WERR_OK;
 
-       /* create winreg connection */
-       status = rpc_pipe_open_internal(mem_ctx,
-                                       &ndr_table_winreg.syntax_id,
-                                       server_info,
-                                       &pipe_handle);
+       strlcpy(client_id.addr, "127.0.0.1", sizeof(client_id.addr));
+       client_id.name = "127.0.0.1";
+
+       status = rpcint_binding_handle(mem_ctx,
+                                      &ndr_table_winreg,
+                                      &client_id,
+                                      server_info,
+                                      msg_ctx,
+                                      &binding_handle);
        if (!NT_STATUS_IS_OK(status)) {
-               DEBUG(0, ("winreg_printer_openkey: Could not connect to winreg_pipe: %s\n",
+               DEBUG(0, ("winreg_printer_openkey: Could not connect to winreg pipe: %s\n",
                          nt_errstr(status)));
                return ntstatus_to_werror(status);
        }
 
-       status = rpccli_winreg_OpenHKLM(pipe_handle,
+       status = dcerpc_winreg_OpenHKLM(binding_handle,
                                        mem_ctx,
                                        NULL,
                                        access_mask,
@@ -277,12 +285,15 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_openkey: Could not open HKLM hive: %s\n",
                          nt_errstr(status)));
-               talloc_free(pipe_handle);
-               if (!W_ERROR_IS_OK(result)) {
-                       return result;
-               }
+               talloc_free(binding_handle);
                return ntstatus_to_werror(status);
        }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(0, ("winreg_printer_openkey: Could not open HKLM hive: %s\n",
+                         win_errstr(result)));
+               talloc_free(binding_handle);
+               return result;
+       }
 
        if (key && *key) {
                keyname = talloc_asprintf(mem_ctx, "%s\\%s", path, key);
@@ -290,7 +301,7 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
                keyname = talloc_strdup(mem_ctx, path);
        }
        if (keyname == NULL) {
-               talloc_free(pipe_handle);
+               talloc_free(binding_handle);
                return WERR_NOMEM;
        }
 
@@ -303,7 +314,7 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
                ZERO_STRUCT(wkeyclass);
                wkeyclass.name = "";
 
-               status = rpccli_winreg_CreateKey(pipe_handle,
+               status = dcerpc_winreg_CreateKey(binding_handle,
                                                 mem_ctx,
                                                 hive_handle,
                                                 wkey,
@@ -326,7 +337,7 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
                                break;
                }
        } else {
-               status = rpccli_winreg_OpenKey(pipe_handle,
+               status = dcerpc_winreg_OpenKey(binding_handle,
                                               mem_ctx,
                                               hive_handle,
                                               wkey,
@@ -336,14 +347,15 @@ static WERROR winreg_printer_openkey(TALLOC_CTX *mem_ctx,
                                               &result);
        }
        if (!NT_STATUS_IS_OK(status)) {
-               talloc_free(pipe_handle);
-               if (!W_ERROR_IS_OK(result)) {
-                       return result;
-               }
+               talloc_free(binding_handle);
                return ntstatus_to_werror(status);
        }
+       if (!W_ERROR_IS_OK(result)) {
+               talloc_free(binding_handle);
+               return result;
+       }
 
-       *winreg_pipe = pipe_handle;
+       *winreg_binding_handle = binding_handle;
 
        return WERR_OK;
 }
@@ -368,7 +380,7 @@ static char *winreg_printer_data_keyname(TALLOC_CTX *mem_ctx, const char *printe
  *
  * @param[in]  mem_ctx  The memory context to use.
  *
- * @param[in]  pipe_handle The pipe handle for the rpc connection.
+ * @param[in]  winreg_handle The binding handle for the rpc connection.
  *
  * @param[in]  key_hnd  The opened key handle.
  *
@@ -380,7 +392,7 @@ static char *winreg_printer_data_keyname(TALLOC_CTX *mem_ctx, const char *printe
  *                           code if something gone wrong.
  */
 static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
-                                       struct rpc_pipe_client *pipe_handle,
+                                       struct dcerpc_binding_handle *winreg_handle,
                                        struct policy_handle *key_hnd,
                                        uint32_t *pnum_values,
                                        struct spoolss_PrinterEnumValues **penum_values)
@@ -405,7 +417,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
 
        ZERO_STRUCT(classname);
 
-       status = rpccli_winreg_QueryInfoKey(pipe_handle,
+       status = dcerpc_winreg_QueryInfoKey(winreg_handle,
                                            tmp_ctx,
                                            key_hnd,
                                            &classname,
@@ -421,12 +433,14 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_enumvalues: Could not query info: %s\n",
                          nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto error;
-               }
                result = ntstatus_to_werror(status);
                goto error;
        }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(0, ("winreg_printer_enumvalues: Could not query info: %s\n",
+                         win_errstr(result)));
+               goto error;
+       }
 
        if (num_values == 0) {
                *pnum_values = 0;
@@ -460,7 +474,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
                }
                length = 0;
 
-               status = rpccli_winreg_EnumValue(pipe_handle,
+               status = dcerpc_winreg_EnumValue(winreg_handle,
                                                 tmp_ctx,
                                                 key_hnd,
                                                 i,
@@ -479,12 +493,14 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
                if (!NT_STATUS_IS_OK(status)) {
                        DEBUG(0, ("winreg_printer_enumvalues: Could not enumerate values: %s\n",
                                  nt_errstr(status)));
-                       if (!W_ERROR_IS_OK(result)) {
-                               goto error;
-                       }
                        result = ntstatus_to_werror(status);
                        goto error;
                }
+               if (!W_ERROR_IS_OK(result)) {
+                       DEBUG(0, ("winreg_printer_enumvalues: Could not enumerate values: %s\n",
+                                 win_errstr(result)));
+                       goto error;
+               }
 
                if (name_buf.name == NULL) {
                        result = WERR_INVALID_PARAMETER;
@@ -499,7 +515,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
                val.value_name_len = strlen_m_term(val.value_name) * 2;
 
                val.type = type;
-               val.data_length = data_size;
+               val.data_length = length;
                val.data = NULL;
                if (val.data_length) {
                        val.data = talloc(enum_values, DATA_BLOB);
@@ -507,7 +523,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
                                result = WERR_NOMEM;
                                goto error;
                        }
-                       *val.data = data_blob_talloc(enum_values, data, data_size);
+                       *val.data = data_blob_talloc(val.data, data, val.data_length);
                }
 
                enum_values[i] = val;
@@ -532,7 +548,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
  *
  * @param[in]  mem_ctx  The memory context to use.
  *
- * @param[in]  pipe_handle The pipe handle for the rpc connection.
+ * @param[in]  winreg_handle The binding handle for the rpc connection.
  *
  * @param[in]  key_hnd  The opened key handle.
  *
@@ -545,7 +561,7 @@ static WERROR winreg_printer_enumvalues(TALLOC_CTX *mem_ctx,
  *                           code if something gone wrong.
  */
 static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
-                                     struct rpc_pipe_client *pipe_handle,
+                                     struct dcerpc_binding_handle *winreg_handle,
                                      struct policy_handle *key_hnd,
                                      uint32_t *pnum_subkeys,
                                      const char ***psubkeys)
@@ -568,7 +584,7 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
 
        ZERO_STRUCT(classname);
 
-       status = rpccli_winreg_QueryInfoKey(pipe_handle,
+       status = dcerpc_winreg_QueryInfoKey(winreg_handle,
                                            tmp_ctx,
                                            key_hnd,
                                            &classname,
@@ -584,12 +600,14 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_enumkeys: Could not query info: %s\n",
                          nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto error;
-               }
                result = ntstatus_to_werror(status);
                goto error;
        }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(0, ("winreg_printer_enumkeys: Could not query info: %s\n",
+                         win_errstr(result)));
+               goto error;
+       }
 
        subkeys = talloc_zero_array(tmp_ctx, const char *, num_subkeys + 2);
        if (subkeys == NULL) {
@@ -630,7 +648,7 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
 
                ZERO_STRUCT(modtime);
 
-               status = rpccli_winreg_EnumKey(pipe_handle,
+               status = dcerpc_winreg_EnumKey(winreg_handle,
                                               tmp_ctx,
                                               key_hnd,
                                               i,
@@ -647,12 +665,14 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
                if (!NT_STATUS_IS_OK(status)) {
                        DEBUG(0, ("winreg_printer_enumkeys: Could not enumerate keys: %s\n",
                                  nt_errstr(status)));
-                       if (!W_ERROR_IS_OK(result)) {
-                               goto error;
-                       }
                        result = ntstatus_to_werror(status);
                        goto error;
                }
+               if (!W_ERROR_IS_OK(result)) {
+                       DEBUG(0, ("winreg_printer_enumkeys: Could not enumerate keys: %s\n",
+                                 win_errstr(result)));
+                       goto error;
+               }
 
                if (name_buf.name == NULL) {
                        result = WERR_INVALID_PARAMETER;
@@ -685,7 +705,7 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
  *
  * @param[in]  mem_ctx  The memory context to use.
  *
- * @param[in]  pipe_handle The pipe handle for the rpc connection.
+ * @param[in]  winreg_handle The binding handle for the rpc connection.
  *
  * @param[in]  hive_handle A opened hive handle to the key.
  *
@@ -697,7 +717,7 @@ static WERROR winreg_printer_enumkeys(TALLOC_CTX *mem_ctx,
  *                      code if something gone wrong.
  */
 static WERROR winreg_printer_delete_subkeys(TALLOC_CTX *mem_ctx,
-                                           struct rpc_pipe_client *pipe_handle,
+                                           struct dcerpc_binding_handle *winreg_handle,
                                            struct policy_handle *hive_handle,
                                            uint32_t access_mask,
                                            const char *key)
@@ -715,7 +735,7 @@ static WERROR winreg_printer_delete_subkeys(TALLOC_CTX *mem_ctx,
 
        DEBUG(2, ("winreg_printer_delete_subkeys: delete key %s\n", key));
        /* open the key */
-       status = rpccli_winreg_OpenKey(pipe_handle,
+       status = dcerpc_winreg_OpenKey(winreg_handle,
                                       mem_ctx,
                                       hive_handle,
                                       wkey,
@@ -726,14 +746,16 @@ static WERROR winreg_printer_delete_subkeys(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_delete_subkeys: Could not open key %s: %s\n",
                          wkey.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       return result;
-               }
                return ntstatus_to_werror(status);
        }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(0, ("winreg_printer_delete_subkeys: Could not open key %s: %s\n",
+                         wkey.name, win_errstr(result)));
+               return result;
+       }
 
        result = winreg_printer_enumkeys(mem_ctx,
-                                        pipe_handle,
+                                        winreg_handle,
                                         &key_hnd,
                                         &num_subkeys,
                                         &subkeys);
@@ -750,7 +772,7 @@ static WERROR winreg_printer_delete_subkeys(TALLOC_CTX *mem_ctx,
 
                DEBUG(2, ("winreg_printer_delete_subkeys: delete subkey %s\n", subkey));
                result = winreg_printer_delete_subkeys(mem_ctx,
-                                                      pipe_handle,
+                                                      winreg_handle,
                                                       hive_handle,
                                                       access_mask,
                                                       subkey);
@@ -760,27 +782,33 @@ static WERROR winreg_printer_delete_subkeys(TALLOC_CTX *mem_ctx,
        }
 
        if (is_valid_policy_hnd(&key_hnd)) {
-               rpccli_winreg_CloseKey(pipe_handle, mem_ctx, &key_hnd, NULL);
+               WERROR ignore;
+               dcerpc_winreg_CloseKey(winreg_handle, mem_ctx, &key_hnd, &ignore);
        }
 
        wkey.name = key;
 
-       status = rpccli_winreg_DeleteKey(pipe_handle,
+       status = dcerpc_winreg_DeleteKey(winreg_handle,
                                         mem_ctx,
                                         hive_handle,
                                         wkey,
                                         &result);
+       if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
 
 done:
        if (is_valid_policy_hnd(&key_hnd)) {
-               rpccli_winreg_CloseKey(pipe_handle, mem_ctx, &key_hnd, NULL);
+               WERROR ignore;
+
+               dcerpc_winreg_CloseKey(winreg_handle, mem_ctx, &key_hnd, &ignore);
        }
 
        return result;
 }
 
 static WERROR winreg_printer_write_sz(TALLOC_CTX *mem_ctx,
-                                     struct rpc_pipe_client *pipe_handle,
+                                     struct dcerpc_binding_handle *winreg_handle,
                                      struct policy_handle *key_handle,
                                      const char *value,
                                      const char *data)
@@ -800,7 +828,7 @@ static WERROR winreg_printer_write_sz(TALLOC_CTX *mem_ctx,
                        return WERR_NOMEM;
                }
        }
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -809,18 +837,18 @@ static WERROR winreg_printer_write_sz(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_sz: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
 }
 
 static WERROR winreg_printer_write_dword(TALLOC_CTX *mem_ctx,
-                                        struct rpc_pipe_client *pipe_handle,
+                                        struct dcerpc_binding_handle *winreg_handle,
                                         struct policy_handle *key_handle,
                                         const char *value,
                                         uint32_t data)
@@ -834,7 +862,7 @@ static WERROR winreg_printer_write_dword(TALLOC_CTX *mem_ctx,
        blob = data_blob_talloc(mem_ctx, NULL, 4);
        SIVAL(blob.data, 0, data);
 
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -843,18 +871,18 @@ static WERROR winreg_printer_write_dword(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_dword: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
 }
 
 static WERROR winreg_printer_write_binary(TALLOC_CTX *mem_ctx,
-                                         struct rpc_pipe_client *pipe_handle,
+                                         struct dcerpc_binding_handle *winreg_handle,
                                          struct policy_handle *key_handle,
                                          const char *value,
                                          DATA_BLOB blob)
@@ -864,7 +892,7 @@ static WERROR winreg_printer_write_binary(TALLOC_CTX *mem_ctx,
        NTSTATUS status;
 
        wvalue.name = value;
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -873,18 +901,18 @@ static WERROR winreg_printer_write_binary(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_binary: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
 }
 
 static WERROR winreg_printer_query_binary(TALLOC_CTX *mem_ctx,
-                                         struct rpc_pipe_client *pipe_handle,
+                                         struct dcerpc_binding_handle *winreg_handle,
                                          struct policy_handle *key_handle,
                                          const char *value,
                                          DATA_BLOB *data)
@@ -898,7 +926,7 @@ static WERROR winreg_printer_query_binary(TALLOC_CTX *mem_ctx,
        DATA_BLOB blob;
 
        wvalue.name = value;
-       status = rpccli_winreg_QueryValue(pipe_handle,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          mem_ctx,
                                          key_handle,
                                          &wvalue,
@@ -908,12 +936,11 @@ static WERROR winreg_printer_query_binary(TALLOC_CTX *mem_ctx,
                                          &value_len,
                                          &result);
        if (!NT_STATUS_IS_OK(status)) {
-               DEBUG(2, ("winreg_printer_query_binary: Could not query value %s: %s\n",
-                         wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(2, ("winreg_printer_query_binary: Could not query value %s: %s\n",
+                         wvalue.name, win_errstr(result)));
                goto done;
        }
 
@@ -928,7 +955,7 @@ static WERROR winreg_printer_query_binary(TALLOC_CTX *mem_ctx,
        }
        value_len = 0;
 
-       status = rpccli_winreg_QueryValue(pipe_handle,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          mem_ctx,
                                          key_handle,
                                          &wvalue,
@@ -938,11 +965,11 @@ static WERROR winreg_printer_query_binary(TALLOC_CTX *mem_ctx,
                                          &value_len,
                                          &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(2, ("winreg_printer_query_binary: Could not query value %s: %s\n",
-                         wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
+                         wvalue.name, win_errstr(result)));
                goto done;
        }
 
@@ -955,7 +982,7 @@ done:
 }
 
 static WERROR winreg_printer_query_dword(TALLOC_CTX *mem_ctx,
-                                        struct rpc_pipe_client *pipe_handle,
+                                        struct dcerpc_binding_handle *winreg_handle,
                                         struct policy_handle *key_handle,
                                         const char *value,
                                         uint32_t *data)
@@ -969,7 +996,7 @@ static WERROR winreg_printer_query_dword(TALLOC_CTX *mem_ctx,
        DATA_BLOB blob;
 
        wvalue.name = value;
-       status = rpccli_winreg_QueryValue(pipe_handle,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          mem_ctx,
                                          key_handle,
                                          &wvalue,
@@ -979,12 +1006,11 @@ static WERROR winreg_printer_query_dword(TALLOC_CTX *mem_ctx,
                                          &value_len,
                                          &result);
        if (!NT_STATUS_IS_OK(status)) {
-               DEBUG(2, ("winreg_printer_query_dword: Could not query value %s: %s\n",
-                         wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
+               DEBUG(2, ("winreg_printer_query_dword: Could not query value %s: %s\n",
+                         wvalue.name, win_errstr(result)));
                goto done;
        }
 
@@ -1005,7 +1031,7 @@ static WERROR winreg_printer_query_dword(TALLOC_CTX *mem_ctx,
        }
        value_len = 0;
 
-       status = rpccli_winreg_QueryValue(pipe_handle,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          mem_ctx,
                                          key_handle,
                                          &wvalue,
@@ -1015,11 +1041,11 @@ static WERROR winreg_printer_query_dword(TALLOC_CTX *mem_ctx,
                                          &value_len,
                                          &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(2, ("winreg_printer_query_dword: Could not query value %s: %s\n",
-                         wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
+                         wvalue.name, win_errstr(result)));
                goto done;
        }
 
@@ -1031,7 +1057,7 @@ done:
 }
 
 static WERROR winreg_printer_write_multi_sz(TALLOC_CTX *mem_ctx,
-                                           struct rpc_pipe_client *pipe_handle,
+                                           struct dcerpc_binding_handle *winreg_handle,
                                            struct policy_handle *key_handle,
                                            const char *value,
                                            const char **data)
@@ -1045,7 +1071,7 @@ static WERROR winreg_printer_write_multi_sz(TALLOC_CTX *mem_ctx,
        if (!push_reg_multi_sz(mem_ctx, &blob, data)) {
                return WERR_NOMEM;
        }
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -1054,24 +1080,25 @@ static WERROR winreg_printer_write_multi_sz(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_multi_sz: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
 }
 
 static WERROR winreg_printer_opendriver(TALLOC_CTX *mem_ctx,
-                                       struct auth_serversupplied_info *server_info,
+                                       const struct auth_serversupplied_info *server_info,
+                                       struct messaging_context *msg_ctx,
                                        const char *drivername,
                                        const char *architecture,
                                        uint32_t version,
                                        uint32_t access_mask,
                                        bool create,
-                                       struct rpc_pipe_client **winreg_pipe,
+                                       struct dcerpc_binding_handle **winreg_binding_handle,
                                        struct policy_handle *hive_hnd,
                                        struct policy_handle *key_hnd)
 {
@@ -1087,7 +1114,8 @@ static WERROR winreg_printer_opendriver(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(mem_ctx,
                                        server_info,
-                                       winreg_pipe,
+                                       msg_ctx,
+                                       winreg_binding_handle,
                                        key_name,
                                        drivername,
                                        create,
@@ -1110,7 +1138,7 @@ static WERROR winreg_enumval_to_dword(TALLOC_CTX *mem_ctx,
                return WERR_INVALID_DATATYPE;
        }
 
-       if (v->data_length == 0) {
+       if (v->data_length != 4) {
                *dw = 0;
                return WERR_OK;
        }
@@ -1178,7 +1206,7 @@ static WERROR winreg_enumval_to_multi_sz(TALLOC_CTX *mem_ctx,
 }
 
 static WERROR winreg_printer_write_date(TALLOC_CTX *mem_ctx,
-                                       struct rpc_pipe_client *pipe_handle,
+                                       struct dcerpc_binding_handle *winreg_handle,
                                        struct policy_handle *key_handle,
                                        const char *value,
                                        NTTIME data)
@@ -1203,7 +1231,7 @@ static WERROR winreg_printer_write_date(TALLOC_CTX *mem_ctx,
        if (!push_reg_sz(mem_ctx, &blob, str)) {
                return WERR_NOMEM;
        }
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -1212,11 +1240,11 @@ static WERROR winreg_printer_write_date(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_date: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
@@ -1244,7 +1272,7 @@ static WERROR winreg_printer_date_to_NTTIME(const char *str, NTTIME *data)
 }
 
 static WERROR winreg_printer_write_ver(TALLOC_CTX *mem_ctx,
-                                      struct rpc_pipe_client *pipe_handle,
+                                      struct dcerpc_binding_handle *winreg_handle,
                                       struct policy_handle *key_handle,
                                       const char *value,
                                       uint64_t data)
@@ -1270,7 +1298,7 @@ static WERROR winreg_printer_write_ver(TALLOC_CTX *mem_ctx,
        if (!push_reg_sz(mem_ctx, &blob, str)) {
                return WERR_NOMEM;
        }
-       status = rpccli_winreg_SetValue(pipe_handle,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        mem_ctx,
                                        key_handle,
                                        wvalue,
@@ -1279,11 +1307,11 @@ static WERROR winreg_printer_write_ver(TALLOC_CTX *mem_ctx,
                                        blob.length,
                                        &result);
        if (!NT_STATUS_IS_OK(status)) {
+               result = ntstatus_to_werror(status);
+       }
+       if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_write_date: Could not set value %s: %s\n",
                        wvalue.name, win_errstr(result)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
        }
 
        return result;
@@ -1310,12 +1338,12 @@ static WERROR winreg_printer_ver_to_dword(const char *str, uint64_t *data)
 ********************************************************************/
 
 WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
-                            struct auth_serversupplied_info *server_info,
-                            const char *servername,
+                            const struct auth_serversupplied_info *server_info,
+                            struct messaging_context *msg_ctx,
                             const char *sharename)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct spoolss_SetPrinterInfo2 *info2;
        struct security_descriptor *secdesc;
@@ -1343,7 +1371,8 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -1364,7 +1393,8 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
        /* Create the main key */
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        true,
@@ -1378,7 +1408,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
        }
 
        if (is_valid_policy_hnd(&key_hnd)) {
-               rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+               dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &result);
        }
 
        /* Create subkeys */
@@ -1398,7 +1428,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                ZERO_STRUCT(wkeyclass);
                wkeyclass.name = "";
 
-               status = rpccli_winreg_CreateKey(winreg_pipe,
+               status = dcerpc_winreg_CreateKey(winreg_handle,
                                                 tmp_ctx,
                                                 &hive_hnd,
                                                 wkey,
@@ -1410,11 +1440,11 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                                                 &action,
                                                 &result);
                if (!NT_STATUS_IS_OK(status)) {
+                       result = ntstatus_to_werror(status);
+               }
+               if (!W_ERROR_IS_OK(result)) {
                        DEBUG(0, ("winreg_create_printer_keys: Could not create key %s: %s\n",
                                wkey.name, win_errstr(result)));
-                       if (!W_ERROR_IS_OK(result)) {
-                               result = ntstatus_to_werror(status);
-                       }
                        goto done;
                }
 
@@ -1425,7 +1455,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        const char *uncname;
 
                        result = winreg_printer_write_sz(tmp_ctx,
-                                                        winreg_pipe,
+                                                        winreg_handle,
                                                         &key_hnd,
                                                         SPOOL_REG_PRINTERNAME,
                                                         sharename);
@@ -1434,7 +1464,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_sz(tmp_ctx,
-                                                        winreg_pipe,
+                                                        winreg_handle,
                                                         &key_hnd,
                                                         SPOOL_REG_SHORTSERVERNAME,
                                                         global_myname());
@@ -1458,7 +1488,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_sz(tmp_ctx,
-                                                        winreg_pipe,
+                                                        winreg_handle,
                                                         &key_hnd,
                                                         SPOOL_REG_SERVERNAME,
                                                         longname);
@@ -1474,7 +1504,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_sz(tmp_ctx,
-                                                        winreg_pipe,
+                                                        winreg_handle,
                                                         &key_hnd,
                                                         SPOOL_REG_UNCNAME,
                                                         uncname);
@@ -1483,7 +1513,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_dword(tmp_ctx,
-                                                           winreg_pipe,
+                                                           winreg_handle,
                                                            &key_hnd,
                                                            SPOOL_REG_VERSIONNUMBER,
                                                            4);
@@ -1492,7 +1522,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_dword(tmp_ctx,
-                                                           winreg_pipe,
+                                                           winreg_handle,
                                                            &key_hnd,
                                                            SPOOL_REG_PRINTSTARTTIME,
                                                            0);
@@ -1501,7 +1531,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_dword(tmp_ctx,
-                                                           winreg_pipe,
+                                                           winreg_handle,
                                                            &key_hnd,
                                                            SPOOL_REG_PRINTENDTIME,
                                                            0);
@@ -1510,7 +1540,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_dword(tmp_ctx,
-                                                           winreg_pipe,
+                                                           winreg_handle,
                                                            &key_hnd,
                                                            SPOOL_REG_PRIORITY,
                                                            1);
@@ -1519,7 +1549,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                        }
 
                        result = winreg_printer_write_dword(tmp_ctx,
-                                                           winreg_pipe,
+                                                           winreg_handle,
                                                            &key_hnd,
                                                            SPOOL_REG_PRINTKEEPPRINTEDJOBS,
                                                            0);
@@ -1532,7 +1562,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                }
 
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &result);
                }
        }
        info2 = talloc_zero(tmp_ctx, struct spoolss_SetPrinterInfo2);
@@ -1541,12 +1571,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                goto done;
        }
 
-       if (servername != NULL) {
-               info2->printername = talloc_asprintf(tmp_ctx, "\\\\%s\\%s",
-                                                    servername, sharename);
-       } else {
-               info2->printername = sharename;
-       }
+       info2->printername = sharename;
        if (info2->printername == NULL) {
                result = WERR_NOMEM;
                goto done;
@@ -1596,6 +1621,7 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
 
        result = winreg_update_printer(tmp_ctx,
                                       server_info,
+                                      msg_ctx,
                                       sharename,
                                       info2_mask,
                                       info2,
@@ -1603,12 +1629,14 @@ WERROR winreg_create_printer(TALLOC_CTX *mem_ctx,
                                       secdesc);
 
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -1617,7 +1645,8 @@ done:
 }
 
 WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
-                            struct auth_serversupplied_info *server_info,
+                            const struct auth_serversupplied_info *server_info,
+                            struct messaging_context *msg_ctx,
                             const char *sharename,
                             uint32_t info2_mask,
                             struct spoolss_SetPrinterInfo2 *info2,
@@ -1625,7 +1654,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
                             struct security_descriptor *secdesc)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        int snum = lp_servicenumber(sharename);
        enum ndr_err_code ndr_err;
@@ -1650,7 +1679,8 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        true,
@@ -1665,7 +1695,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_ATTRIBUTES) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "Attributes",
                                                    info2->attributes);
@@ -1677,7 +1707,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 #if 0
        if (info2_mask & SPOOLSS_PRINTER_INFO_AVERAGEPPM) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "AveragePpm",
                                                    info2->attributes);
@@ -1689,7 +1719,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_COMMENT) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Description",
                                                 info2->comment);
@@ -1700,7 +1730,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_DATATYPE) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Datatype",
                                                 info2->datatype);
@@ -1711,7 +1741,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_DEFAULTPRIORITY) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "Default Priority",
                                                    info2->defaultpriority);
@@ -1743,7 +1773,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
                }
 
                result = winreg_printer_write_binary(tmp_ctx,
-                                                    winreg_pipe,
+                                                    winreg_handle,
                                                     &key_hnd,
                                                     "Default DevMode",
                                                     blob);
@@ -1754,7 +1784,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_DRIVERNAME) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Printer Driver",
                                                 info2->drivername);
@@ -1765,7 +1795,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_LOCATION) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Location",
                                                 info2->location);
@@ -1776,7 +1806,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_PARAMETERS) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Parameters",
                                                 info2->parameters);
@@ -1787,7 +1817,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_PORTNAME) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Port",
                                                 info2->portname);
@@ -1815,7 +1845,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
                        p++;
                }
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Name",
                                                 p);
@@ -1826,7 +1856,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_PRINTPROCESSOR) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Print Processor",
                                                 info2->printprocessor);
@@ -1837,7 +1867,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_PRIORITY) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "Priority",
                                                    info2->priority);
@@ -1859,6 +1889,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
                }
                result = winreg_set_printer_secdesc(tmp_ctx,
                                                    server_info,
+                                                   msg_ctx,
                                                    sharename,
                                                    secdesc);
                if (!W_ERROR_IS_OK(result)) {
@@ -1868,7 +1899,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_SEPFILE) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Separator File",
                                                 info2->sepfile);
@@ -1879,7 +1910,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_SHARENAME) {
                result = winreg_printer_write_sz(tmp_ctx,
-                                                winreg_pipe,
+                                                winreg_handle,
                                                 &key_hnd,
                                                 "Share Name",
                                                 info2->sharename);
@@ -1890,7 +1921,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_STARTTIME) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "StartTime",
                                                    info2->starttime);
@@ -1901,7 +1932,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_STATUS) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "Status",
                                                    info2->status);
@@ -1912,7 +1943,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        if (info2_mask & SPOOLSS_PRINTER_INFO_UNTILTIME) {
                result = winreg_printer_write_dword(tmp_ctx,
-                                                   winreg_pipe,
+                                                   winreg_handle,
                                                    &key_hnd,
                                                    "UntilTime",
                                                    info2->untiltime);
@@ -1922,7 +1953,7 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_write_dword(tmp_ctx,
-                                           winreg_pipe,
+                                           winreg_handle,
                                            &key_hnd,
                                            "ChangeID",
                                            winreg_printer_rev_changeid());
@@ -1932,12 +1963,14 @@ WERROR winreg_update_printer(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -1946,14 +1979,14 @@ done:
 }
 
 WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
-                         struct auth_serversupplied_info *server_info,
-                         const char *servername,
+                         const struct auth_serversupplied_info *server_info,
+                         struct messaging_context *msg_ctx,
                          const char *printer,
                          struct spoolss_PrinterInfo2 **pinfo2)
 {
        struct spoolss_PrinterInfo2 *info2;
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct spoolss_PrinterEnumValues *enum_values = NULL;
        struct spoolss_PrinterEnumValues *v;
@@ -1979,7 +2012,8 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -1993,7 +2027,7 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumvalues(tmp_ctx,
-                                          winreg_pipe,
+                                          winreg_handle,
                                           &key_hnd,
                                           &num_values,
                                           &enum_values);
@@ -2021,14 +2055,6 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
        FILL_STRING(info2, EMPTY_STRING, info2->datatype);
        FILL_STRING(info2, EMPTY_STRING, info2->parameters);
 
-       if (servername != NULL && servername[0] != '\0') {
-               info2->servername = talloc_asprintf(info2, "\\\\%s", servername);
-               if (info2->servername == NULL) {
-                       result = WERR_NOMEM;
-                       goto done;
-               }
-       }
-
        for (i = 0; i < num_values; i++) {
                v = &enum_values[i];
 
@@ -2143,32 +2169,9 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
                goto done;
        }
 
-       /* Create the printername */
-       if (info2->servername != NULL && info2->servername[0] != '\0') {
-               if (lp_force_printername(snum)) {
-                       const char *p = talloc_asprintf(info2, "%s\\%s",
-                                                       info2->servername,
-                                                       info2->sharename);
-                               if (p == NULL) {
-                                       result = WERR_NOMEM;
-                                       goto done;
-                               }
-                               info2->printername = p;
-               } else {
-                       char *p = talloc_asprintf(info2, "%s\\%s",
-                                                 info2->servername,
-                                                 info2->printername);
-                       if (p == NULL) {
-                               result = WERR_NOMEM;
-                               goto done;
-                       }
-                       info2->printername = p;
-               }
-       }
-
        /* Construct the Device Mode */
        result = winreg_printer_query_binary(tmp_ctx,
-                                            winreg_pipe,
+                                            winreg_handle,
                                             &key_hnd,
                                             "Default DevMode",
                                             &blob);
@@ -2198,18 +2201,9 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
                }
        }
 
-       if (info2->devmode != NULL) {
-               info2->devmode->devicename = talloc_strdup(info2->devmode,
-                                                          info2->printername);
-               if (info2->devmode->devicename == NULL) {
-                       DEBUG(0, ("winreg_get_printer: Failed to set devicename\n"));
-                       result = WERR_NOMEM;
-                       goto done;
-               }
-       }
-
        result = winreg_get_printer_secdesc(info2,
                                            server_info,
+                                           msg_ctx,
                                            printer,
                                            &info2->secdesc);
        if (!W_ERROR_IS_OK(result)) {
@@ -2227,12 +2221,14 @@ WERROR winreg_get_printer(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2241,13 +2237,14 @@ done:
 }
 
 WERROR winreg_get_printer_secdesc(TALLOC_CTX *mem_ctx,
-                                 struct auth_serversupplied_info *server_info,
+                                 const struct auth_serversupplied_info *server_info,
+                                 struct messaging_context *msg_ctx,
                                  const char *sharename,
                                  struct spoolss_security_descriptor **psecdesc)
 {
        struct spoolss_security_descriptor *secdesc;
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        enum ndr_err_code ndr_err;
        const char *path;
@@ -2271,7 +2268,8 @@ WERROR winreg_get_printer_secdesc(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -2286,7 +2284,7 @@ WERROR winreg_get_printer_secdesc(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_query_binary(tmp_ctx,
-                                            winreg_pipe,
+                                            winreg_handle,
                                             &key_hnd,
                                             "Security",
                                             &blob);
@@ -2320,15 +2318,29 @@ WERROR winreg_get_printer_secdesc(TALLOC_CTX *mem_ctx,
        goto done;
 
 create_default:
+       result = winreg_printer_openkey(tmp_ctx,
+                                       server_info,
+                                       msg_ctx,
+                                       &winreg_handle,
+                                       path,
+                                       "",
+                                       true,
+                                       access_mask,
+                                       &hive_hnd,
+                                       &key_hnd);
+       if (!W_ERROR_IS_OK(result)) {
+               goto done;
+       }
+
        result = spoolss_create_default_secdesc(tmp_ctx, &secdesc);
        if (!W_ERROR_IS_OK(result)) {
-               return result;
+               goto done;
        }
 
        /* If security descriptor is owned by S-1-1-0 and winbindd is up,
           this security descriptor has been created when winbindd was
           down.  Take ownership of security descriptor. */
-       if (sid_equal(secdesc->owner_sid, &global_sid_World)) {
+       if (dom_sid_equal(secdesc->owner_sid, &global_sid_World)) {
                struct dom_sid owner_sid;
 
                /* Change sd owner to workgroup administrator */
@@ -2368,7 +2380,7 @@ create_default:
        }
 
        result = winreg_printer_write_binary(tmp_ctx,
-                                            winreg_pipe,
+                                            winreg_handle,
                                             &key_hnd,
                                             "Security",
                                             blob);
@@ -2382,12 +2394,14 @@ create_default:
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2396,14 +2410,15 @@ done:
 }
 
 WERROR winreg_set_printer_secdesc(TALLOC_CTX *mem_ctx,
-                                 struct auth_serversupplied_info *server_info,
+                                 const struct auth_serversupplied_info *server_info,
+                                 struct messaging_context *msg_ctx,
                                  const char *sharename,
                                  const struct spoolss_security_descriptor *secdesc)
 {
        const struct spoolss_security_descriptor *new_secdesc = secdesc;
        struct spoolss_security_descriptor *old_secdesc;
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        enum ndr_err_code ndr_err;
        const char *path;
@@ -2435,6 +2450,7 @@ WERROR winreg_set_printer_secdesc(TALLOC_CTX *mem_ctx,
 
                result = winreg_get_printer_secdesc(tmp_ctx,
                                                    server_info,
+                                                   msg_ctx,
                                                    sharename,
                                                    &old_secdesc);
                if (!W_ERROR_IS_OK(result)) {
@@ -2479,7 +2495,8 @@ WERROR winreg_set_printer_secdesc(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -2499,18 +2516,20 @@ WERROR winreg_set_printer_secdesc(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_write_binary(tmp_ctx,
-                                            winreg_pipe,
+                                            winreg_handle,
                                             &key_hnd,
                                             "Security",
                                             blob);
 
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2520,7 +2539,8 @@ done:
 
 /* Set printer data over the winreg pipe. */
 WERROR winreg_set_printer_dataex(TALLOC_CTX *mem_ctx,
-                                struct auth_serversupplied_info *server_info,
+                                const struct auth_serversupplied_info *server_info,
+                                struct messaging_context *msg_ctx,
                                 const char *printer,
                                 const char *key,
                                 const char *value,
@@ -2529,7 +2549,7 @@ WERROR winreg_set_printer_dataex(TALLOC_CTX *mem_ctx,
                                 uint32_t data_size)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        char *path;
@@ -2555,7 +2575,8 @@ WERROR winreg_set_printer_dataex(TALLOC_CTX *mem_ctx,
                        key, value, access_mask, printer));
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        true,
@@ -2569,7 +2590,7 @@ WERROR winreg_set_printer_dataex(TALLOC_CTX *mem_ctx,
        }
 
        wvalue.name = value;
-       status = rpccli_winreg_SetValue(winreg_pipe,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        tmp_ctx,
                                        &key_hnd,
                                        wvalue,
@@ -2580,21 +2601,18 @@ WERROR winreg_set_printer_dataex(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_set_printer_dataex: Could not set value %s: %s\n",
                          value, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
-               goto done;
        }
 
-       result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2604,7 +2622,8 @@ done:
 
 /* Get printer data over a winreg pipe. */
 WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
-                                struct auth_serversupplied_info *server_info,
+                                const struct auth_serversupplied_info *server_info,
+                                struct messaging_context *msg_ctx,
                                 const char *printer,
                                 const char *key,
                                 const char *value,
@@ -2613,7 +2632,7 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
                                 uint32_t *data_size)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        enum winreg_Type type_in;
@@ -2641,7 +2660,8 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        false,
@@ -2661,7 +2681,7 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
         * needed memory size to be allocated, then allocate
         * data buffer and call again.
         */
-       status = rpccli_winreg_QueryValue(winreg_pipe,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          tmp_ctx,
                                          &key_hnd,
                                          &wvalue,
@@ -2673,12 +2693,12 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_get_printer_dataex: Could not query value %s: %s\n",
                          value, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
                goto done;
        }
+       if (!W_ERROR_IS_OK(result)) {
+               goto done;
+       }
 
        data_in = (uint8_t *) TALLOC(tmp_ctx, data_in_size);
        if (data_in == NULL) {
@@ -2687,7 +2707,7 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
        }
        value_len = 0;
 
-       status = rpccli_winreg_QueryValue(winreg_pipe,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          tmp_ctx,
                                          &key_hnd,
                                          &wvalue,
@@ -2699,9 +2719,10 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_get_printer_dataex: Could not query value %s: %s\n",
                          value, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       result = ntstatus_to_werror(status);
-               }
+               result = ntstatus_to_werror(status);
+               goto done;
+       }
+       if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
@@ -2713,12 +2734,14 @@ WERROR winreg_get_printer_dataex(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2728,14 +2751,15 @@ done:
 
 /* Enumerate on the values of a given key and provide the data. */
 WERROR winreg_enum_printer_dataex(TALLOC_CTX *mem_ctx,
-                                 struct auth_serversupplied_info *server_info,
+                                 const struct auth_serversupplied_info *server_info,
+                                 struct messaging_context *msg_ctx,
                                  const char *printer,
                                  const char *key,
                                  uint32_t *pnum_values,
                                  struct spoolss_PrinterEnumValues **penum_values)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
 
        struct spoolss_PrinterEnumValues *enum_values = NULL;
@@ -2758,7 +2782,8 @@ WERROR winreg_enum_printer_dataex(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        false,
@@ -2772,7 +2797,7 @@ WERROR winreg_enum_printer_dataex(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumvalues(tmp_ctx,
-                                          winreg_pipe,
+                                          winreg_handle,
                                           &key_hnd,
                                           &num_values,
                                           &enum_values);
@@ -2789,12 +2814,14 @@ WERROR winreg_enum_printer_dataex(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2804,13 +2831,14 @@ done:
 
 /* Delete printer data over a winreg pipe. */
 WERROR winreg_delete_printer_dataex(TALLOC_CTX *mem_ctx,
-                                   struct auth_serversupplied_info *server_info,
+                                   const struct auth_serversupplied_info *server_info,
+                                   struct messaging_context *msg_ctx,
                                    const char *printer,
                                    const char *key,
                                    const char *value)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        char *path;
@@ -2835,7 +2863,8 @@ WERROR winreg_delete_printer_dataex(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        false,
@@ -2849,7 +2878,7 @@ WERROR winreg_delete_printer_dataex(TALLOC_CTX *mem_ctx,
        }
 
        wvalue.name = value;
-       status = rpccli_winreg_DeleteValue(winreg_pipe,
+       status = dcerpc_winreg_DeleteValue(winreg_handle,
                                           tmp_ctx,
                                           &key_hnd,
                                           wvalue,
@@ -2857,21 +2886,18 @@ WERROR winreg_delete_printer_dataex(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_delete_printer_dataex: Could not delete value %s: %s\n",
                          value, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
-               goto done;
        }
 
-       result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2881,14 +2907,15 @@ done:
 
 /* Enumerate on the subkeys of a given key and provide the data. */
 WERROR winreg_enum_printer_key(TALLOC_CTX *mem_ctx,
-                              struct auth_serversupplied_info *server_info,
+                              const struct auth_serversupplied_info *server_info,
+                              struct messaging_context *msg_ctx,
                               const char *printer,
                               const char *key,
                               uint32_t *pnum_subkeys,
                               const char ***psubkeys)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        char *path;
        const char **subkeys = NULL;
@@ -2914,7 +2941,8 @@ WERROR winreg_enum_printer_key(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        false,
@@ -2928,7 +2956,7 @@ WERROR winreg_enum_printer_key(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumkeys(tmp_ctx,
-                                        winreg_pipe,
+                                        winreg_handle,
                                         &key_hnd,
                                         &num_subkeys,
                                         &subkeys);
@@ -2945,12 +2973,14 @@ WERROR winreg_enum_printer_key(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -2960,12 +2990,13 @@ done:
 
 /* Delete a key with subkeys of a given printer. */
 WERROR winreg_delete_printer_key(TALLOC_CTX *mem_ctx,
-                                struct auth_serversupplied_info *server_info,
+                                const struct auth_serversupplied_info *server_info,
+                                struct messaging_context *msg_ctx,
                                 const char *printer,
                                 const char *key)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        char *keyname;
        char *path;
@@ -2985,7 +3016,8 @@ WERROR winreg_delete_printer_key(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        key,
                                        false,
@@ -3005,7 +3037,7 @@ WERROR winreg_delete_printer_key(TALLOC_CTX *mem_ctx,
        }
 
        if (is_valid_policy_hnd(&key_hnd)) {
-               rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+               dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &result);
        }
 
        if (key == NULL || key[0] == '\0') {
@@ -3022,7 +3054,7 @@ WERROR winreg_delete_printer_key(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_delete_subkeys(tmp_ctx,
-                                              winreg_pipe,
+                                              winreg_handle,
                                               &hive_hnd,
                                               access_mask,
                                               keyname);
@@ -3033,12 +3065,14 @@ WERROR winreg_delete_printer_key(TALLOC_CTX *mem_ctx,
        }
 
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3047,11 +3081,12 @@ done:
 }
 
 WERROR winreg_printer_update_changeid(TALLOC_CTX *mem_ctx,
-                                     struct auth_serversupplied_info *server_info,
+                                     const struct auth_serversupplied_info *server_info,
+                                     struct messaging_context *msg_ctx,
                                      const char *printer)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        char *path;
        WERROR result;
@@ -3073,7 +3108,8 @@ WERROR winreg_printer_update_changeid(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -3087,7 +3123,7 @@ WERROR winreg_printer_update_changeid(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_write_dword(tmp_ctx,
-                                           winreg_pipe,
+                                           winreg_handle,
                                            &key_hnd,
                                            "ChangeID",
                                            winreg_printer_rev_changeid());
@@ -3097,12 +3133,14 @@ WERROR winreg_printer_update_changeid(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3111,12 +3149,13 @@ done:
 }
 
 WERROR winreg_printer_get_changeid(TALLOC_CTX *mem_ctx,
-                                  struct auth_serversupplied_info *server_info,
+                                  const struct auth_serversupplied_info *server_info,
+                                  struct messaging_context *msg_ctx,
                                   const char *printer,
                                   uint32_t *pchangeid)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        uint32_t changeid = 0;
        char *path;
@@ -3139,7 +3178,8 @@ WERROR winreg_printer_get_changeid(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        path,
                                        "",
                                        false,
@@ -3155,7 +3195,7 @@ WERROR winreg_printer_get_changeid(TALLOC_CTX *mem_ctx,
        DEBUG(10, ("winreg_printer_get_changeid: get changeid from %s\n", path));
 
        result = winreg_printer_query_dword(tmp_ctx,
-                                           winreg_pipe,
+                                           winreg_handle,
                                            &key_hnd,
                                            "ChangeID",
                                            &changeid);
@@ -3169,12 +3209,14 @@ WERROR winreg_printer_get_changeid(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3190,11 +3232,12 @@ done:
  */
 
 WERROR winreg_printer_addform1(TALLOC_CTX *mem_ctx,
-                              struct auth_serversupplied_info *server_info,
+                              const struct auth_serversupplied_info *server_info,
+                              struct messaging_context *msg_ctx,
                               struct spoolss_AddFormInfo1 *form)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        DATA_BLOB blob;
@@ -3215,7 +3258,8 @@ WERROR winreg_printer_addform1(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        TOP_LEVEL_CONTROL_FORMS_KEY,
                                        "",
                                        true,
@@ -3228,7 +3272,8 @@ WERROR winreg_printer_addform1(TALLOC_CTX *mem_ctx,
                goto done;
        }
 
-       result = winreg_printer_enumforms1(tmp_ctx, server_info, &num_info, &info);
+       result = winreg_printer_enumforms1(tmp_ctx, server_info, msg_ctx,
+                                          &num_info, &info);
        if (!W_ERROR_IS_OK(result)) {
                DEBUG(0, ("winreg_printer_addform: Could not enum keys %s: %s\n",
                          TOP_LEVEL_CONTROL_FORMS_KEY, win_errstr(result)));
@@ -3255,7 +3300,7 @@ WERROR winreg_printer_addform1(TALLOC_CTX *mem_ctx,
        SIVAL(blob.data, 24, num_info + 1); /* FIXME */
        SIVAL(blob.data, 28, form->flags);
 
-       status = rpccli_winreg_SetValue(winreg_pipe,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        tmp_ctx,
                                        &key_hnd,
                                        wvalue,
@@ -3266,21 +3311,18 @@ WERROR winreg_printer_addform1(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_addform1: Could not set value %s: %s\n",
                          wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
-               goto done;
        }
 
-       result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3290,12 +3332,13 @@ done:
 }
 
 WERROR winreg_printer_enumforms1(TALLOC_CTX *mem_ctx,
-                                struct auth_serversupplied_info *server_info,
+                                const struct auth_serversupplied_info *server_info,
+                                struct messaging_context *msg_ctx,
                                 uint32_t *pnum_info,
                                 union spoolss_FormInfo **pinfo)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        union spoolss_FormInfo *info;
        struct spoolss_PrinterEnumValues *enum_values = NULL;
@@ -3315,7 +3358,8 @@ WERROR winreg_printer_enumforms1(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        TOP_LEVEL_CONTROL_FORMS_KEY,
                                        "",
                                        true,
@@ -3335,7 +3379,7 @@ WERROR winreg_printer_enumforms1(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumvalues(tmp_ctx,
-                                          winreg_pipe,
+                                          winreg_handle,
                                           &key_hnd,
                                           &num_values,
                                           &enum_values);
@@ -3389,12 +3433,14 @@ WERROR winreg_printer_enumforms1(TALLOC_CTX *mem_ctx,
        }
 
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3404,11 +3450,12 @@ done:
 }
 
 WERROR winreg_printer_deleteform1(TALLOC_CTX *mem_ctx,
-                                 struct auth_serversupplied_info *server_info,
+                                 const struct auth_serversupplied_info *server_info,
+                                 struct messaging_context *msg_ctx,
                                  const char *form_name)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        uint32_t num_builtin = ARRAY_SIZE(builtin_forms1);
@@ -3433,7 +3480,8 @@ WERROR winreg_printer_deleteform1(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        TOP_LEVEL_CONTROL_FORMS_KEY,
                                        "",
                                        false,
@@ -3450,34 +3498,32 @@ WERROR winreg_printer_deleteform1(TALLOC_CTX *mem_ctx,
        }
 
        wvalue.name = form_name;
-       status = rpccli_winreg_DeleteValue(winreg_pipe,
+       status = dcerpc_winreg_DeleteValue(winreg_handle,
                                           tmp_ctx,
                                           &key_hnd,
                                           wvalue,
                                           &result);
        if (!NT_STATUS_IS_OK(status)) {
                /* If the value doesn't exist, return WERR_INVALID_FORM_NAME */
-               if (W_ERROR_EQUAL(result, WERR_BADFILE)) {
-                       result = WERR_INVALID_FORM_NAME;
-                       goto done;
-               }
                DEBUG(0, ("winreg_printer_delteform1: Could not delete value %s: %s\n",
                          wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
                goto done;
        }
 
-       result = WERR_OK;
+       if (W_ERROR_EQUAL(result, WERR_BADFILE)) {
+               result = WERR_INVALID_FORM_NAME;
+       }
+
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3486,12 +3532,13 @@ done:
 }
 
 WERROR winreg_printer_setform1(TALLOC_CTX *mem_ctx,
-                              struct auth_serversupplied_info *server_info,
+                              const struct auth_serversupplied_info *server_info,
+                              struct messaging_context *msg_ctx,
                               const char *form_name,
                               struct spoolss_AddFormInfo1 *form)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        DATA_BLOB blob;
@@ -3518,7 +3565,8 @@ WERROR winreg_printer_setform1(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        TOP_LEVEL_CONTROL_FORMS_KEY,
                                        "",
                                        true,
@@ -3533,7 +3581,8 @@ WERROR winreg_printer_setform1(TALLOC_CTX *mem_ctx,
 
        /* If form_name != form->form_name then we renamed the form */
        if (strequal(form_name, form->form_name)) {
-               result = winreg_printer_deleteform1(tmp_ctx, server_info, form_name);
+               result = winreg_printer_deleteform1(tmp_ctx, server_info,
+                                                   msg_ctx, form_name);
                if (!W_ERROR_IS_OK(result)) {
                        DEBUG(0, ("winreg_printer_setform1: Could not open key %s: %s\n",
                                  TOP_LEVEL_CONTROL_FORMS_KEY, win_errstr(result)));
@@ -3553,7 +3602,7 @@ WERROR winreg_printer_setform1(TALLOC_CTX *mem_ctx,
        SIVAL(blob.data, 24, 42);
        SIVAL(blob.data, 28, form->flags);
 
-       status = rpccli_winreg_SetValue(winreg_pipe,
+       status = dcerpc_winreg_SetValue(winreg_handle,
                                        tmp_ctx,
                                        &key_hnd,
                                        wvalue,
@@ -3564,21 +3613,18 @@ WERROR winreg_printer_setform1(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_setform1: Could not set value %s: %s\n",
                          wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
-               goto done;
        }
 
-       result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3587,12 +3633,13 @@ done:
 }
 
 WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
-                              struct auth_serversupplied_info *server_info,
+                              const struct auth_serversupplied_info *server_info,
+                              struct messaging_context *msg_ctx,
                               const char *form_name,
                               struct spoolss_FormInfo1 *r)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct winreg_String wvalue;
        enum winreg_Type type_in;
@@ -3623,7 +3670,8 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_openkey(tmp_ctx,
                                        server_info,
-                                       &winreg_pipe,
+                                       msg_ctx,
+                                       &winreg_handle,
                                        TOP_LEVEL_CONTROL_FORMS_KEY,
                                        "",
                                        true,
@@ -3643,7 +3691,7 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
         * needed memory size to be allocated, then allocate
         * data buffer and call again.
         */
-       status = rpccli_winreg_QueryValue(winreg_pipe,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          tmp_ctx,
                                          &key_hnd,
                                          &wvalue,
@@ -3655,12 +3703,12 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_getform1: Could not query value %s: %s\n",
                          wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
                goto done;
        }
+       if (!W_ERROR_IS_OK(result)) {
+               goto done;
+       }
 
        data_in = (uint8_t *) TALLOC(tmp_ctx, data_in_size);
        if (data_in == NULL) {
@@ -3669,7 +3717,7 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
        }
        value_len = 0;
 
-       status = rpccli_winreg_QueryValue(winreg_pipe,
+       status = dcerpc_winreg_QueryValue(winreg_handle,
                                          tmp_ctx,
                                          &key_hnd,
                                          &wvalue,
@@ -3681,12 +3729,12 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
        if (!NT_STATUS_IS_OK(status)) {
                DEBUG(0, ("winreg_printer_getform1: Could not query value %s: %s\n",
                          wvalue.name, nt_errstr(status)));
-               if (!W_ERROR_IS_OK(result)) {
-                       goto done;
-               }
                result = ntstatus_to_werror(status);
                goto done;
        }
+       if (!W_ERROR_IS_OK(result)) {
+               goto done;
+       }
 
        r->form_name = talloc_strdup(mem_ctx, form_name);
        if (r->form_name == NULL) {
@@ -3705,12 +3753,14 @@ WERROR winreg_printer_getform1(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3719,13 +3769,14 @@ done:
 }
 
 WERROR winreg_add_driver(TALLOC_CTX *mem_ctx,
-                        struct auth_serversupplied_info *server_info,
+                        const struct auth_serversupplied_info *server_info,
+                        struct messaging_context *msg_ctx,
                         struct spoolss_AddDriverInfoCtr *r,
                         const char **driver_name,
                         uint32_t *driver_version)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct spoolss_DriverInfo8 info8;
        TALLOC_CTX *tmp_ctx = NULL;
@@ -3747,11 +3798,12 @@ WERROR winreg_add_driver(TALLOC_CTX *mem_ctx,
 
        result = winreg_printer_opendriver(tmp_ctx,
                                           server_info,
+                                          msg_ctx,
                                           info8.driver_name,
                                           info8.architecture,
                                           info8.version,
                                           access_mask, true,
-                                          &winreg_pipe,
+                                          &winreg_handle,
                                           &hive_hnd,
                                           &key_hnd);
        if (!W_ERROR_IS_OK(result)) {
@@ -3764,161 +3816,161 @@ WERROR winreg_add_driver(TALLOC_CTX *mem_ctx,
 
        /* TODO: "Attributes" ? */
 
-       result = winreg_printer_write_dword(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_dword(tmp_ctx, winreg_handle,
                                            &key_hnd, "Version",
                                            info8.version);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Driver",
                                         info8.driver_path);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Data File",
                                         info8.data_file);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Configuration File",
                                         info8.config_file);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Help File",
                                         info8.help_file);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_handle,
                                               &key_hnd, "Dependent Files",
                                               info8.dependent_files);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Monitor",
                                         info8.monitor_name);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Datatype",
                                         info8.default_datatype);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_handle,
                                               &key_hnd, "Previous Names",
                                               info8.previous_names);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_date(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_date(tmp_ctx, winreg_handle,
                                           &key_hnd, "DriverDate",
                                           info8.driver_date);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_ver(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_ver(tmp_ctx, winreg_handle,
                                          &key_hnd, "DriverVersion",
                                          info8.driver_version);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Manufacturer",
                                         info8.manufacturer_name);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "OEM URL",
                                         info8.manufacturer_url);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "HardwareID",
                                         info8.hardware_id);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Provider",
                                         info8.provider);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "Print Processor",
                                         info8.print_processor);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "VendorSetup",
                                         info8.vendor_setup);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_handle,
                                               &key_hnd, "Color Profiles",
                                               info8.color_profiles);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_sz(tmp_ctx, winreg_handle,
                                         &key_hnd, "InfPath",
                                         info8.inf_path);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_dword(tmp_ctx, winreg_pipe, &key_hnd,
+       result = winreg_printer_write_dword(tmp_ctx, winreg_handle, &key_hnd,
                                            "PrinterDriverAttributes",
                                            info8.printer_driver_attributes);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_multi_sz(tmp_ctx, winreg_handle,
                                               &key_hnd, "CoreDependencies",
                                               info8.core_driver_dependencies);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_date(tmp_ctx, winreg_pipe,
+       result = winreg_printer_write_date(tmp_ctx, winreg_handle,
                                           &key_hnd, "MinInboxDriverVerDate",
                                           info8.min_inbox_driver_ver_date);
        if (!W_ERROR_IS_OK(result)) {
                goto done;
        }
 
-       result = winreg_printer_write_ver(tmp_ctx, winreg_pipe, &key_hnd,
+       result = winreg_printer_write_ver(tmp_ctx, winreg_handle, &key_hnd,
                                          "MinInboxDriverVerVersion",
                                          info8.min_inbox_driver_ver_version);
        if (!W_ERROR_IS_OK(result)) {
@@ -3929,12 +3981,14 @@ WERROR winreg_add_driver(TALLOC_CTX *mem_ctx,
        *driver_version = info8.version;
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -3943,14 +3997,15 @@ done:
 }
 
 WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
-                        struct auth_serversupplied_info *server_info,
+                        const struct auth_serversupplied_info *server_info,
+                        struct messaging_context *msg_ctx,
                         const char *architecture,
                         const char *driver_name,
                         uint32_t driver_version,
                         struct spoolss_DriverInfo8 **_info8)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        struct spoolss_DriverInfo8 i8, *info8;
        struct spoolss_PrinterEnumValues *enum_values = NULL;
@@ -3973,21 +4028,23 @@ WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
                /* look for Win2k first and then for NT4 */
                result = winreg_printer_opendriver(tmp_ctx,
                                                   server_info,
+                                                  msg_ctx,
                                                   driver_name,
                                                   architecture,
                                                   3,
                                                   access_mask, false,
-                                                  &winreg_pipe,
+                                                  &winreg_handle,
                                                   &hive_hnd,
                                                   &key_hnd);
                if (!W_ERROR_IS_OK(result)) {
                        result = winreg_printer_opendriver(tmp_ctx,
                                                           server_info,
+                                                          msg_ctx,
                                                           driver_name,
                                                           architecture,
                                                           2,
                                                           access_mask, false,
-                                                          &winreg_pipe,
+                                                          &winreg_handle,
                                                           &hive_hnd,
                                                           &key_hnd);
                }
@@ -3995,11 +4052,12 @@ WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
                /* ok normal case */
                result = winreg_printer_opendriver(tmp_ctx,
                                                   server_info,
+                                                  msg_ctx,
                                                   driver_name,
                                                   architecture,
                                                   driver_version,
                                                   access_mask, false,
-                                                  &winreg_pipe,
+                                                  &winreg_handle,
                                                   &hive_hnd,
                                                   &key_hnd);
        }
@@ -4012,7 +4070,7 @@ WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumvalues(tmp_ctx,
-                                          winreg_pipe,
+                                          winreg_handle,
                                           &key_hnd,
                                           &num_values,
                                           &enum_values);
@@ -4053,8 +4111,10 @@ WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
                result = winreg_enumval_to_dword(info8, v,
                                                 "Version",
                                                 &tmp);
+               if (NT_STATUS_IS_OK(result)) {
+                       info8->version = (enum spoolss_DriverOSVersion) tmp;
+               }
                CHECK_ERROR(result);
-               info8->version = tmp;
 
                result = winreg_enumval_to_sz(info8, v,
                                              "Driver",
@@ -4193,12 +4253,14 @@ WERROR winreg_get_driver(TALLOC_CTX *mem_ctx,
        *_info8 = talloc_steal(mem_ctx, info8);
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -4207,12 +4269,13 @@ done:
 }
 
 WERROR winreg_del_driver(TALLOC_CTX *mem_ctx,
-                        struct auth_serversupplied_info *server_info,
+                        const struct auth_serversupplied_info *server_info,
+                        struct messaging_context *msg_ctx,
                         struct spoolss_DriverInfo8 *info8,
                         uint32_t version)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        TALLOC_CTX *tmp_ctx;
        char *key_name;
@@ -4229,11 +4292,12 @@ WERROR winreg_del_driver(TALLOC_CTX *mem_ctx,
        /* test that the key exists */
        result = winreg_printer_opendriver(tmp_ctx,
                                           server_info,
+                                          msg_ctx,
                                           info8->driver_name,
                                           info8->architecture,
                                           version,
                                           access_mask, false,
-                                          &winreg_pipe,
+                                          &winreg_handle,
                                           &hive_hnd,
                                           &key_hnd);
        if (!W_ERROR_IS_OK(result)) {
@@ -4252,7 +4316,7 @@ WERROR winreg_del_driver(TALLOC_CTX *mem_ctx,
 
 
        if (is_valid_policy_hnd(&key_hnd)) {
-               rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+               dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &result);
        }
 
        key_name = talloc_asprintf(tmp_ctx,
@@ -4265,7 +4329,7 @@ WERROR winreg_del_driver(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_delete_subkeys(tmp_ctx,
-                                              winreg_pipe,
+                                              winreg_handle,
                                               &hive_hnd,
                                               access_mask,
                                               key_name);
@@ -4279,12 +4343,14 @@ WERROR winreg_del_driver(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }
 
@@ -4293,14 +4359,15 @@ done:
 }
 
 WERROR winreg_get_driver_list(TALLOC_CTX *mem_ctx,
-                             struct auth_serversupplied_info *server_info,
+                             const struct auth_serversupplied_info *server_info,
+                             struct messaging_context *msg_ctx,
                              const char *architecture,
                              uint32_t version,
                              uint32_t *num_drivers,
                              const char ***drivers_p)
 {
        uint32_t access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
-       struct rpc_pipe_client *winreg_pipe = NULL;
+       struct dcerpc_binding_handle *winreg_handle = NULL;
        struct policy_handle hive_hnd, key_hnd;
        const char **drivers;
        TALLOC_CTX *tmp_ctx;
@@ -4321,11 +4388,12 @@ WERROR winreg_get_driver_list(TALLOC_CTX *mem_ctx,
         * parent of all drivers for this architecture and version */
        result = winreg_printer_opendriver(tmp_ctx,
                                           server_info,
+                                          msg_ctx,
                                           NULL,
                                           architecture,
                                           version,
                                           access_mask, false,
-                                          &winreg_pipe,
+                                          &winreg_handle,
                                           &hive_hnd,
                                           &key_hnd);
        if (!W_ERROR_IS_OK(result)) {
@@ -4337,7 +4405,7 @@ WERROR winreg_get_driver_list(TALLOC_CTX *mem_ctx,
        }
 
        result = winreg_printer_enumkeys(tmp_ctx,
-                                        winreg_pipe,
+                                        winreg_handle,
                                         &key_hnd,
                                         num_drivers,
                                         &drivers);
@@ -4352,12 +4420,14 @@ WERROR winreg_get_driver_list(TALLOC_CTX *mem_ctx,
 
        result = WERR_OK;
 done:
-       if (winreg_pipe != NULL) {
+       if (winreg_handle != NULL) {
+               WERROR ignore;
+
                if (is_valid_policy_hnd(&key_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &key_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &key_hnd, &ignore);
                }
                if (is_valid_policy_hnd(&hive_hnd)) {
-                       rpccli_winreg_CloseKey(winreg_pipe, tmp_ctx, &hive_hnd, NULL);
+                       dcerpc_winreg_CloseKey(winreg_handle, tmp_ctx, &hive_hnd, &ignore);
                }
        }