2 Unix SMB/CIFS implementation.
3 test suite for backupkey remote protocol rpc operations
5 Copyright (C) Matthieu Patou 2010-2011
6 Copyright (C) Andreas Schneider <asn@samba.org> 2015
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>.
23 #include "../libcli/security/security.h"
25 #include "torture/rpc/torture_rpc.h"
26 #include "torture/ndr/ndr.h"
28 #include "librpc/gen_ndr/ndr_backupkey_c.h"
29 #include "librpc/gen_ndr/ndr_backupkey.h"
30 #include "librpc/gen_ndr/ndr_lsa_c.h"
31 #include "librpc/gen_ndr/ndr_security.h"
32 #include "lib/cmdline/popt_common.h"
33 #include "libcli/auth/proto.h"
34 #include <system/network.h>
36 #include <gnutls/gnutls.h>
37 #include <gnutls/crypto.h>
38 #include <gnutls/x509.h>
39 #include <gnutls/abstract.h>
45 WRONG_CIPHERTEXT_LENGTH,
47 SHORT_CIPHERTEXT_LENGTH,
49 ZERO_CIPHERTEXT_LENGTH,
55 /* Our very special and valued secret */
56 /* No need to put const as we cast the array in uint8_t
57 * we will get a warning about the discared const
59 static const char secret[] = "tata yoyo mais qu'est ce qu'il y a sous ton grand chapeau ?";
61 /* Get the SID from a user */
62 static struct dom_sid *get_user_sid(struct torture_context *tctx,
66 struct lsa_ObjectAttribute attr;
67 struct lsa_QosInfo qos;
68 struct lsa_OpenPolicy2 r;
71 struct policy_handle handle;
72 struct lsa_LookupNames l;
73 struct lsa_TransSidArray sids;
74 struct lsa_RefDomainList *domains = NULL;
75 struct lsa_String lsa_name;
77 struct dom_sid *result;
79 struct dcerpc_pipe *p2;
80 struct dcerpc_binding_handle *b;
82 const char *domain = cli_credentials_get_domain(cmdline_credentials);
84 torture_assert_ntstatus_ok(tctx,
85 torture_rpc_connection(tctx, &p2, &ndr_table_lsarpc),
86 "could not open lsarpc pipe");
87 b = p2->binding_handle;
89 if (!(tmp_ctx = talloc_new(mem_ctx))) {
93 qos.impersonation_level = 2;
95 qos.effective_only = 0;
99 attr.object_name = NULL;
101 attr.sec_desc = NULL;
104 r.in.system_name = "\\";
106 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
107 r.out.handle = &handle;
109 status = dcerpc_lsa_OpenPolicy2_r(b, tmp_ctx, &r);
110 if (!NT_STATUS_IS_OK(status)) {
111 torture_comment(tctx,
112 "OpenPolicy2 failed - %s\n",
114 talloc_free(tmp_ctx);
117 if (!NT_STATUS_IS_OK(r.out.result)) {
118 torture_comment(tctx,
119 "OpenPolicy2_ failed - %s\n",
120 nt_errstr(r.out.result));
121 talloc_free(tmp_ctx);
128 lsa_name.string = talloc_asprintf(tmp_ctx, "%s\\%s", domain, user);
130 l.in.handle = &handle;
132 l.in.names = &lsa_name;
136 l.out.count = &count;
138 l.out.domains = &domains;
140 status = dcerpc_lsa_LookupNames_r(b, tmp_ctx, &l);
141 if (!NT_STATUS_IS_OK(status)) {
142 torture_comment(tctx,
143 "LookupNames of %s failed - %s\n",
146 talloc_free(tmp_ctx);
150 if (domains->count == 0) {
154 result = dom_sid_add_rid(mem_ctx,
155 domains->domains[0].sid,
156 l.out.sids->sids[0].rid);
157 c.in.handle = &handle;
158 c.out.handle = &handle;
160 status = dcerpc_lsa_Close_r(b, tmp_ctx, &c);
162 if (!NT_STATUS_IS_OK(status)) {
163 torture_comment(tctx,
164 "dcerpc_lsa_Close failed - %s\n",
166 talloc_free(tmp_ctx);
170 if (!NT_STATUS_IS_OK(c.out.result)) {
171 torture_comment(tctx,
172 "dcerpc_lsa_Close failed - %s\n",
173 nt_errstr(c.out.result));
174 talloc_free(tmp_ctx);
178 talloc_free(tmp_ctx);
181 torture_comment(tctx, "Get_user_sid finished\n");
186 * Create a bkrp_encrypted_secret_vX structure
187 * the version depends on the version parameter
188 * the structure is returned as a blob.
189 * The broken flag is to indicate if we want
190 * to create a non conform to specification structre
192 static DATA_BLOB *create_unencryptedsecret(TALLOC_CTX *mem_ctx,
196 TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
197 DATA_BLOB *blob = talloc_zero(mem_ctx, DATA_BLOB);
198 enum ndr_err_code ndr_err;
201 struct bkrp_encrypted_secret_v2 unenc_sec;
203 ZERO_STRUCT(unenc_sec);
204 unenc_sec.secret_len = sizeof(secret);
205 unenc_sec.secret = discard_const_p(uint8_t, secret);
206 generate_random_buffer(unenc_sec.payload_key,
207 sizeof(unenc_sec.payload_key));
209 ndr_err = ndr_push_struct_blob(blob, blob, &unenc_sec,
210 (ndr_push_flags_fn_t)ndr_push_bkrp_encrypted_secret_v2);
211 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
216 /* The magic value is correctly set by the NDR push
217 * but we want to test the behavior of the server
218 * if a differrent value is provided
220 ((uint8_t*)blob->data)[4] = 79; /* A great year !!! */
225 struct bkrp_encrypted_secret_v3 unenc_sec;
227 ZERO_STRUCT(unenc_sec);
228 unenc_sec.secret_len = sizeof(secret);
229 unenc_sec.secret = discard_const_p(uint8_t, secret);
230 generate_random_buffer(unenc_sec.payload_key,
231 sizeof(unenc_sec.payload_key));
233 ndr_err = ndr_push_struct_blob(blob, blob, &unenc_sec,
234 (ndr_push_flags_fn_t)ndr_push_bkrp_encrypted_secret_v3);
235 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
241 * The magic value is correctly set by the NDR push
242 * but we want to test the behavior of the server
243 * if a differrent value is provided
245 ((uint8_t*)blob->data)[4] = 79; /* A great year !!! */
248 talloc_free(tmp_ctx);
253 * Create an access check structure, the format depends on the version parameter.
254 * If broken is specified then we create a stucture that isn't conform to the
257 * If the structure can't be created then NULL is returned.
259 static DATA_BLOB *create_access_check(struct torture_context *tctx,
260 struct dcerpc_pipe *p,
266 TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
267 DATA_BLOB *blob = talloc_zero(mem_ctx, DATA_BLOB);
268 enum ndr_err_code ndr_err;
269 const struct dom_sid *sid = get_user_sid(tctx, tmp_ctx, user);
276 struct bkrp_access_check_v2 access_struct;
277 gnutls_hash_hd_t dig_ctx;
280 ZERO_STRUCT(access_struct);
281 generate_random_buffer(nonce, sizeof(nonce));
282 access_struct.nonce_len = sizeof(nonce);
283 access_struct.nonce = nonce;
284 access_struct.sid = *sid;
286 ndr_err = ndr_push_struct_blob(blob, blob, &access_struct,
287 (ndr_push_flags_fn_t)ndr_push_bkrp_access_check_v2);
288 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
293 * We pushed the whole structure including a null hash
294 * but the hash need to be calculated only up to the hash field
295 * so we reduce the size of what has to be calculated
298 gnutls_hash_init(&dig_ctx, GNUTLS_DIG_SHA1);
301 blob->length - sizeof(access_struct.hash));
302 gnutls_hash_deinit(dig_ctx,
303 blob->data + blob->length - sizeof(access_struct.hash));
305 /* Altering the SHA */
307 blob->data[blob->length - 1]++;
312 struct bkrp_access_check_v3 access_struct;
313 gnutls_hash_hd_t dig_ctx;
316 ZERO_STRUCT(access_struct);
317 generate_random_buffer(nonce, sizeof(nonce));
318 access_struct.nonce_len = sizeof(nonce);
319 access_struct.nonce = nonce;
320 access_struct.sid = *sid;
322 ndr_err = ndr_push_struct_blob(blob, blob, &access_struct,
323 (ndr_push_flags_fn_t)ndr_push_bkrp_access_check_v3);
324 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
328 /*We pushed the whole structure including a null hash
329 * but the hash need to be calculated only up to the hash field
330 * so we reduce the size of what has to be calculated
333 gnutls_hash_init(&dig_ctx, GNUTLS_DIG_SHA512);
336 blob->length - sizeof(access_struct.hash));
337 gnutls_hash_deinit(dig_ctx,
338 blob->data + blob->length - sizeof(access_struct.hash));
340 /* Altering the SHA */
342 blob->data[blob->length -1]++;
345 talloc_free(tmp_ctx);
350 static DATA_BLOB *encrypt_blob(struct torture_context *tctx,
354 DATA_BLOB *to_encrypt,
355 gnutls_cipher_algorithm_t cipher_algo)
357 gnutls_cipher_hd_t cipher_handle = { 0 };
358 gnutls_datum_t gkey = {
362 gnutls_datum_t giv = {
369 blob = talloc(mem_ctx, DATA_BLOB);
374 *blob = data_blob_talloc_zero(mem_ctx, to_encrypt->length);
375 if (blob->data == NULL) {
380 rc = gnutls_cipher_init(&cipher_handle,
384 if (rc != GNUTLS_E_SUCCESS) {
385 torture_comment(tctx,
386 "gnutls_cipher_init failed: %s\n",
387 gnutls_strerror(rc));
392 rc = gnutls_cipher_encrypt2(cipher_handle,
397 gnutls_cipher_deinit(cipher_handle);
398 if (rc != GNUTLS_E_SUCCESS) {
399 torture_comment(tctx,
400 "gnutls_cipher_decrypt2 failed: %s\n",
401 gnutls_strerror(rc));
409 * Certs used for this protocol have a GUID in the issuer_uniq_id field.
410 * This function fetch it.
412 static struct GUID *get_cert_guid(struct torture_context *tctx,
417 gnutls_x509_crt_t x509_cert = NULL;
418 gnutls_datum_t x509_crt_data = {
422 uint8_t dummy[1] = {0};
423 DATA_BLOB issuer_unique_id = {
427 struct GUID *guid = talloc_zero(mem_ctx, struct GUID);
431 rc = gnutls_x509_crt_init(&x509_cert);
432 if (rc != GNUTLS_E_SUCCESS) {
433 torture_comment(tctx,
434 "gnutls_x509_crt_init failed - %s",
435 gnutls_strerror(rc));
439 rc = gnutls_x509_crt_import(x509_cert,
441 GNUTLS_X509_FMT_DER);
442 if (rc != GNUTLS_E_SUCCESS) {
443 torture_comment(tctx,
444 "gnutls_x509_crt_import failed - %s",
445 gnutls_strerror(rc));
446 gnutls_x509_crt_deinit(x509_cert);
450 /* Get the buffer size */
451 rc = gnutls_x509_crt_get_issuer_unique_id(x509_cert,
452 (char *)issuer_unique_id.data,
453 &issuer_unique_id.length);
454 if (rc != GNUTLS_E_SHORT_MEMORY_BUFFER ||
455 issuer_unique_id.length == 0) {
456 gnutls_x509_crt_deinit(x509_cert);
460 issuer_unique_id = data_blob_talloc_zero(mem_ctx,
461 issuer_unique_id.length);
462 if (issuer_unique_id.data == NULL) {
463 gnutls_x509_crt_deinit(x509_cert);
467 rc = gnutls_x509_crt_get_issuer_unique_id(x509_cert,
468 (char *)issuer_unique_id.data,
469 &issuer_unique_id.length);
470 gnutls_x509_crt_deinit(x509_cert);
471 if (rc != GNUTLS_E_SUCCESS) {
472 torture_comment(tctx,
473 "gnutls_x509_crt_get_issuer_unique_id failed - %s",
474 gnutls_strerror(rc));
478 status = GUID_from_data_blob(&issuer_unique_id, guid);
479 if (!NT_STATUS_IS_OK(status)) {
487 * Encrypt a blob with the private key of the certificate
488 * passed as a parameter.
490 static DATA_BLOB *encrypt_blob_pk(struct torture_context *tctx,
494 DATA_BLOB *to_encrypt)
496 gnutls_x509_crt_t x509_cert;
497 gnutls_datum_t x509_crt_data = {
501 gnutls_pubkey_t pubkey;
502 gnutls_datum_t plaintext = {
503 .data = to_encrypt->data,
504 .size = to_encrypt->length,
506 gnutls_datum_t ciphertext = {
512 rc = gnutls_x509_crt_init(&x509_cert);
513 if (rc != GNUTLS_E_SUCCESS) {
517 rc = gnutls_x509_crt_import(x509_cert,
519 GNUTLS_X509_FMT_DER);
520 if (rc != GNUTLS_E_SUCCESS) {
521 gnutls_x509_crt_deinit(x509_cert);
525 rc = gnutls_pubkey_init(&pubkey);
526 if (rc != GNUTLS_E_SUCCESS) {
527 gnutls_x509_crt_deinit(x509_cert);
531 rc = gnutls_pubkey_import_x509(pubkey,
534 gnutls_x509_crt_deinit(x509_cert);
535 if (rc != GNUTLS_E_SUCCESS) {
536 gnutls_pubkey_deinit(pubkey);
540 rc = gnutls_pubkey_encrypt_data(pubkey,
544 gnutls_pubkey_deinit(pubkey);
545 if (rc != GNUTLS_E_SUCCESS) {
549 blob = talloc_zero(mem_ctx, DATA_BLOB);
551 gnutls_pubkey_deinit(pubkey);
555 *blob = data_blob_talloc(blob, ciphertext.data, ciphertext.size);
556 gnutls_free(ciphertext.data);
557 if (blob->data == NULL) {
558 gnutls_pubkey_deinit(pubkey);
565 static struct bkrp_BackupKey *createRetrieveBackupKeyGUIDStruct(struct torture_context *tctx,
566 struct dcerpc_pipe *p, int version, DATA_BLOB *out)
568 struct dcerpc_binding *binding;
569 struct bkrp_client_side_wrapped data;
570 struct GUID *g = talloc(tctx, struct GUID);
571 struct bkrp_BackupKey *r = talloc_zero(tctx, struct bkrp_BackupKey);
572 enum ndr_err_code ndr_err;
580 binding = dcerpc_binding_dup(tctx, p->binding);
581 if (binding == NULL) {
585 status = dcerpc_binding_set_flags(binding, DCERPC_SEAL|DCERPC_AUTH_SPNEGO, 0);
586 if (!NT_STATUS_IS_OK(status)) {
591 status = GUID_from_string(BACKUPKEY_RETRIEVE_BACKUP_KEY_GUID, g);
592 if (!NT_STATUS_IS_OK(status)) {
596 r->in.guidActionAgent = g;
597 data.version = version;
598 ndr_err = ndr_push_struct_blob(&blob, tctx, &data,
599 (ndr_push_flags_fn_t)ndr_push_bkrp_client_side_wrapped);
600 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
603 r->in.data_in = blob.data;
604 r->in.data_in_len = blob.length;
605 r->out.data_out = &out->data;
606 r->out.data_out_len = talloc(r, uint32_t);
610 static struct bkrp_BackupKey *createRestoreGUIDStruct(struct torture_context *tctx,
611 struct dcerpc_pipe *p, int version, DATA_BLOB *out,
615 bool broken_magic_secret,
616 bool broken_magic_access,
617 bool broken_hash_access,
618 bool broken_cert_guid)
620 struct dcerpc_binding_handle *b = p->binding_handle;
621 struct bkrp_client_side_wrapped data;
624 DATA_BLOB *enc_sec = NULL;
625 DATA_BLOB *enc_xs = NULL;
627 DATA_BLOB enc_sec_reverted;
631 struct GUID *guid, *g;
634 enum ndr_err_code ndr_err;
637 gnutls_cipher_algorithm_t cipher_algo;
638 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, version, &out_blob);
644 /* we take a fake user*/
647 user = cli_credentials_get_username(cmdline_credentials);
651 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
653 torture_assert_werr_ok(tctx, r->out.result,
657 * We have to set it outside of the function createRetrieveBackupKeyGUIDStruct
658 * the len of the blob, this is due to the fact that they don't have the
659 * same size (one is 32bits the other 64bits)
661 out_blob.length = *r->out.data_out_len;
663 sec = create_unencryptedsecret(tctx, broken_magic_secret, version);
668 xs = create_access_check(tctx, p, tctx, user, broken_hash_access, version);
673 if (broken_magic_access){
674 /* The start of the access_check structure contains the
675 * GUID of the certificate
680 enc_sec = encrypt_blob_pk(tctx, tctx, out_blob.data, out_blob.length, sec);
684 enc_sec_reverted.data = talloc_array(tctx, uint8_t, enc_sec->length);
685 if (enc_sec_reverted.data == NULL) {
688 enc_sec_reverted.length = enc_sec->length;
691 * We DO NOT revert the array on purpose it's in order to check that
692 * when the server is not able to decrypt then it answer the correct error
695 for(t=0; t< enc_sec->length; t++) {
696 enc_sec_reverted.data[t] = ((uint8_t*)enc_sec->data)[t];
699 for(t=0; t< enc_sec->length; t++) {
700 enc_sec_reverted.data[t] = ((uint8_t*)enc_sec->data)[enc_sec->length - t -1];
707 cipher_algo = GNUTLS_CIPHER_3DES_CBC;
710 cipher_algo = GNUTLS_CIPHER_AES_256_CBC;
715 iv.length = gnutls_cipher_get_iv_size(cipher_algo);
716 iv.data = sec->data + (size - iv.length);
718 key.length = gnutls_cipher_get_key_size(cipher_algo);
719 key.data = sec->data + (size - (key.length + iv.length));
721 enc_xs = encrypt_blob(tctx, tctx, &key, &iv, xs, cipher_algo);
726 /* To cope with the fact that heimdal do padding at the end for the moment */
727 enc_xs->length = xs->length;
729 guid = get_cert_guid(tctx, tctx, out_blob.data, out_blob.length);
734 if (broken_version) {
737 data.version = version;
741 data.encrypted_secret = enc_sec_reverted.data;
742 data.access_check = enc_xs->data;
743 data.encrypted_secret_len = enc_sec->length;
744 data.access_check_len = enc_xs->length;
746 /* We want the blob to persist after this function so we don't
747 * allocate it in the stack
749 blob2 = talloc(tctx, DATA_BLOB);
754 ndr_err = ndr_push_struct_blob(blob2, tctx, &data,
755 (ndr_push_flags_fn_t)ndr_push_bkrp_client_side_wrapped);
756 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
760 if (broken_cert_guid) {
766 g = talloc(tctx, struct GUID);
771 status = GUID_from_string(BACKUPKEY_RESTORE_GUID, g);
772 if (!NT_STATUS_IS_OK(status)) {
776 r->in.guidActionAgent = g;
777 r->in.data_in = blob2->data;
778 r->in.data_in_len = blob2->length;
780 r->out.data_out = &(out->data);
781 r->out.data_out_len = talloc(r, uint32_t);
785 /* Check that we are able to receive the certificate of the DCs
786 * used for client wrap version of the backup key protocol
788 static bool test_RetrieveBackupKeyGUID(struct torture_context *tctx,
789 struct dcerpc_pipe *p)
791 struct dcerpc_binding_handle *b = p->binding_handle;
793 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
794 enum dcerpc_AuthType auth_type;
795 enum dcerpc_AuthLevel auth_level;
801 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
803 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
804 torture_assert_ntstatus_ok(tctx,
805 dcerpc_bkrp_BackupKey_r(b, tctx, r),
808 out_blob.length = *r->out.data_out_len;
809 torture_assert_werr_equal(tctx,
812 "Wrong dce/rpc error code");
814 torture_assert_ntstatus_equal(tctx,
815 dcerpc_bkrp_BackupKey_r(b, tctx, r),
816 NT_STATUS_ACCESS_DENIED,
822 /* Test to check the failure to recover a secret because the
823 * secret blob is not reversed
825 static bool test_RestoreGUID_ko(struct torture_context *tctx,
826 struct dcerpc_pipe *p)
828 enum ndr_err_code ndr_err;
829 struct dcerpc_binding_handle *b = p->binding_handle;
831 struct bkrp_client_side_unwrapped resp;
832 enum dcerpc_AuthType auth_type;
833 enum dcerpc_AuthLevel auth_level;
835 gnutls_global_init();
837 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
839 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
840 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
841 true, false, false, false, false, false, false);
842 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
843 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
844 out_blob.length = *r->out.data_out_len;
845 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
846 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
847 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_PARAMETER, "Wrong error code");
849 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
850 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
851 NT_STATUS_ACCESS_DENIED, "Get GUID");
854 gnutls_global_deinit();
859 static bool test_RestoreGUID_wrongversion(struct torture_context *tctx,
860 struct dcerpc_pipe *p)
862 enum ndr_err_code ndr_err;
863 struct dcerpc_binding_handle *b = p->binding_handle;
865 struct bkrp_client_side_unwrapped resp;
866 enum dcerpc_AuthType auth_type;
867 enum dcerpc_AuthLevel auth_level;
869 gnutls_global_init();
871 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
873 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
874 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
875 false, true, false, false, false, false, false);
876 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
877 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
878 out_blob.length = *r->out.data_out_len;
879 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
880 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
881 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_PARAMETER, "Wrong error code on wrong version");
883 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
884 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
885 NT_STATUS_ACCESS_DENIED, "Get GUID");
888 gnutls_global_deinit();
893 static bool test_RestoreGUID_wronguser(struct torture_context *tctx,
894 struct dcerpc_pipe *p)
896 enum ndr_err_code ndr_err;
897 struct dcerpc_binding_handle *b = p->binding_handle;
899 struct bkrp_client_side_unwrapped resp;
900 enum dcerpc_AuthType auth_type;
901 enum dcerpc_AuthLevel auth_level;
903 gnutls_global_init();
905 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
907 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
908 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
909 false, false, true, false, false, false, false);
910 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
911 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
912 out_blob.length = *r->out.data_out_len;
913 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
914 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
915 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_ACCESS, "Restore GUID");
917 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
918 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
919 NT_STATUS_ACCESS_DENIED, "Get GUID");
922 gnutls_global_deinit();
927 static bool test_RestoreGUID_v3(struct torture_context *tctx,
928 struct dcerpc_pipe *p)
930 enum ndr_err_code ndr_err;
931 struct dcerpc_binding_handle *b = p->binding_handle;
933 struct bkrp_client_side_unwrapped resp;
934 enum dcerpc_AuthType auth_type;
935 enum dcerpc_AuthLevel auth_level;
937 gnutls_global_init();
939 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
941 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
942 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 3, &out_blob,
943 false, false, false, false, false, false, false);
944 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
945 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
946 out_blob.length = *r->out.data_out_len;
947 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
948 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 1, "Unable to unmarshall bkrp_client_side_unwrapped");
949 torture_assert_werr_equal(tctx, r->out.result, WERR_OK, "Restore GUID");
950 torture_assert_str_equal(tctx, (char*)resp.secret.data, secret, "Wrong secret");
952 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
953 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
954 NT_STATUS_ACCESS_DENIED, "Get GUID");
957 gnutls_global_deinit();
962 static bool test_RestoreGUID(struct torture_context *tctx,
963 struct dcerpc_pipe *p)
965 struct dcerpc_binding_handle *b = p->binding_handle;
967 struct bkrp_client_side_unwrapped resp;
968 enum dcerpc_AuthType auth_type;
969 enum dcerpc_AuthLevel auth_level;
971 gnutls_global_init();
973 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
975 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
976 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
977 false, false, false, false, false, false, false);
978 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
979 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
980 out_blob.length = *r->out.data_out_len;
981 torture_assert_werr_equal(tctx, r->out.result, WERR_OK, "Restore GUID");
982 torture_assert_ndr_err_equal(tctx,
983 ndr_pull_struct_blob(&out_blob, tctx, &resp,
984 (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped),
986 "Unable to unmarshall bkrp_client_side_unwrapped");
987 torture_assert_str_equal(tctx, (char*)resp.secret.data, secret, "Wrong secret");
989 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
990 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
991 NT_STATUS_ACCESS_DENIED, "Get GUID");
994 gnutls_global_deinit();
999 static bool test_RestoreGUID_badmagiconsecret(struct torture_context *tctx,
1000 struct dcerpc_pipe *p)
1002 enum ndr_err_code ndr_err;
1003 struct dcerpc_binding_handle *b = p->binding_handle;
1005 struct bkrp_client_side_unwrapped resp;
1006 enum dcerpc_AuthType auth_type;
1007 enum dcerpc_AuthLevel auth_level;
1009 gnutls_global_init();
1011 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1013 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1014 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 3, &out_blob,
1015 false, false, false, true, false, false, false);
1016 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
1017 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
1018 out_blob.length = *r->out.data_out_len;
1019 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
1020 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
1021 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_DATA, "Wrong error code while providing bad magic in secret");
1023 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1024 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
1025 NT_STATUS_ACCESS_DENIED, "Get GUID");
1028 gnutls_global_deinit();
1033 static bool test_RestoreGUID_emptyrequest(struct torture_context *tctx,
1034 struct dcerpc_pipe *p)
1036 struct dcerpc_binding_handle *b = p->binding_handle;
1038 enum dcerpc_AuthType auth_type;
1039 enum dcerpc_AuthLevel auth_level;
1041 gnutls_global_init();
1043 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1045 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1046 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 3, &out_blob,
1047 false, false, false, true, false, false, true);
1049 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
1050 r->in.data_in = talloc(tctx, uint8_t);
1051 r->in.data_in_len = 0;
1053 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
1054 out_blob.length = *r->out.data_out_len;
1055 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_PARAMETER, "Bad error code on wrong has in access check");
1057 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1058 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
1059 NT_STATUS_ACCESS_DENIED, "Get GUID");
1062 gnutls_global_deinit();
1067 static bool test_RestoreGUID_badcertguid(struct torture_context *tctx,
1068 struct dcerpc_pipe *p)
1070 enum ndr_err_code ndr_err;
1071 struct dcerpc_binding_handle *b = p->binding_handle;
1073 struct bkrp_client_side_unwrapped resp;
1074 enum dcerpc_AuthType auth_type;
1075 enum dcerpc_AuthLevel auth_level;
1077 gnutls_global_init();
1079 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1081 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1082 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 3, &out_blob,
1083 false, false, false, false, false, false, true);
1084 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct() failed");
1085 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
1086 out_blob.length = *r->out.data_out_len;
1087 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
1088 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
1091 * Windows 2012R2 has, presumably, a programming error
1092 * returning an NTSTATUS code on this interface
1094 if (W_ERROR_V(r->out.result) != NT_STATUS_V(NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
1095 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_DATA, "Bad error code on wrong has in access check");
1098 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1099 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
1100 NT_STATUS_ACCESS_DENIED, "Get GUID");
1103 gnutls_global_deinit();
1108 static bool test_RestoreGUID_badmagicaccesscheck(struct torture_context *tctx,
1109 struct dcerpc_pipe *p)
1111 enum ndr_err_code ndr_err;
1112 struct dcerpc_binding_handle *b = p->binding_handle;
1114 struct bkrp_client_side_unwrapped resp;
1115 enum dcerpc_AuthType auth_type;
1116 enum dcerpc_AuthLevel auth_level;
1118 gnutls_global_init();
1120 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1122 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1123 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
1124 false, false, false, false, true, false, false);
1125 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
1126 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
1127 out_blob.length = *r->out.data_out_len;
1128 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
1129 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
1130 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_DATA, "Bad error code on wrong has in access check");
1132 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1133 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
1134 NT_STATUS_ACCESS_DENIED, "Get GUID");
1137 gnutls_global_deinit();
1142 static bool test_RestoreGUID_badhashaccesscheck(struct torture_context *tctx,
1143 struct dcerpc_pipe *p)
1145 enum ndr_err_code ndr_err;
1146 struct dcerpc_binding_handle *b = p->binding_handle;
1148 struct bkrp_client_side_unwrapped resp;
1149 enum dcerpc_AuthType auth_type;
1150 enum dcerpc_AuthLevel auth_level;
1152 gnutls_global_init();
1154 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1156 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1157 struct bkrp_BackupKey *r = createRestoreGUIDStruct(tctx, p, 2, &out_blob,
1158 false, false, false, false, false, true, false);
1159 torture_assert(tctx, r != NULL, "createRestoreGUIDStruct failed");
1160 torture_assert_ntstatus_ok(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r), "Restore GUID");
1161 out_blob.length = *r->out.data_out_len;
1162 ndr_err = ndr_pull_struct_blob(&out_blob, tctx, &resp, (ndr_pull_flags_fn_t)ndr_pull_bkrp_client_side_unwrapped);
1163 torture_assert_int_equal(tctx, NDR_ERR_CODE_IS_SUCCESS(ndr_err), 0, "Unable to unmarshall bkrp_client_side_unwrapped");
1164 torture_assert_werr_equal(tctx, r->out.result, WERR_INVALID_DATA, "Bad error code on wrong has in access check");
1166 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1167 torture_assert_ntstatus_equal(tctx, dcerpc_bkrp_BackupKey_r(b, tctx, r),
1168 NT_STATUS_ACCESS_DENIED, "Get GUID");
1171 gnutls_global_init();
1177 * Check that the RSA modulus in the certificate of the DCs has 2048 bits.
1179 static bool test_RetrieveBackupKeyGUID_validate(struct torture_context *tctx,
1180 struct dcerpc_pipe *p)
1182 struct dcerpc_binding_handle *b = p->binding_handle;
1184 struct bkrp_BackupKey *r = createRetrieveBackupKeyGUIDStruct(tctx, p, 2, &out_blob);
1185 enum dcerpc_AuthType auth_type;
1186 enum dcerpc_AuthLevel auth_level;
1188 gnutls_global_init();
1190 torture_assert(tctx, r != NULL, "test_RetrieveBackupKeyGUID_validate failed");
1196 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1198 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1199 gnutls_x509_crt_t x509_cert = NULL;
1200 gnutls_pubkey_t pubkey = NULL;
1201 gnutls_datum_t x509_crt_data;
1202 gnutls_pk_algorithm_t pubkey_algo;
1203 uint8_t dummy[1] = {0};
1204 DATA_BLOB subject_unique_id = {
1208 DATA_BLOB issuer_unique_id = {
1212 DATA_BLOB reversed = {
1216 DATA_BLOB serial_number;
1217 unsigned int RSA_returned_bits = 0;
1223 torture_assert_ntstatus_ok(tctx,
1224 dcerpc_bkrp_BackupKey_r(b, tctx, r),
1227 torture_assert_werr_ok(tctx, r->out.result,
1230 out_blob.length = *r->out.data_out_len;
1232 x509_crt_data.data = out_blob.data;
1233 x509_crt_data.size = out_blob.length;
1235 rc = gnutls_x509_crt_init(&x509_cert);
1236 if (rc != GNUTLS_E_SUCCESS) {
1240 rc = gnutls_x509_crt_import(x509_cert,
1242 GNUTLS_X509_FMT_DER);
1243 torture_assert_int_equal(tctx,
1246 "gnutls_x509_crt_import failed");
1248 /* Compare unique ids */
1250 /* Get buffer size */
1251 rc = gnutls_x509_crt_get_subject_unique_id(x509_cert,
1252 (char *)subject_unique_id.data,
1253 &subject_unique_id.length);
1254 torture_assert_int_equal(tctx,
1256 GNUTLS_E_SHORT_MEMORY_BUFFER,
1257 "gnutls_x509_crt_get_subject_unique_id "
1258 "get buffer size failed");
1260 subject_unique_id = data_blob_talloc_zero(tctx,
1261 subject_unique_id.length);
1263 rc = gnutls_x509_crt_get_subject_unique_id(x509_cert,
1264 (char *)subject_unique_id.data,
1265 &subject_unique_id.length);
1266 torture_assert_int_equal(tctx,
1269 "gnutls_x509_crt_get_subject_unique_id failed");
1271 rc = gnutls_x509_crt_get_issuer_unique_id(x509_cert,
1272 (char *)issuer_unique_id.data,
1273 &issuer_unique_id.length);
1274 torture_assert_int_equal(tctx,
1276 GNUTLS_E_SHORT_MEMORY_BUFFER,
1277 "gnutls_x509_crt_get_issuer_unique_id "
1278 "get buffer size failed");
1280 issuer_unique_id = data_blob_talloc_zero(tctx,
1281 issuer_unique_id.length);
1283 rc = gnutls_x509_crt_get_issuer_unique_id(x509_cert,
1284 (char *)issuer_unique_id.data,
1285 &issuer_unique_id.length);
1286 torture_assert_int_equal(tctx,
1289 "gnutls_x509_crt_get_issuer_unique_id failed");
1291 cmp = data_blob_cmp(&subject_unique_id, &issuer_unique_id);
1292 torture_assert(tctx,
1294 "The GUID to identify the public key is not "
1297 rc = gnutls_x509_crt_get_serial(x509_cert,
1300 torture_assert_int_equal(tctx,
1302 GNUTLS_E_SHORT_MEMORY_BUFFER,
1303 "gnutls_x509_crt_get_serial "
1304 "get buffer size failed");
1306 reversed = data_blob_talloc_zero(tctx,
1309 rc = gnutls_x509_crt_get_serial(x509_cert,
1312 torture_assert_int_equal(tctx,
1315 "gnutls_x509_crt_get_serial failed");
1318 * Heimdal sometimes adds a leading byte to the data buffer of
1319 * the serial number. So lets uses the subject_unique_id size
1320 * and ignore the leading byte.
1322 serial_number = data_blob_talloc_zero(tctx,
1323 subject_unique_id.length);
1325 for (i = 0; i < serial_number.length; i++) {
1326 serial_number.data[i] = reversed.data[reversed.length - i - 1];
1329 cmp = data_blob_cmp(&subject_unique_id, &serial_number);
1330 torture_assert(tctx,
1332 "The GUID to identify the public key is not "
1335 /* Check certificate version */
1336 version = gnutls_x509_crt_get_version(x509_cert);
1337 torture_assert_int_equal(tctx,
1340 "Invalid certificate version");
1342 /* Get the public key */
1343 rc = gnutls_pubkey_init(&pubkey);
1344 torture_assert_int_equal(tctx,
1347 "gnutls_pubkey_init failed");
1349 rc = gnutls_pubkey_import_x509(pubkey,
1352 gnutls_x509_crt_deinit(x509_cert);
1353 torture_assert_int_equal(tctx,
1356 "gnutls_pubkey_import_x509 failed");
1358 pubkey_algo = gnutls_pubkey_get_pk_algorithm(pubkey,
1359 &RSA_returned_bits);
1360 gnutls_pubkey_deinit(pubkey);
1361 torture_assert_int_equal(tctx,
1364 "gnutls_pubkey_get_pk_algorithm did "
1365 "not return a RSA key");
1366 torture_assert_int_equal(tctx,
1369 "RSA Key doesn't have 2048 bits");
1371 torture_assert_ntstatus_equal(tctx,
1372 dcerpc_bkrp_BackupKey_r(b, tctx, r),
1373 NT_STATUS_ACCESS_DENIED,
1377 gnutls_global_deinit();
1382 static bool test_ServerWrap_encrypt_decrypt(struct torture_context *tctx,
1383 struct dcerpc_pipe *p)
1385 struct bkrp_BackupKey r;
1387 DATA_BLOB plaintext = data_blob_const(secret, sizeof(secret));
1388 DATA_BLOB encrypted;
1390 DATA_BLOB decrypted;
1392 struct dcerpc_binding_handle *b = p->binding_handle;
1393 enum dcerpc_AuthType auth_type;
1394 enum dcerpc_AuthLevel auth_level;
1397 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1400 torture_assert_ntstatus_ok(tctx,
1401 GUID_from_string(BACKUPKEY_BACKUP_GUID, &guid),
1404 r.in.guidActionAgent = &guid;
1405 r.in.data_in = plaintext.data;
1406 r.in.data_in_len = plaintext.length;
1408 r.out.data_out = &encrypted.data;
1409 r.out.data_out_len = &enclen;
1410 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1411 torture_assert_ntstatus_ok(tctx,
1412 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1415 torture_assert_ntstatus_equal(tctx,
1416 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1417 NT_STATUS_ACCESS_DENIED,
1421 torture_assert_werr_ok(tctx,
1424 encrypted.length = *r.out.data_out_len;
1427 torture_assert_ntstatus_ok(tctx,
1428 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1431 r.in.guidActionAgent = &guid;
1432 r.in.data_in = encrypted.data;
1433 r.in.data_in_len = encrypted.length;
1435 r.out.data_out = &(decrypted.data);
1436 r.out.data_out_len = &declen;
1437 torture_assert_ntstatus_ok(tctx,
1438 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1440 torture_assert_werr_ok(tctx,
1443 decrypted.length = *r.out.data_out_len;
1446 torture_assert_data_blob_equal(tctx, plaintext, decrypted, "Decrypt failed");
1449 torture_assert_ntstatus_ok(tctx,
1450 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1453 r.in.guidActionAgent = &guid;
1454 r.in.data_in = encrypted.data;
1455 r.in.data_in_len = encrypted.length;
1457 r.out.data_out = &(decrypted.data);
1458 r.out.data_out_len = &declen;
1459 torture_assert_ntstatus_ok(tctx,
1460 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1462 torture_assert_werr_ok(tctx,
1465 decrypted.length = *r.out.data_out_len;
1468 torture_assert_data_blob_equal(tctx, plaintext, decrypted, "Decrypt failed");
1472 static bool test_ServerWrap_decrypt_wrong_keyGUID(struct torture_context *tctx,
1473 struct dcerpc_pipe *p)
1475 struct bkrp_BackupKey r;
1477 DATA_BLOB plaintext = data_blob_const(secret, sizeof(secret));
1478 DATA_BLOB encrypted;
1480 DATA_BLOB decrypted;
1482 struct dcerpc_binding_handle *b = p->binding_handle;
1483 enum ndr_err_code ndr_err;
1484 struct bkrp_server_side_wrapped server_side_wrapped;
1485 enum dcerpc_AuthType auth_type;
1486 enum dcerpc_AuthLevel auth_level;
1489 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1492 torture_assert_ntstatus_ok(tctx,
1493 GUID_from_string(BACKUPKEY_BACKUP_GUID, &guid),
1496 r.in.guidActionAgent = &guid;
1497 r.in.data_in = plaintext.data;
1498 r.in.data_in_len = plaintext.length;
1500 r.out.data_out = &encrypted.data;
1501 r.out.data_out_len = &enclen;
1502 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1503 torture_assert_ntstatus_ok(tctx,
1504 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1507 torture_assert_ntstatus_equal(tctx,
1508 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1509 NT_STATUS_ACCESS_DENIED,
1513 torture_assert_werr_ok(tctx,
1516 encrypted.length = *r.out.data_out_len;
1518 ndr_err = ndr_pull_struct_blob(&encrypted, tctx, &server_side_wrapped,
1519 (ndr_pull_flags_fn_t)ndr_pull_bkrp_server_side_wrapped);
1520 torture_assert_ndr_err_equal(tctx, ndr_err, NDR_ERR_SUCCESS, "pull of server_side_wrapped");
1522 /* Change the GUID */
1523 server_side_wrapped.guid = GUID_random();
1525 ndr_err = ndr_push_struct_blob(&encrypted, tctx, &server_side_wrapped,
1526 (ndr_push_flags_fn_t)ndr_push_bkrp_server_side_wrapped);
1527 torture_assert_ndr_err_equal(tctx, ndr_err, NDR_ERR_SUCCESS, "push of server_side_wrapped");
1530 torture_assert_ntstatus_ok(tctx,
1531 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1534 r.in.guidActionAgent = &guid;
1535 r.in.data_in = encrypted.data;
1536 r.in.data_in_len = encrypted.length;
1538 r.out.data_out = &(decrypted.data);
1539 r.out.data_out_len = &declen;
1540 torture_assert_ntstatus_ok(tctx,
1541 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1543 torture_assert_werr_equal(tctx,
1546 "decrypt should fail with WERR_INVALID_DATA");
1549 torture_assert_ntstatus_ok(tctx,
1550 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1553 r.in.guidActionAgent = &guid;
1554 r.in.data_in = encrypted.data;
1555 r.in.data_in_len = encrypted.length;
1557 r.out.data_out = &(decrypted.data);
1558 r.out.data_out_len = &declen;
1559 torture_assert_ntstatus_ok(tctx,
1560 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1562 torture_assert_werr_equal(tctx,
1565 "decrypt should fail with WERR_INVALID_DATA");
1570 static bool test_ServerWrap_decrypt_empty_request(struct torture_context *tctx,
1571 struct dcerpc_pipe *p)
1573 struct bkrp_BackupKey r;
1575 DATA_BLOB decrypted;
1577 struct dcerpc_binding_handle *b = p->binding_handle;
1578 uint8_t short_request[4] = { 1, 0, 0, 0 };
1579 enum dcerpc_AuthType auth_type;
1580 enum dcerpc_AuthLevel auth_level;
1583 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1586 torture_assert_ntstatus_ok(tctx,
1587 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1590 r.in.guidActionAgent = &guid;
1591 r.in.data_in = short_request;
1592 r.in.data_in_len = 0;
1594 r.out.data_out = &(decrypted.data);
1595 r.out.data_out_len = &declen;
1596 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1597 torture_assert_ntstatus_ok(tctx,
1598 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1601 torture_assert_ntstatus_equal(tctx,
1602 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1603 NT_STATUS_ACCESS_DENIED,
1607 torture_assert_werr_equal(tctx,
1609 WERR_INVALID_PARAMETER,
1610 "decrypt should fail with WERR_INVALID_PARAMETER");
1613 torture_assert_ntstatus_ok(tctx,
1614 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1617 r.in.guidActionAgent = &guid;
1618 r.in.data_in = short_request;
1619 r.in.data_in_len = 0;
1621 r.out.data_out = &(decrypted.data);
1622 r.out.data_out_len = &declen;
1623 torture_assert_ntstatus_ok(tctx,
1624 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1626 torture_assert_werr_equal(tctx,
1628 WERR_INVALID_PARAMETER,
1629 "decrypt should fail with WERR_INVALID_PARAMETER");
1632 torture_assert_ntstatus_ok(tctx,
1633 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1636 r.in.guidActionAgent = &guid;
1637 r.in.data_in = NULL;
1638 r.in.data_in_len = 0;
1640 r.out.data_out = &(decrypted.data);
1641 r.out.data_out_len = &declen;
1642 torture_assert_ntstatus_equal(tctx,
1643 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1644 NT_STATUS_INVALID_PARAMETER_MIX,
1648 torture_assert_ntstatus_ok(tctx,
1649 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1652 r.in.guidActionAgent = &guid;
1653 r.in.data_in = NULL;
1654 r.in.data_in_len = 0;
1656 r.out.data_out = &(decrypted.data);
1657 r.out.data_out_len = &declen;
1658 torture_assert_ntstatus_equal(tctx,
1659 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1660 NT_STATUS_INVALID_PARAMETER_MIX,
1667 static bool test_ServerWrap_decrypt_short_request(struct torture_context *tctx,
1668 struct dcerpc_pipe *p)
1670 struct bkrp_BackupKey r;
1672 DATA_BLOB decrypted;
1674 struct dcerpc_binding_handle *b = p->binding_handle;
1675 uint8_t short_request[4] = { 1, 0, 0, 0 };
1676 enum dcerpc_AuthType auth_type;
1677 enum dcerpc_AuthLevel auth_level;
1680 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
1683 torture_assert_ntstatus_ok(tctx,
1684 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1687 r.in.guidActionAgent = &guid;
1688 r.in.data_in = short_request;
1689 r.in.data_in_len = 4;
1691 r.out.data_out = &(decrypted.data);
1692 r.out.data_out_len = &declen;
1693 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
1694 torture_assert_ntstatus_ok(tctx,
1695 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1698 torture_assert_ntstatus_equal(tctx,
1699 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1700 NT_STATUS_ACCESS_DENIED,
1704 torture_assert_werr_equal(tctx,
1706 WERR_INVALID_PARAMETER,
1707 "decrypt should fail with WERR_INVALID_PARM");
1710 torture_assert_ntstatus_ok(tctx,
1711 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1714 r.in.guidActionAgent = &guid;
1715 r.in.data_in = short_request;
1716 r.in.data_in_len = 4;
1718 r.out.data_out = &(decrypted.data);
1719 r.out.data_out_len = &declen;
1720 torture_assert_ntstatus_ok(tctx,
1721 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1723 torture_assert_werr_equal(tctx,
1725 WERR_INVALID_PARAMETER,
1726 "decrypt should fail with WERR_INVALID_PARAMETER");
1729 torture_assert_ntstatus_ok(tctx,
1730 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
1733 r.in.guidActionAgent = &guid;
1734 r.in.data_in = short_request;
1735 r.in.data_in_len = 1;
1737 r.out.data_out = &(decrypted.data);
1738 r.out.data_out_len = &declen;
1739 torture_assert_ntstatus_ok(tctx,
1740 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1742 torture_assert_werr_equal(tctx,
1744 WERR_INVALID_PARAMETER,
1745 "decrypt should fail with WERR_INVALID_PARAMETER");
1748 torture_assert_ntstatus_ok(tctx,
1749 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
1752 r.in.guidActionAgent = &guid;
1753 r.in.data_in = short_request;
1754 r.in.data_in_len = 1;
1756 r.out.data_out = &(decrypted.data);
1757 r.out.data_out_len = &declen;
1758 torture_assert_ntstatus_ok(tctx,
1759 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
1761 torture_assert_werr_equal(tctx,
1763 WERR_INVALID_PARAMETER,
1764 "decrypt should fail with WERR_INVALID_PARAMETER");
1769 static bool test_ServerWrap_encrypt_decrypt_manual(struct torture_context *tctx,
1770 struct bkrp_server_side_wrapped *server_side_wrapped,
1771 enum test_wrong wrong)
1773 char *lsa_binding_string = NULL;
1774 struct dcerpc_binding *lsa_binding = NULL;
1775 struct dcerpc_pipe *lsa_p = NULL;
1776 struct dcerpc_binding_handle *lsa_b = NULL;
1777 struct lsa_OpenSecret r_secret;
1778 struct lsa_QuerySecret r_query_secret;
1779 struct policy_handle *handle, sec_handle;
1780 struct bkrp_BackupKey r;
1781 struct GUID preferred_key_guid;
1782 DATA_BLOB plaintext = data_blob_const(secret, sizeof(secret));
1783 DATA_BLOB preferred_key, preferred_key_clear, session_key,
1784 decrypt_key, decrypt_key_clear, encrypted_blob,
1786 struct bkrp_dc_serverwrap_key server_key;
1787 struct lsa_DATA_BUF_PTR bufp1;
1788 char *key_guid_string;
1789 struct bkrp_rc4encryptedpayload rc4payload;
1790 struct dom_sid *caller_sid;
1791 uint8_t symkey[20]; /* SHA-1 hash len */
1792 uint8_t mackey[20]; /* SHA-1 hash len */
1793 uint8_t mac[20]; /* SHA-1 hash len */
1794 gnutls_hmac_hd_t hmac_hnd;
1795 gnutls_cipher_hd_t cipher_hnd;
1796 gnutls_datum_t cipher_key;
1800 ZERO_STRUCT(r_secret);
1801 ZERO_STRUCT(r_query_secret);
1803 /* Now read BCKUPKEY_P and prove we can do a matching decrypt and encrypt */
1805 /* lsa_OpenSecret only works with ncacn_np and AUTH_LEVEL_NONE */
1806 lsa_binding_string = talloc_asprintf(tctx, "ncacn_np:%s",
1807 torture_setting_string(tctx, "host", NULL));
1808 torture_assert(tctx, lsa_binding_string != NULL, "lsa_binding_string");
1810 torture_assert_ntstatus_ok(tctx,
1811 dcerpc_parse_binding(tctx, lsa_binding_string, &lsa_binding),
1812 "Failed to parse dcerpc binding");
1814 torture_assert_ntstatus_ok(tctx,
1815 dcerpc_pipe_connect_b(tctx, &lsa_p,
1816 lsa_binding, &ndr_table_lsarpc,
1817 cmdline_credentials, tctx->ev, tctx->lp_ctx),
1818 "Opening LSA pipe");
1819 lsa_b = lsa_p->binding_handle;
1821 torture_assert(tctx, test_lsa_OpenPolicy2(lsa_b, tctx, &handle), "OpenPolicy failed");
1822 r_secret.in.name.string = "G$BCKUPKEY_P";
1824 r_secret.in.handle = handle;
1825 r_secret.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1826 r_secret.out.sec_handle = &sec_handle;
1828 torture_comment(tctx, "Testing OpenSecret\n");
1830 torture_assert_ntstatus_ok(tctx, dcerpc_lsa_OpenSecret_r(lsa_b, tctx, &r_secret),
1831 "OpenSecret failed");
1832 torture_assert_ntstatus_ok(tctx, r_secret.out.result,
1833 "OpenSecret failed");
1835 r_query_secret.in.sec_handle = &sec_handle;
1836 r_query_secret.in.new_val = &bufp1;
1839 torture_assert_ntstatus_ok(tctx, dcerpc_lsa_QuerySecret_r(lsa_b, tctx, &r_query_secret),
1840 "QuerySecret failed");
1841 torture_assert_ntstatus_ok(tctx, r_query_secret.out.result,
1842 "QuerySecret failed");
1845 preferred_key.data = r_query_secret.out.new_val->buf->data;
1846 preferred_key.length = r_query_secret.out.new_val->buf->size;
1847 torture_assert_ntstatus_ok(tctx, dcerpc_fetch_session_key(lsa_p, &session_key),
1848 "dcerpc_fetch_session_key failed");
1850 torture_assert_ntstatus_ok(tctx,
1851 sess_decrypt_blob(tctx,
1852 &preferred_key, &session_key, &preferred_key_clear),
1853 "sess_decrypt_blob failed");
1855 torture_assert_ntstatus_ok(tctx, GUID_from_ndr_blob(&preferred_key_clear, &preferred_key_guid),
1856 "GUID parse failed");
1858 torture_assert_guid_equal(tctx, server_side_wrapped->guid,
1860 "GUID didn't match value pointed at by G$BCKUPKEY_P");
1862 /* And read BCKUPKEY_<guid> and get the actual key */
1864 key_guid_string = GUID_string(tctx, &server_side_wrapped->guid);
1865 r_secret.in.name.string = talloc_asprintf(tctx, "G$BCKUPKEY_%s", key_guid_string);
1867 r_secret.in.handle = handle;
1868 r_secret.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1869 r_secret.out.sec_handle = &sec_handle;
1871 torture_comment(tctx, "Testing OpenSecret\n");
1873 torture_assert_ntstatus_ok(tctx, dcerpc_lsa_OpenSecret_r(lsa_b, tctx, &r_secret),
1874 "OpenSecret failed");
1875 torture_assert_ntstatus_ok(tctx, r_secret.out.result,
1876 "OpenSecret failed");
1878 r_query_secret.in.sec_handle = &sec_handle;
1879 r_query_secret.in.new_val = &bufp1;
1881 torture_assert_ntstatus_ok(tctx, dcerpc_lsa_QuerySecret_r(lsa_b, tctx, &r_query_secret),
1882 "QuerySecret failed");
1883 torture_assert_ntstatus_ok(tctx, r_query_secret.out.result,
1884 "QuerySecret failed");
1887 decrypt_key.data = r_query_secret.out.new_val->buf->data;
1888 decrypt_key.length = r_query_secret.out.new_val->buf->size;
1890 torture_assert_ntstatus_ok(tctx,
1891 sess_decrypt_blob(tctx,
1892 &decrypt_key, &session_key, &decrypt_key_clear),
1893 "sess_decrypt_blob failed");
1895 torture_assert_ndr_err_equal(tctx, ndr_pull_struct_blob(&decrypt_key_clear, tctx, &server_key,
1896 (ndr_pull_flags_fn_t)ndr_pull_bkrp_dc_serverwrap_key),
1897 NDR_ERR_SUCCESS, "Failed to parse server_key");
1899 torture_assert_int_equal(tctx, server_key.magic, 1, "Failed to correctly decrypt server key");
1902 * This is *not* the leading 64 bytes, as indicated in MS-BKRP 3.1.4.1.1
1903 * BACKUPKEY_BACKUP_GUID, it really is the whole key
1905 gnutls_hmac_init(&hmac_hnd,
1908 sizeof(server_key.key));
1909 gnutls_hmac(hmac_hnd,
1910 server_side_wrapped->r2,
1911 sizeof(server_side_wrapped->r2));
1912 gnutls_hmac_output(hmac_hnd, symkey);
1914 /* rc4 decrypt sid and secret using sym key */
1915 cipher_key.data = symkey;
1916 cipher_key.size = sizeof(symkey);
1918 encrypted_blob = data_blob_talloc(tctx, server_side_wrapped->rc4encryptedpayload,
1919 server_side_wrapped->ciphertext_length);
1921 rc = gnutls_cipher_init(&cipher_hnd,
1922 GNUTLS_CIPHER_ARCFOUR_128,
1925 torture_assert_int_equal(tctx,
1928 "gnutls_cipher_init failed");
1929 rc = gnutls_cipher_encrypt2(cipher_hnd,
1930 encrypted_blob.data,
1931 encrypted_blob.length,
1932 encrypted_blob.data,
1933 encrypted_blob.length);
1934 torture_assert_int_equal(tctx,
1937 "gnutls_cipher_encrypt failed");
1938 gnutls_cipher_deinit(cipher_hnd);
1940 torture_assert_ndr_err_equal(tctx, ndr_pull_struct_blob(&encrypted_blob, tctx, &rc4payload,
1941 (ndr_pull_flags_fn_t)ndr_pull_bkrp_rc4encryptedpayload),
1942 NDR_ERR_SUCCESS, "Failed to parse rc4encryptedpayload");
1944 torture_assert_int_equal(tctx, rc4payload.secret_data.length,
1945 server_side_wrapped->payload_length,
1946 "length of decrypted payload not the length declared in surrounding structure");
1949 * This is *not* the leading 64 bytes, as indicated in MS-BKRP 3.1.4.1.1
1950 * BACKUPKEY_BACKUP_GUID, it really is the whole key
1952 gnutls_hmac(hmac_hnd,
1954 sizeof(rc4payload.r3));
1955 gnutls_hmac_deinit(hmac_hnd, mackey);
1957 torture_assert_ndr_err_equal(tctx, ndr_push_struct_blob(&sid_blob, tctx, &rc4payload.sid,
1958 (ndr_push_flags_fn_t)ndr_push_dom_sid),
1959 NDR_ERR_SUCCESS, "unable to push SID");
1961 gnutls_hmac_init(&hmac_hnd,
1966 gnutls_hmac(hmac_hnd,
1970 gnutls_hmac(hmac_hnd,
1971 rc4payload.secret_data.data,
1972 rc4payload.secret_data.length);
1973 gnutls_hmac_output(hmac_hnd, mac);
1975 torture_assert_mem_equal(tctx, mac, rc4payload.mac, sizeof(mac), "mac not correct");
1976 torture_assert_int_equal(tctx, rc4payload.secret_data.length,
1977 plaintext.length, "decrypted data is not correct length");
1978 torture_assert_mem_equal(tctx, rc4payload.secret_data.data,
1979 plaintext.data, plaintext.length,
1980 "decrypted data is not correct");
1982 /* Not strictly correct all the time, but good enough for this test */
1983 caller_sid = get_user_sid(tctx, tctx, cli_credentials_get_username(cmdline_credentials));
1985 torture_assert_sid_equal(tctx, &rc4payload.sid, caller_sid, "Secret saved with wrong SID");
1990 if (wrong == WRONG_SID) {
1991 rc4payload.sid.sub_auths[rc4payload.sid.num_auths - 1] = DOMAIN_RID_KRBTGT;
1994 dump_data_pw("mackey: \n", mackey, sizeof(mackey));
1996 torture_assert_ndr_err_equal(tctx,
1997 ndr_push_struct_blob(&sid_blob, tctx, &rc4payload.sid,
1998 (ndr_push_flags_fn_t)ndr_push_dom_sid),
2000 "push of sid failed");
2003 gnutls_hmac(hmac_hnd,
2007 gnutls_hmac(hmac_hnd,
2008 rc4payload.secret_data.data,
2009 rc4payload.secret_data.length);
2010 gnutls_hmac_deinit(hmac_hnd, rc4payload.mac);
2012 dump_data_pw("rc4payload.mac: \n", rc4payload.mac, sizeof(rc4payload.mac));
2014 torture_assert_ndr_err_equal(tctx,
2015 ndr_push_struct_blob(&encrypted_blob, tctx, &rc4payload,
2016 (ndr_push_flags_fn_t)ndr_push_bkrp_rc4encryptedpayload),
2018 "push of rc4payload failed");
2020 if (wrong == WRONG_KEY) {
2026 /* rc4 encrypt sid and secret using sym key */
2027 cipher_key.data = symkey;
2028 cipher_key.size = sizeof(symkey);
2030 rc = gnutls_cipher_init(&cipher_hnd,
2031 GNUTLS_CIPHER_ARCFOUR_128,
2034 torture_assert_int_equal(tctx,
2037 "gnutls_cipher_init failed");
2038 rc = gnutls_cipher_encrypt2(cipher_hnd,
2039 encrypted_blob.data,
2040 encrypted_blob.length,
2041 encrypted_blob.data,
2042 encrypted_blob.length);
2043 torture_assert_int_equal(tctx,
2046 "gnutls_cipher_encrypt failed");
2047 gnutls_cipher_deinit(cipher_hnd);
2050 /* re-create server wrap structure */
2052 torture_assert_int_equal(tctx, encrypted_blob.length,
2053 server_side_wrapped->ciphertext_length,
2054 "expected encrypted length not to change");
2055 if (wrong == RIGHT_KEY) {
2056 torture_assert_mem_equal(tctx, server_side_wrapped->rc4encryptedpayload,
2057 encrypted_blob.data,
2058 encrypted_blob.length,
2059 "expected encrypted data not to change");
2062 server_side_wrapped->payload_length = rc4payload.secret_data.length;
2063 server_side_wrapped->ciphertext_length = encrypted_blob.length;
2064 server_side_wrapped->rc4encryptedpayload = encrypted_blob.data;
2070 static bool test_ServerWrap_decrypt_wrong_stuff(struct torture_context *tctx,
2071 struct dcerpc_pipe *p,
2072 enum test_wrong wrong)
2074 struct bkrp_BackupKey r;
2076 DATA_BLOB plaintext = data_blob_const(secret, sizeof(secret));
2077 DATA_BLOB encrypted;
2079 DATA_BLOB decrypted;
2081 struct dcerpc_binding_handle *b = p->binding_handle;
2082 enum ndr_err_code ndr_err;
2083 struct bkrp_server_side_wrapped server_side_wrapped;
2084 bool repush = false;
2085 enum dcerpc_AuthType auth_type;
2086 enum dcerpc_AuthLevel auth_level;
2089 gnutls_global_init();
2091 dcerpc_binding_handle_auth_info(b, &auth_type, &auth_level);
2094 torture_assert_ntstatus_ok(tctx,
2095 GUID_from_string(BACKUPKEY_BACKUP_GUID, &guid),
2098 r.in.guidActionAgent = &guid;
2099 r.in.data_in = plaintext.data;
2100 r.in.data_in_len = plaintext.length;
2102 r.out.data_out = &encrypted.data;
2103 r.out.data_out_len = &enclen;
2104 if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
2105 torture_assert_ntstatus_ok(tctx,
2106 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
2109 torture_assert_ntstatus_equal(tctx,
2110 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
2111 NT_STATUS_ACCESS_DENIED,
2115 torture_assert_werr_ok(tctx,
2118 encrypted.length = *r.out.data_out_len;
2120 ndr_err = ndr_pull_struct_blob(&encrypted, tctx, &server_side_wrapped,
2121 (ndr_pull_flags_fn_t)ndr_pull_bkrp_server_side_wrapped);
2122 torture_assert_ndr_err_equal(tctx, ndr_err, NDR_ERR_SUCCESS, "pull of server_side_wrapped");
2124 torture_assert_int_equal(tctx, server_side_wrapped.payload_length, plaintext.length,
2125 "wrong payload length");
2129 /* Change the magic. Forced by our NDR layer, so do it raw */
2130 SIVAL(encrypted.data, 0, 78); /* valid values are 1-3 */
2133 server_side_wrapped.r2[0] = 78;
2134 server_side_wrapped.r2[1] = 78;
2135 server_side_wrapped.r2[3] = 78;
2138 case WRONG_PAYLOAD_LENGTH:
2139 server_side_wrapped.payload_length = UINT32_MAX - 8;
2142 case WRONG_CIPHERTEXT_LENGTH:
2144 * Change the ciphertext len. We can't push this if
2145 * we have it wrong, so do it raw
2147 SIVAL(encrypted.data, 8, UINT32_MAX - 8); /* valid values are 1-3 */
2149 case SHORT_PAYLOAD_LENGTH:
2150 server_side_wrapped.payload_length = server_side_wrapped.payload_length - 8;
2153 case SHORT_CIPHERTEXT_LENGTH:
2155 * Change the ciphertext len. We can't push this if
2156 * we have it wrong, so do it raw
2158 SIVAL(encrypted.data, 8, server_side_wrapped.ciphertext_length - 8); /* valid values are 1-3 */
2160 case ZERO_PAYLOAD_LENGTH:
2161 server_side_wrapped.payload_length = 0;
2164 case ZERO_CIPHERTEXT_LENGTH:
2166 * Change the ciphertext len. We can't push this if
2167 * we have it wrong, so do it raw
2169 SIVAL(encrypted.data, 8, 0); /* valid values are 1-3 */
2175 torture_assert(tctx,
2176 test_ServerWrap_encrypt_decrypt_manual(tctx, &server_side_wrapped, wrong),
2177 "test_ServerWrap_encrypt_decrypt_manual failed");
2183 ndr_err = ndr_push_struct_blob(&encrypted, tctx, &server_side_wrapped,
2184 (ndr_push_flags_fn_t)ndr_push_bkrp_server_side_wrapped);
2185 torture_assert_ndr_err_equal(tctx, ndr_err, NDR_ERR_SUCCESS, "push of server_side_wrapped");
2189 torture_assert_ntstatus_ok(tctx,
2190 GUID_from_string(BACKUPKEY_RESTORE_GUID, &guid),
2193 r.in.guidActionAgent = &guid;
2194 r.in.data_in = encrypted.data;
2195 r.in.data_in_len = encrypted.length;
2197 r.out.data_out = &(decrypted.data);
2198 r.out.data_out_len = &declen;
2199 torture_assert_ntstatus_ok(tctx,
2200 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
2203 if ((wrong == WRONG_R2 || wrong == WRONG_KEY)
2204 && W_ERROR_EQUAL(r.out.result, WERR_INVALID_SID)) {
2205 torture_assert_werr_equal(tctx,
2208 "decrypt should fail with WERR_INVALID_SID or WERR_INVALID_PARAMETER");
2209 } else if (wrong == RIGHT_KEY) {
2210 torture_assert_werr_equal(tctx,
2213 "decrypt should succeed!");
2214 } else if (wrong == WRONG_SID) {
2215 torture_assert_werr_equal(tctx,
2217 WERR_INVALID_ACCESS,
2218 "decrypt should fail with WERR_INVALID_ACCESS");
2220 if (!W_ERROR_EQUAL(r.out.result, WERR_INVALID_ACCESS)
2221 && !W_ERROR_EQUAL(r.out.result, WERR_INVALID_PARAMETER)) {
2222 torture_assert_werr_equal(tctx, r.out.result,
2224 "decrypt should fail with WERR_INVALID_ACCESS, WERR_INVALID_PARAMETER or WERR_INVALID_DATA");
2229 torture_assert_ntstatus_ok(tctx,
2230 GUID_from_string(BACKUPKEY_RESTORE_GUID_WIN2K, &guid),
2233 r.in.guidActionAgent = &guid;
2234 r.in.data_in = encrypted.data;
2235 r.in.data_in_len = encrypted.length;
2237 r.out.data_out = &(decrypted.data);
2238 r.out.data_out_len = &declen;
2239 torture_assert_ntstatus_ok(tctx,
2240 dcerpc_bkrp_BackupKey_r(b, tctx, &r),
2243 if ((wrong == WRONG_R2 || wrong == WRONG_KEY)
2244 && W_ERROR_EQUAL(r.out.result, WERR_INVALID_SID)) {
2245 torture_assert_werr_equal(tctx,
2248 "decrypt should fail with WERR_INVALID_SID or WERR_INVALID_PARAMETER");
2249 } else if (wrong == RIGHT_KEY) {
2250 torture_assert_werr_equal(tctx,
2253 "decrypt should succeed!");
2254 } else if (wrong == WRONG_SID) {
2255 torture_assert_werr_equal(tctx,
2257 WERR_INVALID_ACCESS,
2258 "decrypt should fail with WERR_INVALID_ACCESS");
2260 torture_assert_werr_equal(tctx,
2262 WERR_INVALID_PARAMETER,
2263 "decrypt should fail with WERR_INVALID_PARAMETER");
2266 gnutls_global_deinit();
2271 static bool test_ServerWrap_decrypt_wrong_magic(struct torture_context *tctx,
2272 struct dcerpc_pipe *p)
2274 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_MAGIC);
2277 static bool test_ServerWrap_decrypt_wrong_r2(struct torture_context *tctx,
2278 struct dcerpc_pipe *p)
2280 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_R2);
2283 static bool test_ServerWrap_decrypt_wrong_payload_length(struct torture_context *tctx,
2284 struct dcerpc_pipe *p)
2286 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_PAYLOAD_LENGTH);
2289 static bool test_ServerWrap_decrypt_short_payload_length(struct torture_context *tctx,
2290 struct dcerpc_pipe *p)
2292 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, SHORT_PAYLOAD_LENGTH);
2295 static bool test_ServerWrap_decrypt_zero_payload_length(struct torture_context *tctx,
2296 struct dcerpc_pipe *p)
2298 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, ZERO_PAYLOAD_LENGTH);
2301 static bool test_ServerWrap_decrypt_wrong_ciphertext_length(struct torture_context *tctx,
2302 struct dcerpc_pipe *p)
2304 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_CIPHERTEXT_LENGTH);
2307 static bool test_ServerWrap_decrypt_short_ciphertext_length(struct torture_context *tctx,
2308 struct dcerpc_pipe *p)
2310 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, SHORT_CIPHERTEXT_LENGTH);
2313 static bool test_ServerWrap_decrypt_zero_ciphertext_length(struct torture_context *tctx,
2314 struct dcerpc_pipe *p)
2316 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, ZERO_CIPHERTEXT_LENGTH);
2319 static bool test_ServerWrap_encrypt_decrypt_remote_key(struct torture_context *tctx,
2320 struct dcerpc_pipe *p)
2322 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, RIGHT_KEY);
2325 static bool test_ServerWrap_encrypt_decrypt_wrong_key(struct torture_context *tctx,
2326 struct dcerpc_pipe *p)
2328 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_KEY);
2331 static bool test_ServerWrap_encrypt_decrypt_wrong_sid(struct torture_context *tctx,
2332 struct dcerpc_pipe *p)
2334 return test_ServerWrap_decrypt_wrong_stuff(tctx, p, WRONG_SID);
2337 struct torture_suite *torture_rpc_backupkey(TALLOC_CTX *mem_ctx)
2339 struct torture_suite *suite = torture_suite_create(mem_ctx, "backupkey");
2341 struct torture_rpc_tcase *tcase;
2343 tcase = torture_suite_add_rpc_iface_tcase(suite, "backupkey",
2344 &ndr_table_backupkey);
2346 torture_rpc_tcase_add_test(tcase, "retreive_backup_key_guid",
2347 test_RetrieveBackupKeyGUID);
2349 torture_rpc_tcase_add_test(tcase, "restore_guid",
2352 torture_rpc_tcase_add_test(tcase, "restore_guid version 3",
2353 test_RestoreGUID_v3);
2355 /* We double the test in order to be sure that we don't mess stuff (ie. freeing static stuff) */
2357 torture_rpc_tcase_add_test(tcase, "restore_guid_2nd",
2360 torture_rpc_tcase_add_test(tcase, "unable_to_decrypt_secret",
2361 test_RestoreGUID_ko);
2363 torture_rpc_tcase_add_test(tcase, "wrong_user_restore_guid",
2364 test_RestoreGUID_wronguser);
2366 torture_rpc_tcase_add_test(tcase, "wrong_version_restore_guid",
2367 test_RestoreGUID_wrongversion);
2369 torture_rpc_tcase_add_test(tcase, "bad_magic_on_secret_restore_guid",
2370 test_RestoreGUID_badmagiconsecret);
2372 torture_rpc_tcase_add_test(tcase, "bad_hash_on_secret_restore_guid",
2373 test_RestoreGUID_badhashaccesscheck);
2375 torture_rpc_tcase_add_test(tcase, "bad_magic_on_accesscheck_restore_guid",
2376 test_RestoreGUID_badmagicaccesscheck);
2378 torture_rpc_tcase_add_test(tcase, "bad_cert_guid_restore_guid",
2379 test_RestoreGUID_badcertguid);
2381 torture_rpc_tcase_add_test(tcase, "empty_request_restore_guid",
2382 test_RestoreGUID_emptyrequest);
2384 torture_rpc_tcase_add_test(tcase, "retreive_backup_key_guid_validate",
2385 test_RetrieveBackupKeyGUID_validate);
2387 torture_rpc_tcase_add_test(tcase, "server_wrap_encrypt_decrypt",
2388 test_ServerWrap_encrypt_decrypt);
2390 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_wrong_keyGUID",
2391 test_ServerWrap_decrypt_wrong_keyGUID);
2393 torture_rpc_tcase_add_test(tcase, "server_wrap_empty_request",
2394 test_ServerWrap_decrypt_empty_request);
2396 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_short_request",
2397 test_ServerWrap_decrypt_short_request);
2399 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_wrong_magic",
2400 test_ServerWrap_decrypt_wrong_magic);
2402 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_wrong_r2",
2403 test_ServerWrap_decrypt_wrong_r2);
2405 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_wrong_payload_length",
2406 test_ServerWrap_decrypt_wrong_payload_length);
2408 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_short_payload_length",
2409 test_ServerWrap_decrypt_short_payload_length);
2411 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_zero_payload_length",
2412 test_ServerWrap_decrypt_zero_payload_length);
2414 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_wrong_ciphertext_length",
2415 test_ServerWrap_decrypt_wrong_ciphertext_length);
2417 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_short_ciphertext_length",
2418 test_ServerWrap_decrypt_short_ciphertext_length);
2420 torture_rpc_tcase_add_test(tcase, "server_wrap_decrypt_zero_ciphertext_length",
2421 test_ServerWrap_decrypt_zero_ciphertext_length);
2423 torture_rpc_tcase_add_test(tcase, "server_wrap_encrypt_decrypt_remote_key",
2424 test_ServerWrap_encrypt_decrypt_remote_key);
2426 torture_rpc_tcase_add_test(tcase, "server_wrap_encrypt_decrypt_wrong_key",
2427 test_ServerWrap_encrypt_decrypt_wrong_key);
2429 torture_rpc_tcase_add_test(tcase, "server_wrap_encrypt_decrypt_wrong_sid",
2430 test_ServerWrap_encrypt_decrypt_wrong_sid);