s4:torture/netlogon: add/use test_SetupCredentialsPipe() helper function
[samba.git] / source4 / torture / rpc / drsuapi_cracknames.c
1 /* 
2    Unix SMB/CIFS implementation.
3
4    DRSUapi tests
5
6    Copyright (C) Andrew Tridgell 2003
7    Copyright (C) Stefan (metze) Metzmacher 2004
8    Copyright (C) Andrew Bartlett <abartlet@samba.org> 2005
9
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 3 of the License, or
13    (at your option) any later version.
14    
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19    
20    You should have received a copy of the GNU General Public License
21    along with this program.  If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #include "includes.h"
25 #include "librpc/gen_ndr/ndr_drsuapi_c.h"
26 #include "torture/rpc/torture_rpc.h"
27 #include <ldb.h>
28 #include "libcli/security/security.h"
29
30 struct DsCrackNamesPrivate {
31         struct DsPrivate base;
32
33         /* following names are used in Crack Names Matrix test */
34         const char *fqdn_name;
35         const char *user_principal_name;
36         const char *service_principal_name;
37 };
38
39 static bool test_DsCrackNamesMatrix(struct torture_context *tctx,
40                                     struct DsPrivate *priv, const char *dn,
41                                     const char *user_principal_name, const char *service_principal_name)
42 {
43         NTSTATUS status;
44         const char *err_msg;
45         struct drsuapi_DsCrackNames r;
46         union drsuapi_DsNameRequest req;
47         uint32_t level_out;
48         union drsuapi_DsNameCtr ctr;
49         struct dcerpc_pipe *p = priv->drs_pipe;
50         TALLOC_CTX *mem_ctx = priv;
51
52         enum drsuapi_DsNameFormat formats[] = {
53                 DRSUAPI_DS_NAME_FORMAT_UNKNOWN,
54                 DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
55                 DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
56                 DRSUAPI_DS_NAME_FORMAT_DISPLAY,
57                 DRSUAPI_DS_NAME_FORMAT_GUID,
58                 DRSUAPI_DS_NAME_FORMAT_CANONICAL,
59                 DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
60                 DRSUAPI_DS_NAME_FORMAT_CANONICAL_EX,
61                 DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
62                 DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
63                 DRSUAPI_DS_NAME_FORMAT_DNS_DOMAIN
64         };
65         struct drsuapi_DsNameString names[ARRAY_SIZE(formats)];
66         int i, j;
67
68         const char *n_matrix[ARRAY_SIZE(formats)][ARRAY_SIZE(formats)];
69         const char *n_from[ARRAY_SIZE(formats)];
70
71         ZERO_STRUCT(r);
72         r.in.bind_handle                = &priv->bind_handle;
73         r.in.level                      = 1;
74         r.in.req                        = &req;
75         r.in.req->req1.codepage         = 1252; /* german */
76         r.in.req->req1.language         = 0x00000407; /* german */
77         r.in.req->req1.count            = 1;
78         r.in.req->req1.names            = names;
79         r.in.req->req1.format_flags     = DRSUAPI_DS_NAME_FLAG_NO_FLAGS;
80
81         r.out.level_out                 = &level_out;
82         r.out.ctr                       = &ctr;
83
84         n_matrix[0][0] = dn;
85
86         for (i = 0; i < ARRAY_SIZE(formats); i++) {
87                 r.in.req->req1.format_offered   = DRSUAPI_DS_NAME_FORMAT_FQDN_1779;
88                 r.in.req->req1.format_desired   = formats[i];
89                 names[0].str = dn;
90                 torture_comment(tctx, "Testing DsCrackNames (matrix prep) with name '%s'"
91                                       " offered format: %d desired format:%d\n",
92                                 names[0].str,
93                                 r.in.req->req1.format_offered,
94                                 r.in.req->req1.format_desired);
95                 status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
96                 if (!NT_STATUS_IS_OK(status)) {
97                         const char *errstr = nt_errstr(status);
98                         err_msg = talloc_asprintf(mem_ctx,
99                                         "testing DsCrackNames (matrix prep) with name '%s' from format: %d desired format:%d failed - %s",
100                                         names[0].str, r.in.req->req1.format_offered, r.in.req->req1.format_desired, errstr);
101                         torture_fail(tctx, err_msg);
102                 } else if (!W_ERROR_IS_OK(r.out.result)) {
103                         err_msg = talloc_asprintf(mem_ctx,
104                                         "testing DsCrackNames (matrix prep) with name '%s' from format: %d desired format:%d failed - %s",
105                                names[0].str, r.in.req->req1.format_offered, r.in.req->req1.format_desired, win_errstr(r.out.result));
106                         torture_fail(tctx, err_msg);
107                 }
108                         
109                 switch (formats[i]) {
110                 case DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL:  
111                         if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE) {
112                                 err_msg = talloc_asprintf(mem_ctx,
113                                                 "Unexpected error (%d): This name lookup should fail",
114                                                 r.out.ctr->ctr1->array[0].status);
115                                 torture_fail(tctx, err_msg);
116                         }
117                         torture_comment(tctx, __location__ ": (expected) error\n");
118                         break;
119                 case DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL:
120                         if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_NO_MAPPING) {
121                                 err_msg = talloc_asprintf(mem_ctx,
122                                                 "Unexpected error (%d): This name lookup should fail",
123                                                 r.out.ctr->ctr1->array[0].status);
124                                 torture_fail(tctx, err_msg);
125                         }
126                         torture_comment(tctx, __location__ ": (expected) error\n");
127                         break;
128                 case DRSUAPI_DS_NAME_FORMAT_UNKNOWN:    /* should fail as we ask server to convert to Unknown format */
129                 case DRSUAPI_DS_NAME_FORMAT_DNS_DOMAIN: 
130                 case DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY: 
131                         if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_RESOLVE_ERROR) {
132                                 err_msg = talloc_asprintf(mem_ctx,
133                                                 "Unexpected error (%d): This name lookup should fail",
134                                                 r.out.ctr->ctr1->array[0].status);
135                                 torture_fail(tctx, err_msg);
136                         }
137                         torture_comment(tctx, __location__ ": (expected) error\n");
138                         break;
139                 default:
140                         if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
141                                 err_msg = talloc_asprintf(mem_ctx,
142                                                 "DsCrackNames error: %d",
143                                                 r.out.ctr->ctr1->array[0].status);
144                                 torture_fail(tctx, err_msg);
145                         }
146                         break;
147                 }
148
149                 switch (formats[i]) {
150                 case DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL:
151                         n_from[i] = user_principal_name;
152                         break;
153                 case DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL:  
154                         n_from[i] = service_principal_name;
155                         break;
156                 case DRSUAPI_DS_NAME_FORMAT_UNKNOWN:
157                 case DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY: 
158                 case DRSUAPI_DS_NAME_FORMAT_DNS_DOMAIN: 
159                         n_from[i] = NULL;
160                         break;
161                 default:
162                         n_from[i] = r.out.ctr->ctr1->array[0].result_name;
163                         printf("%s\n", n_from[i]);
164                         break;
165                 }
166         }
167
168         for (i = 0; i < ARRAY_SIZE(formats); i++) {
169                 for (j = 0; j < ARRAY_SIZE(formats); j++) {
170                         r.in.req->req1.format_offered   = formats[i];
171                         r.in.req->req1.format_desired   = formats[j];
172                         if (!n_from[i]) {
173                                 n_matrix[i][j] = NULL;
174                                 continue;
175                         }
176                         names[0].str = n_from[i];
177                         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
178                         if (!NT_STATUS_IS_OK(status)) {
179                                 const char *errstr = nt_errstr(status);
180                                 err_msg = talloc_asprintf(mem_ctx,
181                                                 "testing DsCrackNames (matrix) with name '%s' from format: %d desired format:%d failed - %s",
182                                                 names[0].str, r.in.req->req1.format_offered, r.in.req->req1.format_desired, errstr);
183                                 torture_fail(tctx, err_msg);
184                         } else if (!W_ERROR_IS_OK(r.out.result)) {
185                                 err_msg = talloc_asprintf(mem_ctx,
186                                                 "testing DsCrackNames (matrix) with name '%s' from format: %d desired format:%d failed - %s",
187                                                 names[0].str, r.in.req->req1.format_offered, r.in.req->req1.format_desired,
188                                                 win_errstr(r.out.result));
189                                 torture_fail(tctx, err_msg);
190                         }
191                         
192                         if (r.out.ctr->ctr1->array[0].status == DRSUAPI_DS_NAME_STATUS_OK) {
193                                 n_matrix[i][j] = r.out.ctr->ctr1->array[0].result_name;
194                         } else {
195                                 n_matrix[i][j] = NULL;
196                         }
197                 }
198         }
199
200         for (i = 0; i < ARRAY_SIZE(formats); i++) {
201                 for (j = 0; j < ARRAY_SIZE(formats); j++) {
202                         torture_comment(tctx, "Converting %s (format %d)"
203                                                 " to %d gave %s\n",
204                                                 n_from[i], formats[i],
205                                                 formats[j], n_matrix[i][j]);
206                         if (n_matrix[i][j] == n_from[j]) {
207                                 
208                         /* We don't have a from name for these yet (and we can't map to them to find it out) */
209                         } else if (n_matrix[i][j] == NULL && n_from[i] == NULL) {
210                                 
211                         /* we can't map to these two */
212                         } else if (n_matrix[i][j] == NULL && formats[j] == DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL) {
213                         } else if (n_matrix[i][j] == NULL && formats[j] == DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL) {
214                         } else if (n_matrix[i][j] == NULL && n_from[j] != NULL) {
215                                 err_msg = talloc_asprintf(mem_ctx,
216                                                 "dcerpc_drsuapi_DsCrackNames mismatch - from %d to %d: %s should be %s",
217                                                 formats[i], formats[j], n_matrix[i][j], n_from[j]);
218                                 torture_fail(tctx, err_msg);
219                         } else if (n_matrix[i][j] != NULL && n_from[j] == NULL) {
220                                 err_msg = talloc_asprintf(mem_ctx,
221                                                 "dcerpc_drsuapi_DsCrackNames mismatch - from %d to %d: %s should be %s",
222                                                 formats[i], formats[j], n_matrix[i][j], n_from[j]);
223                                 torture_fail(tctx, err_msg);
224                         } else if (strcmp(n_matrix[i][j], n_from[j]) != 0) {
225                                 err_msg = talloc_asprintf(mem_ctx,
226                                                 "dcerpc_drsuapi_DsCrackNames mismatch - from %d to %d: %s should be %s",
227                                                 formats[i], formats[j], n_matrix[i][j], n_from[j]);
228                                 torture_fail(tctx, err_msg);
229                         }
230                 }
231         }
232
233         return true;
234 }
235
236 bool test_DsCrackNames(struct torture_context *tctx,
237                        struct DsPrivate *priv)
238 {
239         NTSTATUS status;
240         const char *err_msg;
241         struct drsuapi_DsCrackNames r;
242         union drsuapi_DsNameRequest req;
243         uint32_t level_out;
244         union drsuapi_DsNameCtr ctr;
245         struct drsuapi_DsNameString names[1];
246         const char *dns_domain;
247         const char *nt4_domain;
248         const char *FQDN_1779_name;
249         struct ldb_context *ldb;
250         struct ldb_dn *FQDN_1779_dn;
251         struct ldb_dn *realm_dn;
252         const char *realm_dn_str;
253         const char *realm_canonical;
254         const char *realm_canonical_ex;
255         const char *user_principal_name;
256         char *user_principal_name_short;
257         const char *service_principal_name;
258         const char *canonical_name;
259         const char *canonical_ex_name;
260         const char *dom_sid;
261         const char *test_dc = torture_join_netbios_name(priv->join);
262         struct dcerpc_pipe *p = priv->drs_pipe;
263         TALLOC_CTX *mem_ctx = priv;
264
265         ZERO_STRUCT(r);
266         r.in.bind_handle                = &priv->bind_handle;
267         r.in.level                      = 1;
268         r.in.req                        = &req;
269         r.in.req->req1.codepage         = 1252; /* german */
270         r.in.req->req1.language         = 0x00000407; /* german */
271         r.in.req->req1.count            = 1;
272         r.in.req->req1.names            = names;
273         r.in.req->req1.format_flags     = DRSUAPI_DS_NAME_FLAG_NO_FLAGS;
274
275         r.in.req->req1.format_offered   = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY;
276         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT;
277
278         r.out.level_out                 = &level_out;
279         r.out.ctr                       = &ctr;
280
281         dom_sid = dom_sid_string(mem_ctx, torture_join_sid(priv->join));
282         
283         names[0].str = dom_sid;
284
285         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
286                               " offered format: %d desired format:%d\n",
287                         names[0].str,
288                         r.in.req->req1.format_offered,
289                         r.in.req->req1.format_desired);
290
291         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
292         if (!NT_STATUS_IS_OK(status)) {
293                 const char *errstr = nt_errstr(status);
294                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
295                 torture_fail(tctx, err_msg);
296         } else if (!W_ERROR_IS_OK(r.out.result)) {
297                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
298                 torture_fail(tctx, err_msg);
299         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
300                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
301                                           r.out.ctr->ctr1->array[0].status);
302                 torture_fail(tctx, err_msg);
303         }
304
305         dns_domain = r.out.ctr->ctr1->array[0].dns_domain_name;
306         nt4_domain = r.out.ctr->ctr1->array[0].result_name;
307
308         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_GUID;
309
310         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
311                               " offered format: %d desired format:%d\n",
312                         names[0].str,
313                         r.in.req->req1.format_offered,
314                         r.in.req->req1.format_desired);
315
316         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
317         if (!NT_STATUS_IS_OK(status)) {
318                 const char *errstr = nt_errstr(status);
319                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
320                 torture_fail(tctx, err_msg);
321         } else if (!W_ERROR_IS_OK(r.out.result)) {
322                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
323                 torture_fail(tctx, err_msg);
324         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
325                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
326                                           r.out.ctr->ctr1->array[0].status);
327                 torture_fail(tctx, err_msg);
328         }
329
330         priv->domain_dns_name = r.out.ctr->ctr1->array[0].dns_domain_name;
331         priv->domain_guid_str = r.out.ctr->ctr1->array[0].result_name;
332         GUID_from_string(priv->domain_guid_str, &priv->domain_guid);
333
334         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_FQDN_1779;
335
336         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
337                               " offered format: %d desired format:%d\n",
338                         names[0].str,
339                         r.in.req->req1.format_offered,
340                         r.in.req->req1.format_desired);
341
342         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
343         if (!NT_STATUS_IS_OK(status)) {
344                 const char *errstr = nt_errstr(status);
345                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
346                 torture_fail(tctx, err_msg);
347         } else if (!W_ERROR_IS_OK(r.out.result)) {
348                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
349                 torture_fail(tctx, err_msg);
350         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
351                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
352                                           r.out.ctr->ctr1->array[0].status);
353                 torture_fail(tctx, err_msg);
354         }
355
356         ldb = ldb_init(mem_ctx, tctx->ev);
357         
358         realm_dn_str = r.out.ctr->ctr1->array[0].result_name;
359         realm_dn =  ldb_dn_new(mem_ctx, ldb, realm_dn_str);
360         realm_canonical = ldb_dn_canonical_string(mem_ctx, realm_dn);
361
362         if (strcmp(realm_canonical,
363                    talloc_asprintf(mem_ctx, "%s/", dns_domain))!= 0) {
364                 err_msg = talloc_asprintf(mem_ctx, "local Round trip on canonical name failed: %s != %s!",
365                                           realm_canonical,
366                                           talloc_asprintf(mem_ctx, "%s/", dns_domain));
367                 torture_fail(tctx, err_msg);
368         };
369
370         realm_canonical_ex = ldb_dn_canonical_ex_string(mem_ctx, realm_dn);
371
372         if (strcmp(realm_canonical_ex, 
373                    talloc_asprintf(mem_ctx, "%s\n", dns_domain))!= 0) {
374                 err_msg = talloc_asprintf(mem_ctx, "local Round trip on canonical ex name failed: %s != %s!",
375                                           realm_canonical_ex,
376                                           talloc_asprintf(mem_ctx, "%s\n", dns_domain));
377                 torture_fail(tctx, err_msg);
378         };
379
380         r.in.req->req1.format_offered   = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT;
381         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_FQDN_1779;
382         names[0].str = nt4_domain;
383
384         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
385                               " offered format: %d desired format:%d\n",
386                         names[0].str,
387                         r.in.req->req1.format_offered,
388                         r.in.req->req1.format_desired);
389
390         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
391         if (!NT_STATUS_IS_OK(status)) {
392                 const char *errstr = nt_errstr(status);
393                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
394                 torture_fail(tctx, err_msg);
395         } else if (!W_ERROR_IS_OK(r.out.result)) {
396                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
397                 torture_fail(tctx, err_msg);
398         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
399                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
400                                           r.out.ctr->ctr1->array[0].status);
401                 torture_fail(tctx, err_msg);
402         }
403
404         priv->domain_obj_dn = r.out.ctr->ctr1->array[0].result_name;
405
406         r.in.req->req1.format_offered   = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT;
407         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_FQDN_1779;
408         names[0].str = talloc_asprintf(mem_ctx, "%s%s$", nt4_domain, test_dc);
409
410         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
411                               " offered format: %d desired format:%d\n",
412                         names[0].str,
413                         r.in.req->req1.format_offered,
414                         r.in.req->req1.format_desired);
415
416         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
417         if (!NT_STATUS_IS_OK(status)) {
418                 const char *errstr = nt_errstr(status);
419                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
420                 torture_fail(tctx, err_msg);
421         } else if (!W_ERROR_IS_OK(r.out.result)) {
422                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
423                 torture_fail(tctx, err_msg);
424         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
425                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
426                                           r.out.ctr->ctr1->array[0].status);
427                 torture_fail(tctx, err_msg);
428         }
429
430         FQDN_1779_name = r.out.ctr->ctr1->array[0].result_name;
431
432         r.in.req->req1.format_offered   = DRSUAPI_DS_NAME_FORMAT_GUID;
433         r.in.req->req1.format_desired   = DRSUAPI_DS_NAME_FORMAT_FQDN_1779;
434         names[0].str = priv->domain_guid_str;
435
436         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
437                               " offered format: %d desired format:%d\n",
438                         names[0].str,
439                         r.in.req->req1.format_offered,
440                         r.in.req->req1.format_desired);
441
442         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
443         if (!NT_STATUS_IS_OK(status)) {
444                 const char *errstr = nt_errstr(status);
445                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
446                 torture_fail(tctx, err_msg);
447         } else if (!W_ERROR_IS_OK(r.out.result)) {
448                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
449                 torture_fail(tctx, err_msg);
450         } else if (r.out.ctr->ctr1->array[0].status != DRSUAPI_DS_NAME_STATUS_OK) {
451                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed on name - %d",
452                                           r.out.ctr->ctr1->array[0].status);
453                 torture_fail(tctx, err_msg);
454         }
455
456         if (strcmp(priv->domain_dns_name, r.out.ctr->ctr1->array[0].dns_domain_name) != 0) {
457                 err_msg = talloc_asprintf(mem_ctx,
458                                 "DsCrackNames failed to return same DNS name - expected %s got %s",
459                                 priv->domain_dns_name, r.out.ctr->ctr1->array[0].dns_domain_name);
460                 torture_fail(tctx, err_msg);
461         }
462
463         FQDN_1779_dn = ldb_dn_new(mem_ctx, ldb, FQDN_1779_name);
464
465         canonical_name = ldb_dn_canonical_string(mem_ctx, FQDN_1779_dn);
466         canonical_ex_name = ldb_dn_canonical_ex_string(mem_ctx, FQDN_1779_dn);
467
468         user_principal_name = talloc_asprintf(mem_ctx, "%s$@%s", test_dc, dns_domain);
469
470         /* form up a user@DOMAIN */
471         user_principal_name_short = talloc_asprintf(mem_ctx, "%s$@%s", test_dc, nt4_domain);
472         /* variable nt4_domain includs a trailing \ */
473         user_principal_name_short[strlen(user_principal_name_short) - 1] = '\0';
474         
475         service_principal_name = talloc_asprintf(mem_ctx, "HOST/%s", test_dc);
476         {
477                 
478                 struct {
479                         enum drsuapi_DsNameFormat format_offered;
480                         enum drsuapi_DsNameFormat format_desired;
481                         const char *comment;
482                         const char *str;
483                         const char *expected_str;
484                         const char *expected_dns;
485                         enum drsuapi_DsNameStatus status;
486                         enum drsuapi_DsNameStatus alternate_status;
487                         enum drsuapi_DsNameFlags flags;
488                         bool skip;
489                 } crack[] = {
490                         {
491                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
492                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
493                                 .str = user_principal_name,
494                                 .expected_str = FQDN_1779_name,
495                                 .status = DRSUAPI_DS_NAME_STATUS_OK
496                         },
497                         {
498                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
499                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
500                                 .str = user_principal_name_short,
501                                 .expected_str = FQDN_1779_name,
502                                 .status = DRSUAPI_DS_NAME_STATUS_OK
503                         },
504                         {
505                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
506                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
507                                 .str = FQDN_1779_name,
508                                 .status = DRSUAPI_DS_NAME_STATUS_NO_MAPPING
509                         },
510                         {
511                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
512                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
513                                 .str = service_principal_name,
514                                 .expected_str = FQDN_1779_name,
515                                 .status = DRSUAPI_DS_NAME_STATUS_OK
516                         },
517                         {
518                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
519                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
520                                 .str = talloc_asprintf(mem_ctx, "cifs/%s.%s", test_dc, dns_domain),
521                                 .comment = "ServicePrincipal Name",
522                                 .expected_str = FQDN_1779_name,
523                                 .status = DRSUAPI_DS_NAME_STATUS_OK
524                         },
525                         {
526                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
527                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL,
528                                 .str = FQDN_1779_name,
529                                 .expected_str = canonical_name,
530                                 .status = DRSUAPI_DS_NAME_STATUS_OK
531                         },
532                         {
533                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_CANONICAL, 
534                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
535                                 .str = canonical_name,
536                                 .expected_str = FQDN_1779_name,
537                                 .status = DRSUAPI_DS_NAME_STATUS_OK
538                         },
539                         {
540                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
541                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL_EX,
542                                 .str = FQDN_1779_name,
543                                 .expected_str = canonical_ex_name,
544                                 .status = DRSUAPI_DS_NAME_STATUS_OK
545                         },
546                         {
547                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_CANONICAL_EX, 
548                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
549                                 .str = canonical_ex_name,
550                                 .expected_str = FQDN_1779_name,
551                                 .status = DRSUAPI_DS_NAME_STATUS_OK
552                         },
553                         {
554                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
555                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL,
556                                 .str = FQDN_1779_name,
557                                 .comment = "DN to cannoical syntactial only",
558                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
559                                 .expected_str = canonical_name,
560                                 .flags = DRSUAPI_DS_NAME_FLAG_SYNTACTICAL_ONLY
561                         },
562                         {
563                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
564                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL_EX,
565                                 .str = FQDN_1779_name,
566                                 .comment = "DN to cannoical EX syntactial only",
567                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
568                                 .expected_str = canonical_ex_name,
569                                 .flags = DRSUAPI_DS_NAME_FLAG_SYNTACTICAL_ONLY
570                         },
571                         {
572                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
573                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_DISPLAY,
574                                 .str = FQDN_1779_name,
575                                 .status = DRSUAPI_DS_NAME_STATUS_OK
576                         },
577                         {
578                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
579                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_GUID,
580                                 .str = FQDN_1779_name,
581                                 .status = DRSUAPI_DS_NAME_STATUS_OK
582                         },
583                         {
584                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
585                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
586                                 .str = priv->domain_guid_str,
587                                 .comment = "Domain GUID to NT4 ACCOUNT",
588                                 .expected_str = nt4_domain,
589                                 .status = DRSUAPI_DS_NAME_STATUS_OK
590                         },
591                         {
592                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
593                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL,
594                                 .str = priv->domain_guid_str,
595                                 .comment = "Domain GUID to Canonical",
596                                 .expected_str = talloc_asprintf(mem_ctx, "%s/", dns_domain),
597                                 .status = DRSUAPI_DS_NAME_STATUS_OK
598                         },
599                         {
600                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
601                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_CANONICAL_EX,
602                                 .str = priv->domain_guid_str,
603                                 .comment = "Domain GUID to Canonical EX",
604                                 .expected_str = talloc_asprintf(mem_ctx, "%s\n", dns_domain),
605                                 .status = DRSUAPI_DS_NAME_STATUS_OK
606                         },
607                         {
608                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_DISPLAY,
609                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
610                                 .str = "CN=Microsoft Corporation,L=Redmond,S=Washington,C=US",
611                                 .comment = "display name for Microsoft Support Account",
612                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
613                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE,
614                                 .skip = torture_setting_bool(tctx, "samba4", false)
615                         },
616                         {
617                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
618                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
619                                 .str = GUID_string2(mem_ctx, torture_join_user_guid(priv->join)),
620                                 .comment = "Account GUID -> DN",
621                                 .expected_str = FQDN_1779_name,
622                                 .status = DRSUAPI_DS_NAME_STATUS_OK
623                         },
624                         {
625                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
626                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
627                                 .str = GUID_string2(mem_ctx, torture_join_user_guid(priv->join)),
628                                 .comment = "Account GUID -> NT4 Account",
629                                 .expected_str = talloc_asprintf(mem_ctx, "%s%s$", nt4_domain, test_dc),
630                                 .status = DRSUAPI_DS_NAME_STATUS_OK
631                         },
632                         {               
633                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
634                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
635                                 .str = GUID_string2(mem_ctx, &priv->dcinfo.site_guid),
636                                 .comment = "Site GUID",
637                                 .expected_str = priv->dcinfo.site_dn,
638                                 .status = DRSUAPI_DS_NAME_STATUS_OK
639                         },
640                         {
641                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
642                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
643                                 .str = GUID_string2(mem_ctx, &priv->dcinfo.computer_guid),
644                                 .comment = "Computer GUID",
645                                 .expected_str = priv->dcinfo.computer_dn,
646                                 .status = DRSUAPI_DS_NAME_STATUS_OK
647                         },
648                         {
649                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
650                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
651                                 .str = GUID_string2(mem_ctx, &priv->dcinfo.computer_guid),
652                                 .comment = "Computer GUID -> NT4 Account",
653                                 .status = DRSUAPI_DS_NAME_STATUS_OK
654                         },
655                         {
656                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
657                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
658                                 .str = GUID_string2(mem_ctx, &priv->dcinfo.server_guid),
659                                 .comment = "Server GUID",
660                                 .expected_str = priv->dcinfo.server_dn,
661                                 .status = DRSUAPI_DS_NAME_STATUS_OK
662                         },
663                         {
664                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
665                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
666                                 .str = GUID_string2(mem_ctx, &priv->dcinfo.ntds_guid),
667                                 .comment = "NTDS GUID",
668                                 .expected_str = priv->dcinfo.ntds_dn,
669                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
670                                 .skip = GUID_all_zero(&priv->dcinfo.ntds_guid)
671                         },
672                         {
673                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_DISPLAY,
674                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
675                                 .str = test_dc,
676                                 .comment = "DISLPAY NAME search for DC short name",
677                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
678                         },
679                         {
680                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
681                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
682                                 .str = talloc_asprintf(mem_ctx, "krbtgt/%s", dns_domain),
683                                 .comment = "Looking for KRBTGT as a serivce principal",
684                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
685                                 .expected_dns = dns_domain
686                         },
687                         {
688                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
689                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
690                                 .str = talloc_asprintf(mem_ctx, "bogus/%s", dns_domain),
691                                 .comment = "Looking for bogus serivce principal",
692                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
693                                 .expected_dns = dns_domain
694                         },
695                         {
696                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
697                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
698                                 .str = talloc_asprintf(mem_ctx, "bogus/%s.%s", test_dc, dns_domain),
699                                 .comment = "Looking for bogus serivce on test DC",
700                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
701                                 .expected_dns = talloc_asprintf(mem_ctx, "%s.%s", test_dc, dns_domain)
702                         },
703                         { 
704                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
705                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
706                                 .str = talloc_asprintf(mem_ctx, "krbtgt"),
707                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
708                         },
709                         { 
710                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
711                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
712                                 .comment = "Looking for the kadmin/changepw service as a serivce principal",
713                                 .str = talloc_asprintf(mem_ctx, "kadmin/changepw"),
714                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
715                                 .expected_str = talloc_asprintf(mem_ctx, "CN=krbtgt,CN=Users,%s", realm_dn_str),
716                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE
717                         },
718                         {
719                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
720                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
721                                 .str = talloc_asprintf(mem_ctx, "cifs/%s.%s@%s", 
722                                                        test_dc, dns_domain,
723                                                        dns_domain),
724                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY
725                         },
726                         {
727                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
728                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
729                                 .str = talloc_asprintf(mem_ctx, "cifs/%s.%s@%s", 
730                                                        test_dc, dns_domain,
731                                                        "BOGUS"),
732                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
733                                 .expected_dns = "BOGUS"
734                         },
735                         {
736                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
737                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
738                                 .str = talloc_asprintf(mem_ctx, "cifs/%s.%s@%s", 
739                                                        test_dc, "REALLY",
740                                                        "BOGUS"),
741                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
742                                 .expected_dns = "BOGUS"
743                         },
744                         {
745                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
746                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
747                                 .str = talloc_asprintf(mem_ctx, "cifs/%s.%s", 
748                                                        test_dc, dns_domain),
749                                 .status = DRSUAPI_DS_NAME_STATUS_OK
750                         },
751                         {
752                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
753                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
754                                 .str = talloc_asprintf(mem_ctx, "cifs/%s", 
755                                                        test_dc),
756                                 .status = DRSUAPI_DS_NAME_STATUS_OK
757                         },
758                         {
759                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
760                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
761                                 .str = "NOT A GUID",
762                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
763                         },
764                         {
765                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
766                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
767                                 .str = "NOT A SID",
768                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
769                         },
770                         {
771                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
772                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
773                                 .str = "NOT AN NT4 NAME",
774                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
775                         },
776                         {
777                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
778                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_GUID,
779                                 .comment = "Unparsable DN",
780                                 .str = "NOT A DN",
781                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
782                         },
783                         {
784                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
785                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
786                                 .comment = "Unparsable user principal",
787                                 .str = "NOT A PRINCIPAL",
788                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
789                         },
790                         {
791                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
792                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
793                                 .comment = "Unparsable service principal",
794                                 .str = "NOT A SERVICE PRINCIPAL",
795                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
796                         },
797                         {
798                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_GUID,
799                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
800                                 .comment = "BIND GUID (ie, not in the directory)",
801                                 .str = GUID_string2(mem_ctx, &priv->bind_guid),
802                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
803                         },
804                         {
805                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
806                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
807                                 .comment = "Unqualified Machine account as user principal",
808                                 .str = talloc_asprintf(mem_ctx, "%s$", test_dc),
809                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
810                         },
811                         {
812                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
813                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
814                                 .comment = "Machine account as service principal",
815                                 .str = talloc_asprintf(mem_ctx, "%s$", test_dc),
816                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
817                         },
818                         {
819                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SERVICE_PRINCIPAL,
820                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
821                                 .comment = "Full Machine account as service principal",
822                                 .str = user_principal_name,
823                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
824                         },
825                         {
826                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
827                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
828                                 .comment = "Realm as an NT4 domain lookup",
829                                 .str = talloc_asprintf(mem_ctx, "%s\\", dns_domain),
830                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
831                         }, 
832                         {
833                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
834                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
835                                 .comment = "BUILTIN\\ -> DN",
836                                 .str = "BUILTIN\\",
837                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
838                         }, 
839                         {
840                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
841                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
842                                 .comment = "NT AUTHORITY\\ -> DN",
843                                 .str = "NT AUTHORITY\\",
844                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
845                         }, 
846                         {
847                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
848                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
849                                 .comment = "NT AUTHORITY\\ANONYMOUS LOGON -> DN",
850                                 .str = "NT AUTHORITY\\ANONYMOUS LOGON",
851                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
852                         }, 
853                         {
854                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
855                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
856                                 .comment = "NT AUTHORITY\\SYSTEM -> DN",
857                                 .str = "NT AUTHORITY\\SYSTEM",
858                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
859                         }, 
860                         {
861                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
862                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
863                                 .comment = "BUITIN SID -> NT4 account",
864                                 .str = SID_BUILTIN,
865                                 .status = DRSUAPI_DS_NAME_STATUS_NO_MAPPING,
866                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE
867                         }, 
868                         {
869                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
870                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
871                                 .str = SID_BUILTIN,
872                                 .comment = "Builtin Domain SID -> DN",
873                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
874                                 .expected_str = talloc_asprintf(mem_ctx, "CN=Builtin,%s", realm_dn_str),
875                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE
876                         },
877                         {
878                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
879                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
880                                 .str = SID_BUILTIN_ADMINISTRATORS,
881                                 .comment = "Builtin Administrors SID -> DN",
882                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
883                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE
884                         },
885                         {
886                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
887                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
888                                 .str = SID_BUILTIN_ADMINISTRATORS,
889                                 .comment = "Builtin Administrors SID -> NT4 Account",
890                                 .status = DRSUAPI_DS_NAME_STATUS_OK,
891                                 .alternate_status = DRSUAPI_DS_NAME_STATUS_NOT_UNIQUE
892                         },
893                         {
894                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
895                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
896                                 .str = SID_NT_ANONYMOUS,
897                                 .comment = "NT Anonymous SID -> NT4 Account",
898                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
899                         },
900                         {
901                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
902                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
903                                 .str = SID_NT_SYSTEM,
904                                 .comment = "NT SYSTEM SID -> NT4 Account",
905                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
906                         },
907                         {
908                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
909                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
910                                 .comment = "Domain SID -> DN",
911                                 .str = dom_sid,
912                                 .expected_str = realm_dn_str,
913                                 .status = DRSUAPI_DS_NAME_STATUS_OK
914                         },
915                         {
916                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_SID_OR_SID_HISTORY,
917                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_NT4_ACCOUNT,
918                                 .comment = "Domain SID -> NT4 account",
919                                 .str = dom_sid,
920                                 .expected_str = nt4_domain,
921                                 .status = DRSUAPI_DS_NAME_STATUS_OK
922                         },
923                         {
924                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
925                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
926                                 .comment = "invalid user principal name",
927                                 .str = "foo@bar",
928                                 .status = DRSUAPI_DS_NAME_STATUS_DOMAIN_ONLY,
929                                 .expected_dns = "bar"
930                         },
931                         {
932                                 .format_offered = DRSUAPI_DS_NAME_FORMAT_USER_PRINCIPAL,
933                                 .format_desired = DRSUAPI_DS_NAME_FORMAT_FQDN_1779,
934                                 .comment = "invalid user principal name in valid domain",
935                                 .str = talloc_asprintf(mem_ctx, "invalidusername@%s", dns_domain),
936                                 .status = DRSUAPI_DS_NAME_STATUS_NOT_FOUND
937                         }
938                 };
939                 int i;
940                 
941                 for (i=0; i < ARRAY_SIZE(crack); i++) {
942                         const char *comment;
943
944                         torture_comment(tctx, "Testing DsCrackNames with name '%s'"
945                                         " offered format: %d desired format:%d\n",
946                                         crack[i].str,
947                                         crack[i].format_offered,
948                                         crack[i].format_desired);
949
950                         r.in.req->req1.format_flags   = crack[i].flags;
951                         r.in.req->req1.format_offered = crack[i].format_offered;
952                         r.in.req->req1.format_desired = crack[i].format_desired;
953                         names[0].str = crack[i].str;
954                         
955                         if (crack[i].comment) {
956                                 comment = talloc_asprintf(mem_ctx,
957                                                           "'%s' with name '%s' offered format:%d desired format:%d\n",
958                                                           crack[i].comment, names[0].str,
959                                                           r.in.req->req1.format_offered,
960                                                           r.in.req->req1.format_desired);
961                         } else {
962                                 comment = talloc_asprintf(mem_ctx, "'%s' offered format:%d desired format:%d\n",
963                                                           names[0].str,
964                                                           r.in.req->req1.format_offered,
965                                                           r.in.req->req1.format_desired);
966                         }
967                         if (crack[i].skip) {
968                                 torture_comment(tctx, "skipping: %s", comment);
969                                 continue;
970                         }
971                         status = dcerpc_drsuapi_DsCrackNames_r(p->binding_handle, mem_ctx, &r);
972                         if (!NT_STATUS_IS_OK(status)) {
973                                 const char *errstr = nt_errstr(status);
974                                 err_msg = talloc_asprintf(mem_ctx, "dcerpc_drsuapi_DsCrackNames failed - %s", errstr);
975                                 torture_fail(tctx, err_msg);
976                         } else if (!W_ERROR_IS_OK(r.out.result)) {
977                                 err_msg = talloc_asprintf(mem_ctx, "DsCrackNames failed - %s", win_errstr(r.out.result));
978                                 torture_fail(tctx, err_msg);
979                         } else if (r.out.ctr->ctr1->array[0].status != crack[i].status) {
980                                 if (crack[i].alternate_status) {
981                                         if (r.out.ctr->ctr1->array[0].status != crack[i].alternate_status) {
982                                                 err_msg = talloc_asprintf(mem_ctx,
983                                                                 "DsCrackNames unexpected status %d, wanted %d or %d on: %s",
984                                                                 r.out.ctr->ctr1->array[0].status,
985                                                                 crack[i].status,
986                                                                 crack[i].alternate_status,
987                                                                 comment);
988                                                 torture_fail(tctx, err_msg);
989                                         }
990                                 } else {
991                                         err_msg = talloc_asprintf(mem_ctx,
992                                                         "DsCrackNames unexpected status %d, wanted %d on: %s\n",
993                                                         r.out.ctr->ctr1->array[0].status,
994                                                         crack[i].status,
995                                                         comment);
996                                         torture_fail(tctx, err_msg);
997                                 }
998                         } else if (crack[i].expected_str &&
999                                    (!r.out.ctr->ctr1->count ||
1000                                     !r.out.ctr->ctr1->array[0].result_name))
1001                         {
1002                                 if (!r.out.ctr->ctr1->count) {
1003                                         err_msg = talloc_asprintf(mem_ctx,
1004                                                                   "DsCrackNames failed - got 0 entries, expected %s on %s",
1005                                                                   crack[i].expected_str, comment);
1006                                         torture_fail(tctx, err_msg);
1007                                 } else {
1008                                         err_msg = talloc_asprintf(mem_ctx,
1009                                                                   "DsCrackNames failed - got NULL pointer, expected %s on %s",
1010                                                                   crack[i].expected_str, comment);
1011                                         torture_fail(tctx, err_msg);
1012                                 }
1013                         } else if (crack[i].expected_str
1014                                    && (strcmp(r.out.ctr->ctr1->array[0].result_name,
1015                                               crack[i].expected_str) != 0))
1016                         {
1017                                 if (strcasecmp(r.out.ctr->ctr1->array[0].result_name,
1018                                                crack[i].expected_str) != 0) {
1019                                         err_msg = talloc_asprintf(mem_ctx,
1020                                                         "DsCrackNames failed - got %s, expected %s on %s",
1021                                                         r.out.ctr->ctr1->array[0].result_name,
1022                                                         crack[i].expected_str, comment);
1023                                         torture_fail(tctx, err_msg);
1024                                 } else {
1025                                         torture_comment(tctx,
1026                                                         "(warning) DsCrackNames returned different case - got %s, expected %s on %s\n",
1027                                                         r.out.ctr->ctr1->array[0].result_name,
1028                                                         crack[i].expected_str, comment);
1029                                 }
1030                         } else if (crack[i].expected_dns
1031                                    && (strcmp(r.out.ctr->ctr1->array[0].dns_domain_name,
1032                                               crack[i].expected_dns) != 0)) {
1033                                 err_msg = talloc_asprintf(mem_ctx,
1034                                                 "DsCrackNames failed - got DNS name %s, expected %s on %s",
1035                                                 r.out.ctr->ctr1->array[0].result_name,
1036                                                 crack[i].expected_str, comment);
1037                                 torture_fail(tctx, err_msg);
1038                         }
1039
1040                         torture_comment(tctx, "Testing DsCrackNames got %s\n", r.out.ctr->ctr1->array[0].result_name);
1041                 }
1042         }
1043
1044         return test_DsCrackNamesMatrix(tctx, priv, FQDN_1779_name,
1045                                         user_principal_name, service_principal_name);
1046 }
1047
1048 /**
1049  * Test case setup for CrackNames
1050  */
1051 static bool torture_drsuapi_cracknames_setup(struct torture_context *tctx, void **data)
1052 {
1053         struct DsCrackNamesPrivate *priv;
1054
1055         *data = priv = talloc_zero(tctx, struct DsCrackNamesPrivate);
1056
1057         return torture_drsuapi_tcase_setup_common(tctx, &priv->base);
1058 }
1059
1060 /**
1061  * Test case tear-down for CrackNames
1062  */
1063 static bool torture_drsuapi_cracknames_teardown(struct torture_context *tctx, void *data)
1064 {
1065         struct DsCrackNamesPrivate *priv = talloc_get_type(data, struct DsCrackNamesPrivate);
1066
1067         return torture_drsuapi_tcase_teardown_common(tctx, &priv->base);
1068 }
1069
1070 /**
1071  * CRACKNAMES test suite implementation
1072  */
1073 void torture_rpc_drsuapi_cracknames_tcase(struct torture_suite *suite)
1074 {
1075         typedef bool (*run_func) (struct torture_context *test, void *tcase_data);
1076
1077         struct torture_tcase *tcase = torture_suite_add_tcase(suite, "cracknames");
1078
1079         torture_tcase_set_fixture(tcase,
1080                                   torture_drsuapi_cracknames_setup,
1081                                   torture_drsuapi_cracknames_teardown);
1082
1083         torture_tcase_add_simple_test(tcase, "cracknames-test", (run_func)test_DsCrackNames);
1084 }